From 219d63bada37a4d2e9f4b00d12371b96dc070b05 Mon Sep 17 00:00:00 2001 From: Luca Elia Date: Sat, 11 Jun 2022 19:08:01 +0200 Subject: [PATCH] igs017.cpp, igs022.cpp: Improved protection and decryption; ,oved protection data to external files. (#9890) * igs017.cpp: Improved protection and decryption [Luca Elia] - Implemented "magic" i/o as a memory map (IGS_MUX) for added flexibility - Hooked up IGS_INCDEC protection to cpoker2, tarzanc, spkrform, starzan - Implemented specific IGS_INC protection in cpoker2 - Hooked up improved IGS022 protection to lhzb2, sqlz2 - Added IGS025 string protection to lhzb2, lhzb2a, mgcs, spkrform, slqz2, starzan, tarzanc, tjsb - Palette scramble and tweaked tiles decryption in tarzanc (used also by starzan, happyskl, cpoker2) - Decrypted sprites in tarzanc and starzan (used also by happyskl) - Lamps and layout for starzan, happyskl, cpoker2 - Cleaned up/finished hopper emulation, added diplocations - Joystick inputs in mgcs - Finished inputs in spkrform. Allow hiding gambling (switching to Formosa and back) - Moved protection data to external files * igs022.cpp: Fixes for igs017.cpp games [Luca Elia, RockyWall] - Fixed initial auto-DMA mode - Enlarged internal RAM. Added stack - Fixed command 12: Copy -> Stack Push - Added command 45: Stack Pop - Fixed command 6d opcode 1: Add Imm -> Sub Values - Added command 6d opcode 0: Add Values - Extended logging Machines promoted to working ---------------------------- Tarzan Chuang Tian Guan (China, V109C, set 1) [Luca Elia, iq_132, Ivan Vangelista, Guru, Dyq, bnathan] Super Tarzan (Italy, V100I) [Luca Elia, iq_132, Ivan Vangelista, f205v, Mirko Buffoni] Happy Skill (Italy, V611IT) [Luca Elia, Ivan Vangelista, Caius, The Dumping Union] Champion Poker 2 (V100A) [Luca Elia, Ivan Vangelista, Jorge Silva, Fernando Oliveira] Long Hu Zhengba 2 (China, set 1) [Luca Elia, RockyWall, David Haywood, iq_132, Pierpaolo Prazzoli, XingXing] Shuang Long Qiang Zhu 2 VS (China, VS203J) [Luca Elia, RockyWall, David Haywood, iq_132, Pierpaolo Prazzoli, XingXing] Clones promoted to working -------------------------- Super Poker (V100xD03) / Formosa [Luca Elia, ANY] --- src/mame/drivers/igs017.cpp | 4606 +++++++++++--------- src/mame/layout/igsslot.lay | 132 + src/mame/machine/igs022.cpp | 468 +- src/mame/machine/igs022.h | 27 +- src/mame/machine/pgmprot_igs025_igs022.cpp | 21 +- src/mame/mame.lst | 6 +- src/mame/video/igs017_igs031.cpp | 8 +- 7 files changed, 3049 insertions(+), 2219 deletions(-) create mode 100644 src/mame/layout/igsslot.lay diff --git a/src/mame/drivers/igs017.cpp b/src/mame/drivers/igs017.cpp index bc5cedc85a9..174e072896f 100644 --- a/src/mame/drivers/igs017.cpp +++ b/src/mame/drivers/igs017.cpp @@ -9,41 +9,42 @@ CPU: Z180 or 68000 Video: IGS017 or IGS031 (2 tilemaps, variable size sprites, protection) Other: IGS025 (8255), IGS022 (protection, MCU), IGS029 (protection) -Sound: M6295 + [YM2413] +Sound: M6295(K668/AR17961) + [YM2413(U3567)] -------------------------------------------------------------------------------------------------------------- -Year + Game PCB CPU Sound Custom Other -------------------------------------------------------------------------------------------------------------- -96 Shuzi Leyuan NO-0131-4 Z180 M6295 YM2413 IGS017 8255 Battery -97 Mj Super Da Man Guan II NO-0147-6 68000 M6295 IGS031 8255 Battery -97 Mj Tian Jiang Shen Bing NO-0157-2 Z180 M6295 YM2413 IGS017 IGS025 Battery -97 Mj Man Guan Daheng NO-0252 68000 M6295 IGS031 IGS025 IGS???* Battery -98 Genius 6 NO-0131-4 Z180 M6295 YM2413 IGS017 IGS003c Battery -98 Mj Long Hu Zhengba 2 NO-0206 68000 M6295 IGS031 IGS025 IGS022* Battery -98 Mj Shuang Long Qiang Zhu 2 NO-0207 68000 M6295 IGS031 IGS025 IGS022 Battery -98 Mj Man Guan Caishen NO-0192-1 68000 M6295 IGS017 IGS025 IGS029 Battery -99 Tarzan (V107) NO-0228? Z180 M6295 IGS031 IGS025 IGS029 Battery -99 Tarzan (V109C) NO-0248-1 Z180 M6295 IGS031 IGS025 Battery -00? Super Tarzan (V100I) NO-0230-1 Z180 M6295 IGS031 IGS025 Battery -01? Happy Skill (V611) NO-0281 Z180 M6295 (K668) IGS031 IGS025 Battery -01? unknown (V100A) unreadable Z180 M6295 IGS031 IGS025 Battery -?? Super Poker / Formosa NO-0187 Z180 M6295 YM2413 IGS017 IGS025 Battery -------------------------------------------------------------------------------------------------------------- - * not present in one set +-------------------------------------------------------------------------------------------------------- +Year + Game PCB CPU Sound Custom Other +-------------------------------------------------------------------------------------------------------- +96 Shuzi Leyuan (V127M) NO-0131-4 Z180 AR17961 U3567 IGS017 8255 Battery +97 Super Da Man Guan II (V754C) NO-0147-6 68000 K668 IGS031 8255 Battery +97 Tian Jiang Shen Bing (V137C) NO-0157-2 Z180 AR17961 U3567 IGS017 IGS025 Battery +97 Man Guan Daheng (V123T1) NO-0252 68000 M6295 IGS031 IGS025 IGS???* Battery +98 Genius 6 (V110F) NO-0131-4 Z180 K668 U3567 IGS017 IGS003c Battery +98 Long Hu Zhengba 2 (set 1) NO-0206 68000 K668 IGS031 IGS025 IGS022* Battery +98 Shuang Long Qiang Zhu 2 VS (VS203J) NO-0207 68000 K668 IGS031 IGS025 IGS022 Battery +98 Man Guan Caishen (V103CS) NO-0192-1 68000 K668 IGS017 IGS025 IGS029 Battery +99 Tarzan (V107) NO-0228? Z180 U6295 IGS031 IGS025 IGS029 Battery +99 Tarzan (V109C) NO-0248-1 Z180 U6295 IGS031 IGS025 Battery +00? Super Tarzan (V100I) NO-0230-1 Z180 K668 IGS031 IGS025 Battery +00? Happy Skill (V611IT) NO-0281 Z180 K668 IGS031 IGS025 Battery +00? Champion Poker 2 (V100A) unreadable Z180 M6295 IGS031 IGS025 Battery +00? Super Poker (V100xD03) / Formosa NO-0187 Z180 K668 U3567 IGS017 IGS025 Battery +-------------------------------------------------------------------------------------------------------- + not present in another set * To Do: - Protection emulation in some games, instead of patching the roms. - NVRAM. -- mgcs: implement joystick inputs. Finish IGS029 protection simulation. +- mgcs: Finish IGS029 protection simulation. Notes: -- iqblocka: keep start pressed during boot for DSWs & input test. Keep test (F2) pressed for book-keeping / setup [pass: press Play (2)] -- iqblockf/genius6: for gambling, press service1 (9) then press Play (2) eight times. Then test (F2) enters book-keeping / setup -- lhzb2, mgcs, tjsb: press service + stats during test mode for sound test. -- mgdh: press A + B during test mode for sound test (B1+B2+B3 when using a joystick). -- mgdh: test mode is accessed by keeping test pressed during boot (as usual), but pressing F2+F3 in MAME - does not actually work. It does work if F2 is pressed in the debug window at boot, and held while closing it. +- Test mode is usually accessed by keeping test (F2) pressed during boot. +- iqblocka: keep start (1) pressed during boot for DSWs & input test. Keep test (F2) pressed for book-keeping / setup [pass: press deal (2)]. +- iqblockf/genius6: press service1 (9) then press deal (2) eight times to switch to gambling. Then test (F2) enters book-keeping / setup. +- lhzb2, mgcs, slqz2, tjsb: press test (F2) + book (0) during inputs test for sound test. +- mgdh, sdmg2: press keys A + B during test mode for sound test (B1 + B2 + B3 when using a joystick in mgdh). +- spkrform: to switch from poker to Formosa press service1 (9). To switch back, press in sequence: + service3 (right of 0) then Bet (M) then press "Hold 1".."Hold 5" (Z, X, C, V, B) ************************************************************************************************************/ @@ -52,18 +53,232 @@ Notes: #include "cpu/m68000/m68000.h" #include "cpu/z180/z180.h" #include "machine/i8255.h" -#include "sound/okim6295.h" -#include "sound/ymopl.h" -#include "machine/igs025.h" #include "machine/igs022.h" #include "machine/ticket.h" #include "machine/timer.h" +#include "sound/okim6295.h" +#include "sound/ymopl.h" #include "video/igs017_igs031.h" #include "emupal.h" #include "screen.h" #include "speaker.h" +#include "igspoker.lh" +#include "igsslot.lh" + +#define LOG_PROT_STRING (1U << 1) +#define LOG_PROT_BITSWAP (1U << 2) +#define LOG_PROT_INCDEC (1U << 3) +#define LOG_PROT_INC (1U << 4) +#define LOG_PROT_SCRAMBLE (1U << 5) +#define LOG_PROT_REMAP (1U << 6) +#define LOG_PROT_IGS022 (1U << 7) +#define LOG_PROT_IGS029 (1U << 8) + +//#define VERBOSE (LOG_GENERAL | LOG_PROT_STRING | LOG_PROT_BITSWAP | LOG_PROT_INCDEC | LOG_PROT_INC | LOG_PROT_SCRAMBLE | LOG_PROT_REMAP | LOG_PROT_IGS022 | LOG_PROT_IGS029) +#define VERBOSE (0) +#include "logmacro.h" + +/*************************************************************************** + + ---- IGS Multiplexer ---- + +***************************************************************************/ + +class igs_mux_device : + public device_t, + public device_memory_interface +{ +public: + igs_mux_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + void address_w(u8 data); + void data_w(u8 data); + u8 data_r(); + +protected: + virtual void device_start() override; + virtual void device_reset() override; + + virtual space_config_vector memory_space_config() const override; + +private: + address_space_config m_space_config; + u8 m_address = 0; +}; + +device_memory_interface::space_config_vector igs_mux_device::memory_space_config() const +{ + return space_config_vector { + std::make_pair(0, &m_space_config) + }; +} + +DEFINE_DEVICE_TYPE(IGS_MUX, igs_mux_device, "igs_mux", "IGS I/O Multiplexer") + +igs_mux_device::igs_mux_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, IGS_MUX, tag, owner, clock) + , device_memory_interface(mconfig, *this) + , m_space_config("igs_mux", ENDIANNESS_LITTLE, 8, 8, 0) +{ } + +void igs_mux_device::device_start() +{ + save_item(NAME(m_address)); +} + +void igs_mux_device::device_reset() +{ +} + +void igs_mux_device::address_w(u8 data) +{ + m_address = data; +} + +void igs_mux_device::data_w(u8 data) +{ + space().write_byte(m_address, data); +} + +u8 igs_mux_device::data_r() +{ + return space().read_byte(m_address); +} + +/*************************************************************************** + + ---- IGS String Protection ---- + +***************************************************************************/ + +class igs_string_device : public device_t +{ +public: + igs_string_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + u8 result_r(); // 0x05: result_r + void do_bitswap_w(offs_t offset, u8 data); // 0x20-0x27: do_bitswap_w + u8 advance_string_offs_r(address_space &space); // 0x40: advance_string_offs_r + + // Call after decryption, e.g. at the end of init_ + void dump(const char *filename, u32 string_addr, u32 xor_addr, bool is_16bits) const; + +protected: + virtual void device_start() override; + virtual void device_reset() override; + +private: + required_memory_region m_region_key; + + u16 m_string_word = 0, m_word = 0; + u8 m_string_offs = 0; +}; + +DEFINE_DEVICE_TYPE(IGS_STRING, igs_string_device, "igs_string", "IGS String Protection") + +igs_string_device::igs_string_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, IGS_STRING, tag, owner, clock) + , m_region_key(*this, DEVICE_SELF) +{ } + +void igs_string_device::dump(const char *filename, u32 string_addr, u32 xor_addr, bool is_16bits) const +{ + FILE *f = fopen(filename, "wb"); + if (!f) + { + printf("Error opening igs_string dump file %s\n", filename); + fclose(f); + return; + } + + printf("igs_string addr = %x, %x (%d bits)\n", string_addr, xor_addr, is_16bits ? 16 : 8); + + const u8 * const string_base = (const u8 *)memregion(":maincpu")->base() + string_addr; + const u8 * const xor_base = (const u8 *)memregion(":maincpu")->base() + xor_addr; + for (u32 i = 0; i < 0xec; ++i) + { + const u32 addr = is_16bits ? BYTE_XOR_BE(i) : i; + const u8 data = string_base[addr] ^ xor_base[addr]; + fwrite(&data, 1, 1, f); + } + + fclose(f); +} + +void igs_string_device::device_start() +{ + save_item(NAME(m_string_offs)); + save_item(NAME(m_string_word)); + save_item(NAME(m_word)); +} + +void igs_string_device::device_reset() +{ + m_string_word = m_word = 0; + m_string_offs = 0; +} + +u8 igs_string_device::result_r() +{ + const u8 res = bitswap<8>(m_word, 5, 2, 9, 7, 10, 13, 12, 15); + LOGMASKED(LOG_PROT_STRING, "%s: read bitswap - word %04x -> %02x\n", machine().describe_context(), m_word, res); + return res; +} + +void igs_string_device::do_bitswap_w(offs_t offset, u8 data) +{ + const u16 x = m_word; + + m_word = 0; + + m_word |= (BIT( x, 0) ^ BIT(m_string_word, 0)) << 1; // bit 1 + m_word |= (BIT(~x, 1) ^ BIT(m_string_word, 1)) << 2; // bit 2 + m_word |= (BIT(~x, 2) ^ BIT(m_string_word, 2)) << 3; // bit 3 + m_word |= (BIT(~x, 13) ^ BIT( x, 3)) << 4; // bit 4 + m_word |= (BIT(~x, 4) ^ BIT(m_string_word, 4)) << 5; // bit 5 + m_word |= (BIT( x, 5) ^ BIT(m_string_word, 5)) << 6; // bit 6 + m_word |= (BIT(~x, 6) ^ BIT(m_string_word, 6)) << 7; // bit 7 + m_word |= (BIT(~x, 7) ^ BIT(m_string_word, 7)) << 8; // bit 8 + m_word |= (BIT(~x, 8) ^ BIT(m_string_word, 8)) << 9; // bit 9 + m_word |= (BIT( x, 9) ^ BIT(m_string_word, 9)) << 10; // bit 10 + m_word |= (BIT(~x, 10) ^ BIT( x, 3)) << 11; // bit 11 + m_word |= (BIT( x, 11) ^ BIT(m_string_word, 11)) << 12; // bit 12 + m_word |= (BIT(~x, 12) ^ BIT(m_string_word, 12)) << 13; // bit 13 + m_word |= (BIT( x, 13) ^ BIT(m_string_word, 13)) << 14; // bit 14 + m_word |= (BIT( x, 14) ^ BIT(m_string_word, 14)) << 15; // bit 15 + + // bit 0 + const u16 bit0 = BIT(~x, 15) ^ BIT(x, 7); + + // bit 0 is further xor'd with bit x of the data written to this address + const u16 xor0 = BIT(data, offset & 7); + m_word |= bit0 ^ xor0; + + LOGMASKED(LOG_PROT_STRING, "%s: exec bitswap on port %02x = %02x - bit0 %x, xor0 %x, word %04x -> %04x\n", machine().describe_context(), + offset, data, bit0, xor0, x, m_word); +} + +u8 igs_string_device::advance_string_offs_r(address_space &space) +{ + const u8 next_string_offs = ((m_string_offs + 1) < 0xec ? (m_string_offs + 1) : 0); + + const u8 shift = (next_string_offs & 1) ? 8 : 0; + + const u8 next_string_byte = m_region_key ? m_region_key->base()[next_string_offs] : 0; + + const u16 next_string_word = (m_string_word & (0xff << (8 - shift))) | (next_string_byte << shift); + + LOGMASKED(LOG_PROT_STRING, "%s: advance string offs %02x -> %02x, string data = %02x, string word %04x -> %04x\n", machine().describe_context(), + m_string_offs, next_string_offs, next_string_byte, m_string_word, next_string_word); + + m_string_offs = next_string_offs; + m_string_word = next_string_word; + + return space.unmap(); +} + // Similar protection to that found in igs011.cpp: /*************************************************************************** @@ -88,18 +303,12 @@ class igs_bitswap_device : public device_t public: igs_bitswap_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - auto in_pa_callback() { return m_in_pa_cb.bind(); } - auto in_pb_callback() { return m_in_pb_cb.bind(); } - auto in_pc_callback() { return m_in_pc_cb.bind(); } - - auto out_pa_callback() { return m_out_pa_cb.bind(); } - auto out_pb_callback() { return m_out_pb_cb.bind(); } - auto out_pc_callback() { return m_out_pc_cb.bind(); } - auto out_pd_callback() { return m_out_pd_cb.bind(); } - - void address_w(u8 data); - void data_w(u8 data); - u8 data_r(); + u8 result_r(); // 0x03: result_r + void word_w(u8 data); // 0x40-0x47: word_w + void mode_f_w(u8 data); // 0x48: mode_f_w + void mode_3_w(u8 data); // 0x50: mode_3_w + void do_bitswap_w(offs_t offset, u8 data); // 0x80-0x87: do_bitswap_w + void reset_w(u8 data); // 0xa0: reset_w template void set_m3_bits(u8 b0, u8 b1, u8 b2, u8 b3); void set_mf_bits(u8 b0, u8 b1, u8 b2, u8 b3); @@ -110,21 +319,12 @@ protected: virtual void device_reset() override; private: - devcb_read8 m_in_pa_cb; - devcb_read8 m_in_pb_cb; - devcb_read8 m_in_pc_cb; + u8 m_m3 = 0, m_mf = 0; + u16 m_val = 0, m_word = 0; - devcb_write8 m_out_pa_cb; - devcb_write8 m_out_pb_cb; - devcb_write8 m_out_pc_cb; - devcb_write8 m_out_pd_cb; - - u8 m_address, m_m3, m_mf; - u16 m_val, m_word; - - u8 m_m3_bits[4][4]; - u8 m_mf_bits[4]; - u16 m_val_xor; + u8 m_m3_bits[4][4] = { {0,0,0,0}, {0,0,0,0}, {0,0,0,0}, {0,0,0,0} }; + u8 m_mf_bits[4] = {0,0,0,0}; + u16 m_val_xor = 0; }; template void igs_bitswap_device::set_m3_bits(u8 b0, u8 b1, u8 b2, u8 b3) @@ -135,11 +335,11 @@ template void igs_bitswap_device::set_m3_bits(u8 b0, u8 b1, u8 b2, m_m3_bits[N][3] = b3; #if 0 - printf("igs_bitswap: INIT m3_bits[%x] =", m3); + printf("igs_bitswap: INIT m3_bits[%x] =", N); for (int i = 0; i < 4; ++i) { - u8 bit = m_m3_bits[m3][i]; - printf(" %c%d", (bit & 0x80) ? '~' : ' ', (bit & 0x80) ? (bit ^ 0xff) : bit); + u8 bit = m_m3_bits[N][i]; + printf(" %c%d", BIT(bit, 7) ? '~' : ' ', BIT(bit, 7) ? (bit ^ 0xff) : bit); } printf("\n"); #endif @@ -168,31 +368,12 @@ void igs_bitswap_device::set_val_xor(u16 val_xor) DEFINE_DEVICE_TYPE(IGS_BITSWAP, igs_bitswap_device, "igs_bitswap", "IGS Bitswap Protection") -igs_bitswap_device::igs_bitswap_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) : - device_t(mconfig, IGS_BITSWAP, tag, owner, clock), - m_in_pa_cb(*this), - m_in_pb_cb(*this), - m_in_pc_cb(*this), - m_out_pa_cb(*this), - m_out_pb_cb(*this), - m_out_pc_cb(*this), - m_out_pd_cb(*this) -{ -} +igs_bitswap_device::igs_bitswap_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, IGS_BITSWAP, tag, owner, clock) +{ } void igs_bitswap_device::device_start() { - // resolve callbacks - m_in_pa_cb.resolve(); - m_in_pb_cb.resolve(); - m_in_pc_cb.resolve(); - m_out_pa_cb.resolve(); - m_out_pb_cb.resolve(); - m_out_pc_cb.resolve(); - m_out_pd_cb.resolve(); - - // register for save states - save_item(NAME(m_address)); save_item(NAME(m_m3)); save_item(NAME(m_mf)); save_item(NAME(m_val)); @@ -201,197 +382,90 @@ void igs_bitswap_device::device_start() void igs_bitswap_device::device_reset() { - m_address = m_m3 = m_mf = 0; + m_m3 = m_mf = 0; m_val = m_word = 0; } -void igs_bitswap_device::address_w(u8 data) +u8 igs_bitswap_device::result_r() { - m_address = data; + u8 res = bitswap<8>(m_val, 5, 2, 9, 7, 10, 13, 12, 15); + LOGMASKED(LOG_PROT_BITSWAP, "%s: read bitswap - val %04x -> %02x\n", machine().describe_context(), m_val, res); + return res; } -void igs_bitswap_device::data_w(u8 data) +void igs_bitswap_device::word_w(u8 data) { - switch (m_address) + m_word = (m_word << 8) | data; + LOGMASKED(LOG_PROT_BITSWAP, "%s: word = %02x\n", machine().describe_context(), m_word); +} + +void igs_bitswap_device::mode_f_w(u8 data) +{ + m_mf = 0; + if ((m_word & 0x0f00) != 0x0a00) m_mf |= 0x08; + if ((m_word & 0xf000) != 0x9000) m_mf |= 0x04; + if ((m_word & 0x000f) != 0x0006) m_mf |= 0x02; + if ((m_word & 0x00f0) != 0x0090) m_mf |= 0x01; + + LOGMASKED(LOG_PROT_BITSWAP, "%s: mode_f = %x (word = %04x)\n", machine().describe_context(), m_mf, m_word); +} + +void igs_bitswap_device::mode_3_w(u8 data) +{ + m_m3 = 0; + if ((m_word & 0x000f) != 0x0003) m_m3 |= 0x02; + if ((m_word & 0x00f0) != 0x0050) m_m3 |= 0x01; + + LOGMASKED(LOG_PROT_BITSWAP, "%s: mode_3 = %x (word = %04x)\n", machine().describe_context(), m_m3, m_word); +} + +void igs_bitswap_device::do_bitswap_w(offs_t offset, u8 data) +{ + u16 x = m_val; + + // bits 1-15 come from inverting some bits, xor-ing 4 bits (they change per game) with the mf bits, then shifting to the left + m_val ^= m_val_xor; + for (int i = 0; i < 4; ++i) + m_val ^= BIT(m_mf, i) << m_mf_bits[i]; + m_val <<= 1; + + // bit 0 is the xor of 4 bits from val (some inverted). The 4 bits are picked based on m3 (and they change per game) + u16 bit0 = 0; + for (int i = 0; i < 4; ++i) { - case 0x00: - if (!m_out_pa_cb.isnull()) - { - m_out_pa_cb(data); - return; - } - break; - case 0x01: - if (!m_out_pb_cb.isnull()) - { - m_out_pb_cb(data); - return; - } - break; - case 0x02: - if (!m_out_pc_cb.isnull()) - { - m_out_pc_cb(data); - return; - } - break; - case 0x03: - if (!m_out_pd_cb.isnull()) - { - m_out_pd_cb(data); - return; - } - break; - - case 0x40: // word - { - m_word = (m_word << 8) | data; - logerror("%s: word = %02x\n", machine().describe_context(), m_word); - return; - } - case 0x41: - case 0x42: - case 0x43: - case 0x44: - case 0x45: - case 0x46: - case 0x47: - // same value as address 0x40 - return; - - case 0x48: // mode_f - { - m_mf = 0; - if ((m_word & 0x0f00) != 0x0a00) m_mf |= 0x08; - if ((m_word & 0xf000) != 0x9000) m_mf |= 0x04; - if ((m_word & 0x000f) != 0x0006) m_mf |= 0x02; - if ((m_word & 0x00f0) != 0x0090) m_mf |= 0x01; - - logerror("%s: mode_f = %x (word = %04x)\n", machine().describe_context(), m_mf, m_word); - return; - } - - case 0x50: // mode_3 - { - m_m3 = 0; - if ((m_word & 0x000f) != 0x0003) m_m3 |= 0x02; - if ((m_word & 0x00f0) != 0x0050) m_m3 |= 0x01; - - logerror("%s: mode_3 = %x (word = %04x)\n", machine().describe_context(), m_m3, m_word); - return; - } - - case 0x80: // do bitswap - case 0x81: - case 0x82: - case 0x83: - case 0x84: - case 0x85: - case 0x86: - case 0x87: - { - u16 x = m_val; - - // bits 1-15 come from inverting some bits, xor-ing 4 bits (they change per game) with the mf bits, then shifting to the left - m_val ^= m_val_xor; - for (int i = 0; i < 4; ++i) - m_val ^= BIT(m_mf, i) << m_mf_bits[i]; - m_val <<= 1; - - // bit 0 is the xor of 4 bits from val (some inverted). The 4 bits are picked based on m3 (and they change per game) - u16 bit0 = 0; - for (int i = 0; i < 4; ++i) - { - u8 bit = m_m3_bits[m_m3][i]; - bit0 ^= (bit & 0x80) ? (BIT(x, bit ^ 0xff) ^ 1) : BIT(x, bit); - } - - // bit 0 is further xor'd with bit x of the data written to this address (8x) - u16 xor0 = BIT(data, m_address & 7); - m_val |= bit0 ^ xor0; - - logerror("%s: exec bitswap on port %02x = %02x - mode_3 %02x, mode_f %02x, bit0 %x, xor0 %x, val %04x -> %04x\n", machine().describe_context(), m_address, data, m_m3, m_mf, bit0, xor0, x, m_val); - return; - } - - case 0xa0: // reset - { - logerror("%s: reset bitswap - val %04x -> 0\n", machine().describe_context(), m_val); - m_val = 0; - return; - } + u8 bit = m_m3_bits[m_m3][i]; + bit0 ^= BIT(bit, 7) ? (BIT(x, bit ^ 0xff) ^ 1) : BIT(x, bit); } - logerror("%s: warning, writing to address %02x = %02x\n", machine().describe_context(), m_address, data); + // bit 0 is further xor'd with bit x of the data written to this address (8x) + u16 xor0 = BIT(data, offset & 7); + m_val |= bit0 ^ xor0; + + LOGMASKED(LOG_PROT_BITSWAP, "%s: exec bitswap on port %02x = %02x - mode_3 %02x, mode_f %02x, bit0 %x, xor0 %x, val %04x -> %04x\n", machine().describe_context(), offset, data, m_m3, m_mf, bit0, xor0, x, m_val); + return; } -u8 igs_bitswap_device::data_r() +void igs_bitswap_device::reset_w(u8 data) { - switch (m_address) - { - case 0x00: - if (!m_in_pa_cb.isnull()) - return m_in_pa_cb(); - break; - case 0x01: - if (!m_in_pb_cb.isnull()) - return m_in_pb_cb(); - break; - case 0x02: - if (!m_in_pc_cb.isnull()) - return m_in_pc_cb(); - break; - - case 0x03: // result - { - u8 res = bitswap<16>(m_val, 0,0,0,0,0,0,0,0, 5,2,9,7,10,13,12,15) & 0xff; - logerror("%s: read bitswap - val %04x -> %02x\n", machine().describe_context(), m_val, res); - return res; - } - - case 0x20: return 0x49; // 'I' - case 0x21: return 0x47; // 'G' - case 0x22: return 0x53; // 'S' - - case 0x24: return 0x41; - case 0x25: return 0x41; - case 0x26: return 0x7f; - case 0x27: return 0x41; - case 0x28: return 0x41; - - case 0x2a: return 0x3e; - case 0x2b: return 0x41; - case 0x2c: return 0x49; - case 0x2d: return 0xf9; - case 0x2e: return 0x0a; - - case 0x30: return 0x26; - case 0x31: return 0x49; - case 0x32: return 0x49; - case 0x33: return 0x49; - case 0x34: return 0x32; - } - - logerror("%s: warning, reading with address = %02x\n", machine().describe_context(), m_address); - return 0xff; + LOGMASKED(LOG_PROT_BITSWAP, "%s: reset bitswap - val %04x -> 0\n", machine().describe_context(), m_val); + m_val = 0; } - /*************************************************************************** ---- IGS Inc/Dec Protection ---- - The chip holds an internal 8-bit (or less) value. It is manipulated by issuing commands, + The chip holds an internal 4-bit value. It is manipulated by issuing commands, where each command is assigned a specific address range, and is triggered by writing to that range. Possible commands: - - INC: increment value - - DEC: decrement value - - RESET: value = 0 + - [offset 0] RESET: value = 0 + - [offset 1] DEC: decrement value + - [offset 3] INC: increment value The protection value is read from an additional address range: - - READ: read bitswap(value). Only 4 bits are checked. + - [offset 5] READ: read bitswap(value). Only 4 bits are checked (0-32-1--, i.e. mask $B4) ***************************************************************************/ @@ -400,10 +474,10 @@ class igs_incdec_device : public device_t public: igs_incdec_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - void reset_w(u8 data = 0); - void inc_w(u8 data = 0); - void dec_w(u8 data = 0); - u8 val_r(); + u8 result_r(); + void reset_w(u8 data); + void inc_w(u8 data); + void dec_w(u8 data); protected: virtual void device_start() override; @@ -413,45 +487,43 @@ private: u8 m_val = 0; }; +u8 igs_incdec_device::result_r() +{ + u8 res = (BIT(m_val, 0) << 7) | + (BIT(m_val, 3) << 5) | + (BIT(m_val, 2) << 4) | + (BIT(m_val, 1) << 2) ; + + LOGMASKED(LOG_PROT_INCDEC, "%s: value read, %02x -> %02x\n", machine().describe_context(), m_val, res); + return res; +} + void igs_incdec_device::reset_w(u8 data) { m_val = 0x00; - logerror("%s: reset -> %02x\n", machine().describe_context(), m_val); + LOGMASKED(LOG_PROT_INCDEC, "%s: reset -> %02x\n", machine().describe_context(), m_val); } void igs_incdec_device::inc_w(u8 data) { m_val++; - logerror("%s: inc -> %02x\n", machine().describe_context(), m_val); + LOGMASKED(LOG_PROT_INCDEC, "%s: inc -> %02x\n", machine().describe_context(), m_val); } void igs_incdec_device::dec_w(u8 data) { m_val--; - logerror("%s: dec -> %02x\n", machine().describe_context(), m_val); -} - -u8 igs_incdec_device::val_r() -{ - u8 res = (BIT(m_val, 0) << 7) | - (BIT(m_val, 3) << 5) | - (BIT(m_val, 2) << 4) | - (BIT(m_val, 1) << 2) ; - - logerror("%s: value read, %02x -> %02x\n", machine().describe_context(), m_val, res); - return res; + LOGMASKED(LOG_PROT_INCDEC, "%s: dec -> %02x\n", machine().describe_context(), m_val); } DEFINE_DEVICE_TYPE(IGS_INCDEC, igs_incdec_device, "igs_incdec", "IGS Inc/Dec Protection") -igs_incdec_device::igs_incdec_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) : - device_t(mconfig, IGS_INCDEC, tag, owner, clock) -{ -} +igs_incdec_device::igs_incdec_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, IGS_INCDEC, tag, owner, clock) +{ } void igs_incdec_device::device_start() { - // register for save states save_item(NAME(m_val)); } @@ -460,63 +532,137 @@ void igs_incdec_device::device_reset() m_val = 0; } +/*************************************************************************** + + ---- IGS Inc Protection ---- + +***************************************************************************/ + +class igs_inc_device : public device_t +{ +public: + igs_inc_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); + + u8 result_r(); + void reset_w(u8 data); + void inc_w(u8 data); + +protected: + virtual void device_start() override; + virtual void device_reset() override; + +private: + u8 m_val = 0; +}; + +u8 igs_inc_device::result_r() +{ + const u8 res = (BIT(~m_val, 0) | (BIT(m_val, 1) & BIT(m_val, 2))) << 5; + + LOGMASKED(LOG_PROT_INC, "%s: value read, %02x -> %02x\n", machine().describe_context(), m_val, res); + return res; +} + +void igs_inc_device::reset_w(u8 data) +{ + m_val = 0x00; + LOGMASKED(LOG_PROT_INC, "%s: reset -> %02x\n", machine().describe_context(), m_val); +} + +void igs_inc_device::inc_w(u8 data) +{ + m_val++; + LOGMASKED(LOG_PROT_INC, "%s: inc -> %02x\n", machine().describe_context(), m_val); +} + +DEFINE_DEVICE_TYPE(IGS_INC, igs_inc_device, "igs_inc", "IGS Inc Protection") + +igs_inc_device::igs_inc_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) + : device_t(mconfig, IGS_INC, tag, owner, clock) +{ } + +void igs_inc_device::device_start() +{ + save_item(NAME(m_val)); +} + +void igs_inc_device::device_reset() +{ + m_val = 0; +} + + +namespace { // igs017_state class igs017_state : public driver_device { public: - igs017_state(const machine_config &mconfig, device_type type, const char *tag) : - driver_device(mconfig, type, tag), - m_remap_addr(-1), - m_maincpu(*this, "maincpu"), - m_oki(*this, "oki"), - m_hopperdev(*this, "hopper"), - m_igs025(*this,"igs025"), - m_igs022(*this,"igs022"), - m_screen(*this, "screen"), - m_decrypted_opcodes(*this, "decrypted_opcodes"), - m_igs017_igs031(*this, "igs017_igs031"), - m_igs_bitswap(*this, "igs_bitswap"), - m_igs_incdec(*this, "igs_incdec"), - m_io_coins(*this, "COINS"), - m_io_buttons(*this, "BUTTONS"), - m_io_player1(*this, "PLAYER1"), - m_io_player2(*this, "PLAYER2"), - m_io_hopper(*this, "HOPPER"), - m_io_key(*this, "KEY%u", 0U), - m_io_dsw(*this, "DSW%u", 1U) + igs017_state(const machine_config &mconfig, device_type type, const char *tag) + : driver_device(mconfig, type, tag) + , m_remap_addr(-1) + , m_maincpu(*this, "maincpu") + , m_screen(*this, "screen") + , m_igs017_igs031(*this, "igs017_igs031") + , m_oki(*this, "oki") + , m_igs_mux(*this, "igs_mux") + , m_ppi(*this, "ppi8255") + // Optional shared pointers + , m_decrypted_opcodes(*this, "decrypted_opcodes") + // Optional devices + , m_hopper(*this, "hopper") + , m_igs_bitswap(*this, "igs_bitswap") + , m_igs_string(*this, "igs_string") + , m_igs_incdec(*this, "igs_incdec") + , m_igs_inc(*this, "igs_inc") + , m_igs022(*this,"igs022") + // Optional I/O + , m_io_coins(*this, "COINS") + , m_io_joy(*this, "JOY") + , m_io_key(*this, "KEY%u", 0U) + , m_io_dsw(*this, "DSW%u", 1U) + , m_lamps(*this, "lamp%u", 1U) { } - void mgcs(machine_config &config); - void mgdha(machine_config &config); - void tjsb(machine_config &config); - void lhzb2a(machine_config &config); - void slqz2(machine_config &config); + // Construct + void base_machine_oki(machine_config &config, const XTAL &xtal_oki); + // Z180 + void cpoker2(machine_config &config); + void genius6(machine_config &config); + void happyskl(machine_config &config); void iqblocka(machine_config &config); void iqblockf(machine_config &config); - void genius6(machine_config &config); - void lhzb2(machine_config &config); - void starzan(machine_config &config); void spkrform(machine_config &config); - void sdmg2(machine_config &config); + void starzan(machine_config &config); void tarzan(machine_config &config); + void tjsb(machine_config &config); + // 68000 + void lhzb2(machine_config &config); + void lhzb2a(machine_config &config); + void mgcs(machine_config &config); + void mgdh(machine_config &config); + void mgdha(machine_config &config); + void sdmg2(machine_config &config); + void slqz2(machine_config &config); + // Init + void init_cpoker2(); + void init_happyskl(); void init_iqblocka(); - void init_mgdh(); - void init_slqz2(); void init_lhzb2(); - void init_starzan(); + void init_lhzb2a(); void init_mgcs(); - void init_tjsb(); - void init_spkrform(); + void init_mgdh(); + void init_mgdha(); void init_sdmg2(); + void init_slqz2(); + void init_spkrform(); + void init_starzan(); void init_tarzan(); void init_tarzana(); - void init_lhzb2a(); - void init_mgdha(); - void init_happyskl(); - void init_unkigs(); + void init_tarzanc(); + void init_tjsb(); protected: virtual void machine_start() override; @@ -526,34 +672,35 @@ protected: private: int m_remap_addr; required_device m_maincpu; - - required_device m_oki; - optional_device m_hopperdev; - optional_device m_igs025; // Mj Shuang Long Qiang Zhu 2 - optional_device m_igs022; // Mj Shuang Long Qiang Zhu 2 required_device m_screen; - optional_shared_ptr m_decrypted_opcodes; required_device m_igs017_igs031; - optional_device m_igs_bitswap; - optional_device m_igs_incdec; + required_device m_oki; + required_device m_igs_mux; + required_device m_ppi; + // Optional shared pointers + optional_shared_ptr m_decrypted_opcodes; + + // Optional devices + optional_device m_hopper; + optional_device m_igs_bitswap; + optional_device m_igs_string; + optional_device m_igs_incdec; + optional_device m_igs_inc; + optional_device m_igs022; + + // Optional I/O optional_ioport m_io_coins; - optional_ioport m_io_buttons; - optional_ioport m_io_player1; - optional_ioport m_io_player2; - optional_ioport m_io_hopper; + optional_ioport m_io_joy; optional_ioport_array<5> m_io_key; optional_ioport_array<3> m_io_dsw; - void igs025_to_igs022_callback(void); + output_finder<6> m_lamps; u8 m_input_select; - u8 m_hopper; - u16 m_igs_magic; - u8 m_scramble_data; - u8 m_dsw_select; - u8 m_i8255_portc_mux; + u8 m_scramble_data; + u8 m_igs022_latch; // IGS029 protection (communication) u8 m_igs029_send_data, m_igs029_recv_data; @@ -562,97 +709,194 @@ private: // IGS029 protection (mgcs) u32 m_igs029_mgcs_long; - void input_select_w(u8 data); + void dsw_select_w(u8 data); + u8 dsw_r(); - void iqblocka_keyin_w(u8 data); - void iqblockf_keyout_w(u8 data); - void iqblocka_remap_addr_w(offs_t offset, u8 data); + template + void input_select_w(u8 data) + { + m_input_select = data; - u16 mgcs_palette_bitswap(u16 bgr) const; + if (data & WarnMask) + logerror("%s: warning, unknown bits written in input_select_w = %02x\n", machine().describe_context(), data); + } + + template + void oki_sound_bank_w(u8 data) + { + m_oki->set_rom_bank(BIT(data, Bit)); + + if (data & WarnMask) + logerror("%s: warning, unknown bits written in oki_sound_bank_w = %02x\n", machine().describe_context(), data); + } + + template + void hopper_motor_w(u8 data) + { + m_hopper->motor_w(BIT(data, Bit)); + + if (data & WarnMask) + logerror("%s: warning, unknown bits written in hopper_motor_w = %02x\n", machine().describe_context(), data); + } + + template + void counter_w(u8 data) + { + machine().bookkeeping().coin_counter_w(Counter, BIT(data, Bit)); +// popmessage("COUNTER %d: %02X", Counter, data); + if (data & WarnMask) + logerror("%s: warning, unknown bits written in counter_w = %02x\n", machine().describe_context(), data); + } + + template + void igs022_execute_w(u8 data) + { + if (!BIT(m_igs022_latch, Bit) && BIT(data, Bit)) // 0 -> 1 executes + { + m_igs022->handle_command(); + + const u8 new_scramble_data = (m_scramble_data + 1) & 0x7f; + LOGMASKED(LOG_PROT_IGS022, "%s: IGS022 scrambled data %02x -> %02x\n", machine().describe_context(), m_scramble_data, new_scramble_data); + m_scramble_data = new_scramble_data; + } + + if (data & WarnMask) + logerror("%s: warning, unknown bits written in igs022_execute_w = %02x\n", machine().describe_context(), data); + + m_igs022_latch = data; + } + + // Palette u16 lhzb2a_palette_bitswap(u16 bgr) const; - u16 tjsb_palette_bitswap(u16 bgr) const; + u16 mgcs_palette_bitswap(u16 bgr) const; u16 slqz2_palette_bitswap(u16 bgr) const; + u16 tarzan_palette_bitswap(u16 bgr) const; + u16 tjsb_palette_bitswap(u16 bgr) const; - void magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 magic_r(); + // Game Specific I/O + void incdec_remap_addr_w(offs_t offset, u8 data); - void mgcs_magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 mgcs_magic_r(); + void cpoker2_lamps_sound_w(u8 data); - u8 sdmg2_keys_r(); - void sdmg2_magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 sdmg2_magic_r(); + void happyskl_lamps_sound_w(u8 data); - u8 mgdh_keys_r(); - void mgdha_magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 mgdha_magic_r(); + u8 lhzb2_keys_r(); + void lhzb2_keys_hopper_w(u8 data); + u8 lhzb2_scramble_data_r(); + void lhzb2_igs022_execute_w(u8 data); - void tjsb_output_w(u8 data); - u8 tjsb_input_r(); - u8 spkrform_input_r(); - - void lhzb2a_input_select_w(offs_t offset, u16 data, u16 mem_mask = ~0); + void lhzb2a_keys_hopper_w(offs_t offset, u16 data, u16 mem_mask = ~0); u16 lhzb2a_input_r(offs_t offset); void lhzb2a_remap_addr_w(address_space &space, u16 data); - void lhzb2_magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 lhzb2_magic_r(); + u8 mgcs_keys_joy_r(); + void mgcs_keys_hopper_igs029_w(u8 data); + u8 mgcs_scramble_data_r(); + void mgcs_scramble_data_w(u8 data); + u8 mgcs_igs029_data_r(); + void mgcs_igs029_data_w(u8 data); - void slqz2_magic_w(offs_t offset, u16 data, u16 mem_mask = ~0); - u16 slqz2_magic_r(); - u8 mgcs_keys_r(); + u8 mgdh_keys_r(); + void mgdh_keys_hopper_w(u8 data); + void mgdh_counter_w(u8 data); - u8 i8255_port_c_mux_r(); // starzan, happyskl, unkigs (maybe tarzanc and clones, too) + u8 sdmg2_keys_joy_r(); + void sdmg2_keys_hopper_w(u8 data); - DECLARE_MACHINE_RESET(iqblocka); - DECLARE_MACHINE_RESET(mgcs); + void slqz2_sound_hopper_w(u8 data); + u8 slqz2_scramble_data_r(); + + void starzan_counter_w(u8 data); + void starzan_lamps_sound_w(u8 data); + + u8 tarzan_keys_joy_r(); + void tarzan_counter_w(u8 data); + void tarzan_dsw_sound_w(u8 data); + void tarzan_incdec_remap_addr_w(offs_t offset, u8 data); + + // Machine DECLARE_MACHINE_RESET(lhzb2a); + TIMER_DEVICE_CALLBACK_MEMBER(iqblocka_interrupt); TIMER_DEVICE_CALLBACK_MEMBER(mgcs_interrupt); TIMER_DEVICE_CALLBACK_MEMBER(mgdh_interrupt); + // Decrypt void decrypt_program_rom(int mask, int a7, int a6, int a5, int a4, int a3, int a2, int a1, int a0); - void tjsb_decrypt_sprites(); + + void lhzb2_decrypt_sprites(); + void lhzb2_decrypt_tiles(); void mgcs_decrypt_program_rom(); void mgcs_decrypt_tiles(); void mgcs_flip_sprites(); - void mgcs_patch_rom(); void mgcs_igs029_run(); - void tarzan_decrypt_tiles(); - void tarzan_decrypt_program_rom(); - void tarzana_decrypt_program_rom(); - void starzan_decrypt_program_rom(); - void lhzb2_patch_rom(); - void lhzb2_decrypt_tiles(); - void lhzb2_decrypt_sprites(); - void slqz2_patch_rom(); void slqz2_decrypt_tiles(); void spkrform_decrypt_sprites(); + void starzan_decrypt_program_rom(); + void starzan_decrypt_sprites(); + void tarzan_decrypt_program_rom(); + void tarzan_decrypt_sprites(size_t max_size); + void tarzan_decrypt_tiles(int address_xor); + void tarzana_decrypt_program_rom(); + void tjsb_decrypt_sprites(); + // ROM Patches +// void lhzb2_patch_rom(); +// void mgcs_patch_rom(); +// void slqz2_patch_rom(); + void mgdh_patch_rom(); + void spkrform_patch_rom(); + + // Memory maps void decrypted_opcodes_map(address_map &map); + + void igs_bitswap_mux_map(address_map &map); + void igs_fixed_data_mux_map(address_map &map); + void igs_string_mux_map(address_map &map); + + void cpoker2_io(address_map &map); + void cpoker2_map(address_map &map); + void cpoker2_mux_map(address_map &map); + void happyskl_io(address_map &map); + void happyskl_mux_map(address_map &map); void iqblocka_io(address_map &map); void iqblocka_map(address_map &map); + void iqblocka_mux_map(address_map &map); + void iqblockf_mux_map(address_map &map); void lhzb2_map(address_map &map); + void lhzb2_mux_map(address_map &map); void lhzb2a_map(address_map &map); + void lhzb2a_mux_map(address_map &map); void mgcs_map(address_map &map); - void mgdha_map(address_map &map); + void mgcs_mux_map(address_map &map); + void mgdh_mux_map(address_map &map); + void mgdh_map(address_map &map); + void mgdha_mux_map(address_map &map); void sdmg2_map(address_map &map); + void sdmg2_mux_map(address_map &map); void slqz2_map(address_map &map); + void slqz2_mux_map(address_map &map); void spkrform_io(address_map &map); - void spkrform_map(address_map &map); + void spkrform_mux_map(address_map &map); + void starzan_io(address_map &map); + void starzan_mux_map(address_map &map); + void tarzan_io(address_map &map); + void tarzan_mux_map(address_map &map); void tjsb_io(address_map &map); void tjsb_map(address_map &map); + void tjsb_mux_map(address_map &map); }; void igs017_state::machine_start() { + m_lamps.resolve(); + save_item(NAME(m_remap_addr)); save_item(NAME(m_input_select)); - save_item(NAME(m_hopper)); - save_item(NAME(m_igs_magic)); - save_item(NAME(m_scramble_data)); save_item(NAME(m_dsw_select)); - save_item(NAME(m_i8255_portc_mux)); + save_item(NAME(m_scramble_data)); + save_item(NAME(m_igs022_latch)); + save_item(NAME(m_igs029_send_data)); save_item(NAME(m_igs029_recv_data)); save_item(NAME(m_igs029_send_buf)); @@ -664,7 +908,25 @@ void igs017_state::machine_start() void igs017_state::machine_reset() { + m_input_select = m_dsw_select = 0xff; + m_scramble_data = 0; + m_igs029_send_len = m_igs029_recv_len = 0; + m_igs029_mgcs_long = 0; +} + +void igs017_state::dsw_select_w(u8 data) +{ + m_dsw_select = data; +} + +u8 igs017_state::dsw_r() +{ + u8 ret = 0xff; + if (!BIT(m_dsw_select, 0)) ret &= m_io_dsw[0]->read(); + if (!BIT(m_dsw_select, 1)) ret &= m_io_dsw[1]->read(); + if (!BIT(m_dsw_select, 2)) ret &= m_io_dsw[2]->read(); + return ret; } /*************************************************************************** @@ -686,13 +948,11 @@ u16 igs017_state::mgcs_palette_bitswap(u16 bgr) const u16 igs017_state::lhzb2a_palette_bitswap(u16 bgr) const { -// bgr = ((bgr & 0xff00) >> 8) | ((bgr & 0x00ff) << 8); return bitswap<16>(bgr, 15,9,13,12,11,5,4,8,7,6,0,14,3,2,1,10); } u16 igs017_state::tjsb_palette_bitswap(u16 bgr) const { - // bitswap return bitswap<16>(bgr, 15,12,3,6,10,5,4,2,9,13,8,7,11,1,0,14); } @@ -701,22 +961,32 @@ u16 igs017_state::slqz2_palette_bitswap(u16 bgr) const return bitswap<16>(bgr, 15,14,9,4,11,10,12,3,7,6,5,8,13,2,1,0); } - +u16 igs017_state::tarzan_palette_bitswap(u16 bgr) const +{ + return bitswap<16>(bgr, 15, 0,1,2,3,4, 10,11,12,13,14, 5,6,7,8,9); +} /*************************************************************************** Decryption ***************************************************************************/ +[[maybe_unused]] void save_decrypted_rom(const u8 * const rom, int rom_size) +{ + FILE *f = fopen("igs017_decrypted.bin", "wb"); + fwrite(rom, 1, rom_size, f); + fclose(f); +} + void igs017_state::decrypt_program_rom(int mask, int a7, int a6, int a5, int a4, int a3, int a2, int a1, int a0) { - int length = memregion("maincpu")->bytes(); - u8 *rom = memregion("maincpu")->base(); - std::unique_ptr tmp = std::make_unique(length); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); // decrypt the program ROM // XOR layer - for (int i = 0; i < length; i++) + for (int i = 0; i < rom_size; i++) { if (i & 0x2000) { @@ -746,23 +1016,18 @@ void igs017_state::decrypt_program_rom(int mask, int a7, int a6, int a5, int a4, } } - memcpy(tmp.get(),rom,length); + memcpy(tmp.get(),rom,rom_size); // address lines swap - for (int i = 0; i < length; i++) + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xff) | bitswap<8>(i,a7,a6,a5,a4,a3,a2,a1,a0); rom[i] = tmp[addr]; } -#if 0 - FILE *f = fopen("igs017_decrypted.bin", "wb"); - fwrite(rom, 1, length, f); - fclose(f); -#endif +// save_decrypted_rom(rom, rom_size); } - // iqblocka, iqblockf, genius6 void igs017_state::init_iqblocka() @@ -774,22 +1039,22 @@ void igs017_state::init_iqblocka() void igs017_state::tjsb_decrypt_sprites() { - int length = memregion("igs017_igs031:sprites")->bytes(); - u8 *rom = memregion("igs017_igs031:sprites")->base(); - std::unique_ptr tmp = std::make_unique(length); + const int rom_size = memregion("igs017_igs031:sprites")->bytes(); + u8 * const rom = memregion("igs017_igs031:sprites")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); // address lines swap - memcpy(tmp.get(), rom, length); - for (int i = 0; i < length; i++) + memcpy(tmp.get(), rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xff) | bitswap<8>(i,7,6,5,2,1,4,3,0); rom[i] = tmp[addr]; } // data lines swap - for (int i = 0; i < length; i += 2) + for (int i = 0; i < rom_size; i += 2) { - u16 data = (rom[i+1] << 8) | rom[i+0]; // x-22222-11111-00000 + u16 data = (rom[i+1] << 8) | rom[i+0]; // x-22222-11111-00000 data = bitswap<16>(data, 15, 14,13,12,11,10, 9,1,7,6,5, 4,3,2,8,0); rom[i+0] = data; rom[i+1] = data >> 8; @@ -801,6 +1066,8 @@ void igs017_state::init_tjsb() decrypt_program_rom(0x05, 7, 6, 3, 2, 5, 4, 1, 0); tjsb_decrypt_sprites(); + +// m_igs_string->dump("tjsb_string.key", 0x1d24a, 0x1db4, false); } @@ -808,15 +1075,14 @@ void igs017_state::init_tjsb() void igs017_state::mgcs_decrypt_program_rom() { - u16 *src = (u16 *)memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); - int rom_size = 0x80000; - - for (int i=0; ibytes(); - u8 *rom = memregion("igs017_igs031:tilemaps")->base(); - std::vector tmp(length); + const int rom_size = memregion("igs017_igs031:tilemaps")->bytes(); + u8 * const rom = memregion("igs017_igs031:tilemaps")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); - memcpy(&tmp[0],rom,length); - for (int i = 0; i < length; i++) + memcpy(&tmp[0], rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xffff) | bitswap<16>(i,15,14,13,12,11,10,6,7,8,9,5,4,3,2,1,0); rom[i^1] = bitswap<8>(tmp[addr],0,1,2,3,4,5,6,7); @@ -871,10 +1137,10 @@ void igs017_state::mgcs_decrypt_tiles() void igs017_state::mgcs_flip_sprites() { - int length = memregion("igs017_igs031:sprites")->bytes(); - u8 *rom = memregion("igs017_igs031:sprites")->base(); + const int rom_size = memregion("igs017_igs031:sprites")->bytes(); + u8 * const rom = memregion("igs017_igs031:sprites")->base(); - for (int i = 0; i < length; i+=2) + for (int i = 0; i < rom_size; i+=2) { u16 pixels = (rom[i+1] << 8) | rom[i+0]; @@ -889,50 +1155,54 @@ void igs017_state::mgcs_flip_sprites() } } +#if 0 void igs017_state::mgcs_patch_rom() { -// u16 *rom = (u16 *)memregion("maincpu")->base(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); -// rom[0x20666/2] = 0x601e; // 020666: 671E beq $20686 (rom check) + rom[0x20666/2] = 0x601e; // 020666: 671E beq $20686 (rom check) // IGS029 send command -// rom[0x4dfce/2] = 0x6010; // 04DFCE: 6610 bne $4dfe0 -// rom[0x4e00e/2] = 0x4e75; -// rom[0x4e036/2] = 0x6006; // 04E036: 6306 bls $4e03e + rom[0x4dfce/2] = 0x6010; // 04DFCE: 6610 bne $4dfe0 + rom[0x4e00e/2] = 0x4e75; + rom[0x4e036/2] = 0x6006; // 04E036: 6306 bls $4e03e } +#endif void igs017_state::init_mgcs() { mgcs_decrypt_program_rom(); - mgcs_patch_rom(); +// mgcs_patch_rom(); mgcs_decrypt_tiles(); mgcs_flip_sprites(); + +// m_igs_string->dump("mgcs_string.key", 0x1424, 0x1338, true); } // tarzan, tarzana -void igs017_state::tarzan_decrypt_tiles() +void igs017_state::tarzan_decrypt_tiles(int address_xor) { - int length = memregion("igs017_igs031:tilemaps")->bytes(); - u8 *rom = memregion("igs017_igs031:tilemaps")->base(); - std::vector tmp(length); + const int rom_size = memregion("igs017_igs031:tilemaps")->bytes(); + u8 * const rom = memregion("igs017_igs031:tilemaps")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); - memcpy(&tmp[0],rom,length); - for (int i = 0; i < length; i++) + memcpy(&tmp[0], rom, rom_size); + for (int i = 0; i < rom_size; i++) { - int addr = (i & ~0xffff) | bitswap<16>(i,15,14,13,12,11,7,8,6,10,9,5,4,3,2,1,0); + int addr = (i & ~0xffff) | (bitswap<16>(i,15,14,13,12,11, 7,8,6,10,9, 5,4,3,2,1,0) ^ address_xor); rom[i] = bitswap<8>(tmp[addr],0,1,2,3,4,5,6,7); } } -// decryption should be good void igs017_state::tarzan_decrypt_program_rom() { - u8 *rom = memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -945,7 +1215,7 @@ void igs017_state::tarzan_decrypt_program_rom() m_decrypted_opcodes[i] = x; } - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -958,17 +1228,21 @@ void igs017_state::tarzan_decrypt_program_rom() } } -void igs017_state::init_tarzan() +void igs017_state::init_tarzanc() { tarzan_decrypt_program_rom(); - tarzan_decrypt_tiles(); + tarzan_decrypt_tiles(1); + tarzan_decrypt_sprites(0); + +// m_igs_string->dump("tarzan_string.key", 0xa98a, 0xab01, false); // tarzan / tarzanc (same program rom) } void igs017_state::tarzana_decrypt_program_rom() { - u8 *rom = memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -982,7 +1256,7 @@ void igs017_state::tarzana_decrypt_program_rom() m_decrypted_opcodes[i] = x; } - for (int i = 0; i < 0x40000; i++) // by iq_132 + for (int i = 0; i < rom_size; i++) // by iq_132 { u8 x = rom[i]; @@ -990,16 +1264,29 @@ void igs017_state::tarzana_decrypt_program_rom() if ((i & 0x02180) == 0x00000) x ^= 0x01; if ((i & 0x001a0) != 0x00020) x ^= 0x20; if ((i & 0x00260) != 0x00200) x ^= 0x40; - if ((i & 0x00060) != 0x00000 && (i & 0x00260) != 0x00240) x ^= 0x80; + if ((i & 0x00060) != 0x00000 && (i & 0x00260) != 0x00240) x ^= 0x80; rom[i] = x; } + +// save_decrypted_rom(rom, rom_size); +// save_decrypted_rom(m_decrypted_opcodes, rom_size); +} + +void igs017_state::init_tarzan() +{ + tarzan_decrypt_program_rom(); + tarzan_decrypt_tiles(0); + +// m_igs_string->dump("tarzan_string.key", 0xa98a, 0xab01, false); // tarzan / tarzanc (same program rom) } void igs017_state::init_tarzana() { tarzana_decrypt_program_rom(); -// tarzana_decrypt_tiles(); // to do when dumped + tarzan_decrypt_tiles(0); + +// m_igs_string->dump("tarzana_string.key", 0xaa64, 0xabdb, false); // same data as tarzan / tarzanc } @@ -1007,9 +1294,10 @@ void igs017_state::init_tarzana() void igs017_state::starzan_decrypt_program_rom() { - u8 *rom = memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -1023,7 +1311,7 @@ void igs017_state::starzan_decrypt_program_rom() m_decrypted_opcodes[i] = x; } - for (int i = 0; i < 0x40000; i++) // by iq_132 + for (int i = 0; i < rom_size; i++) // by iq_132 { u8 x = rom[i]; @@ -1043,16 +1331,55 @@ void igs017_state::starzan_decrypt_program_rom() void igs017_state::init_starzan() { starzan_decrypt_program_rom(); - tarzan_decrypt_tiles(); - mgcs_flip_sprites(); // ? + tarzan_decrypt_tiles(1); + starzan_decrypt_sprites(); + +// m_igs_string->dump("starzan_string.key", 0xa86f, 0xa966, false); } +void igs017_state::tarzan_decrypt_sprites(size_t max_size) +{ + mgcs_flip_sprites(); + + const int rom_size = max_size ? max_size : memregion("igs017_igs031:sprites")->bytes(); + u8 *rom = memregion("igs017_igs031:sprites")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); + + // address lines swap + memcpy(tmp.get(), rom, rom_size); + for (int i = 0; i < rom_size; i++) + { + int addr = (i & ~0xffff) | bitswap<16>(i,15,14,13, 9,10,11,12, 5,6,7,8, 4,3,2,1,0); + rom[i] = tmp[addr]; + } +} + +void igs017_state::starzan_decrypt_sprites() +{ + tarzan_decrypt_sprites(0x200000); + + // Overlay rom: + + const int rom_size = 0x80000; + u8 *rom = memregion("igs017_igs031:sprites")->base() + 0x200000; + std::unique_ptr tmp = std::make_unique(rom_size); + + // address lines swap + memcpy(tmp.get(), rom, rom_size); + for (int i = 0; i < rom_size; i++) + { + int addr = (i & ~0xffff) | bitswap<16>(i,15,14,13,12,11,10,9, 6,5, 8,7, 1,2,3,4, 0); + rom[i] = tmp[addr]; + } +} + void igs017_state::init_happyskl() { - u8 *rom = memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -1066,7 +1393,7 @@ void igs017_state::init_happyskl() m_decrypted_opcodes[i] = x; } - for (int i = 0; i < 0x40000; i++) // adapted from starzan, seems ok + for (int i = 0; i < rom_size; i++) // adapted from starzan { u8 x = rom[i]; @@ -1082,15 +1409,17 @@ void igs017_state::init_happyskl() rom[i] = x; } - tarzan_decrypt_tiles(); // enough for chars + tarzan_decrypt_tiles(1); + starzan_decrypt_sprites(); } -void igs017_state::init_unkigs() +void igs017_state::init_cpoker2() { - u8 *rom = memregion("maincpu")->base(); + const int rom_size = memregion("maincpu")->bytes(); + u8 * const rom = memregion("maincpu")->base(); - for (int i = 0; i < 0x40000; i++) + for (int i = 0; i < rom_size; i++) { u8 x = rom[i]; @@ -1101,12 +1430,12 @@ void igs017_state::init_unkigs() if ((i & 0x00020) == 0x00020) x ^= 0x80; if ((i & 0x00260) == 0x00240) x ^= 0x80; - // this hasn't got split data / opcodes encryption like happyskl, but let's keep the same machine_config for easier testing - m_decrypted_opcodes[i] = x; + // this hasn't got split data / opcodes encryption rom[i] = x; } - tarzan_decrypt_tiles(); // enough for chars + tarzan_decrypt_tiles(1); + tarzan_decrypt_sprites(0); } @@ -1114,13 +1443,14 @@ void igs017_state::init_unkigs() void igs017_state::init_sdmg2() { - u16 *src = (u16 *)memregion("maincpu")->base(); - int rom_size = 0x80000; + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); + for (int i = 0; i < rom_size / 2; i++) { - u16 x = src[i]; + u16 x = rom[i]; - /* bit 0 xor layer */ + // bit 0 xor layer if (i & 0x20/2) { @@ -1138,7 +1468,7 @@ void igs017_state::init_sdmg2() } } - /* bit 9 xor layer */ + // bit 9 xor layer if (i & 0x20000/2) { x ^= 0x0200; @@ -1151,13 +1481,13 @@ void igs017_state::init_sdmg2() } } - /* bit 12 xor layer */ + // bit 12 xor layer if (i & 0x20000/2) { x ^= 0x1000; } - src[i] = x; + rom[i] = x; } } @@ -1166,11 +1496,12 @@ void igs017_state::init_sdmg2() void igs017_state::init_mgdha() { - u16 *src = (u16 *)memregion("maincpu")->base(); - int rom_size = 0x80000; + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); + for (int i = 0; i < rom_size / 2; i++) { - u16 x = src[i]; + u16 x = rom[i]; if ((i & 0x20/2) && (i & 0x02/2)) { @@ -1189,44 +1520,53 @@ void igs017_state::init_mgdha() if ((i & 0x1000/2) || ((i & 0x4000/2) && (i & 0x40/2) && (i & 0x80/2)) || ((i & 0x2000/2) && (i & 0x400/2))) x ^= 0x0800; - src[i] = x; + rom[i] = x; } mgcs_flip_sprites(); + +// m_igs_string->dump("mgdh_string.key", 0x7b214, 0x7b128, true); // mgdh, mgdha (0x7c5ba, ???) +} + +void igs017_state::mgdh_patch_rom() +{ + u16 * const rom = (u16 *)memregion("maincpu")->base(); + + // game id check + rom[0x4ad50/2] = 0x4e71; } void igs017_state::init_mgdh() { init_mgdha(); - u16 *rom = (u16 *)memregion("maincpu")->base(); - - // additional protection - rom[0x4ad50/2] = 0x4e71; + mgdh_patch_rom(); } // lhzb2 +#if 0 void igs017_state::lhzb2_patch_rom() { - u16 *rom = (u16 *)memregion("maincpu")->base(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); // Prot. checks: - rom[0x14786/2] = 0x6044; // 014786: 6744 beq $147cc + rom[0x14786/2] = 0x6044; // 014786: 6744 beq $147cc // ROM check: - rom[0x0b48a/2] = 0x604e; // 00B48A: 674E beq $b4da + rom[0x0b48a/2] = 0x604e; // 00B48A: 674E beq $b4da } +#endif void igs017_state::lhzb2_decrypt_tiles() { - int length = memregion("igs017_igs031:tilemaps")->bytes(); - u8 *rom = memregion("igs017_igs031:tilemaps")->base(); - std::vector tmp(length); + const int rom_size = memregion("igs017_igs031:tilemaps")->bytes(); + u8 * const rom = memregion("igs017_igs031:tilemaps")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); - memcpy(&tmp[0], rom, length); - for (int i = 0; i < length; i++) + memcpy(&tmp[0], rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xffffff) | bitswap<24>(i,23,22,21,20,19,18,17,1,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,0); rom[i] = tmp[addr]; @@ -1235,42 +1575,38 @@ void igs017_state::lhzb2_decrypt_tiles() void igs017_state::lhzb2_decrypt_sprites() { - int length = memregion("igs017_igs031:sprites")->bytes(); - u8 *rom = memregion("igs017_igs031:sprites")->base(); - std::unique_ptr tmp = std::make_unique(length); + const int rom_size = memregion("igs017_igs031:sprites")->bytes(); + u8 * const rom = memregion("igs017_igs031:sprites")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); // address lines swap - memcpy(tmp.get(), rom, length); - for (int i = 0; i < length; i++) + memcpy(tmp.get(), rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xffff) | bitswap<16>(i,15,14,13,6,7,10,9,8,11,12,5,4,3,2,1,0); rom[i] = tmp[addr]; } // data lines swap - for (int i = 0; i < length; i+=2) + for (int i = 0; i < rom_size; i+=2) { - u16 data = (rom[i+1] << 8) | rom[i+0]; // x-22222-11111-00000 + u16 data = (rom[i+1] << 8) | rom[i+0]; // x-22222-11111-00000 data = bitswap<16>(data, 15, 7,6,5,4,3, 2,1,0,14,13, 12,11,10,9,8); rom[i+0] = data; rom[i+1] = data >> 8; } } -void igs017_state::igs025_to_igs022_callback(void) -{ - m_igs022->IGS022_handle_command(); -} - void igs017_state::init_lhzb2() { - u16 *src = (u16 *) (memregion("maincpu")->base()); - int rom_size = 0x80000; + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); + for (int i = 0; i < rom_size / 2; i++) { - u16 x = src[i]; + u16 x = rom[i]; - /* bit 0 xor layer */ + // bit 0 xor layer if (i & 0x20/2) { if (i & 0x02/2) @@ -1287,7 +1623,7 @@ void igs017_state::init_lhzb2() } } - /* bit 13 xor layer */ + // bit 13 xor layer if (!(i & 0x1000/2)) { @@ -1341,18 +1677,15 @@ void igs017_state::init_lhzb2() } } - src[i] = x; + rom[i] = x; } lhzb2_decrypt_tiles(); lhzb2_decrypt_sprites(); - lhzb2_patch_rom(); - // install and configure protection device(s) -// m_maincpu->space(AS_PROGRAM).install_readwrite_handler(0xda5610, 0xda5613, read16_delegate(*m_igs025, FUNC(igs025_device::killbld_igs025_prot_r)), write16_delegate(*m_igs025, FUNC(igs025_device::killbld_igs025_prot_w))); -// m_igs025->m_kb_source_data = dw3_source_data; -// m_igs025->m_kb_source_data_offset = 0; -// m_igs025->m_kb_game_id = 0x00060000; +// lhzb2_patch_rom(); + +// m_igs_string->dump("lhzb2_string.key", 0x7b214, 0x7b128, true); } @@ -1360,13 +1693,14 @@ void igs017_state::init_lhzb2() void igs017_state::init_lhzb2a() { - u16 *src = (u16 *) (memregion("maincpu")->base()); - int rom_size = 0x80000; + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); + for (int i = 0; i < rom_size / 2; i++) { - u16 x = src[i]; + u16 x = rom[i]; - /* bit 0 xor layer */ + // bit 0 xor layer if (i & 0x20/2) { if (i & 0x02/2) @@ -1383,7 +1717,7 @@ void igs017_state::init_lhzb2a() } } - /* bit 5 xor layer */ + // bit 5 xor layer if (i & 0x4000/2) { @@ -1409,35 +1743,39 @@ void igs017_state::init_lhzb2a() } } - src[i] = x; + rom[i] = x; } lhzb2_decrypt_tiles(); lhzb2_decrypt_sprites(); + +// m_igs_string->dump("lhzb2a_string.key", 0x6e11c, 0x6e030, true); // same data as lhzb2 } // slqz2 +#if 0 void igs017_state::slqz2_patch_rom() { - u16 *rom = (u16 *)memregion("maincpu")->base(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); // Prot. checks: - rom[0x1489c/2] = 0x6044; // 01489C: 6744 beq $148e2 + rom[0x1489c/2] = 0x6044; // 01489C: 6744 beq $148e2 // ROM check: - rom[0x0b77a/2] = 0x604e; // 00B77A: 674E beq $b7ca + rom[0x0b77a/2] = 0x604e; // 00B77A: 674E beq $b7ca } +#endif void igs017_state::slqz2_decrypt_tiles() { - int length = memregion("igs017_igs031:tilemaps")->bytes(); - u8 *rom = memregion("igs017_igs031:tilemaps")->base(); - std::vector tmp(length); + const int rom_size = memregion("igs017_igs031:tilemaps")->bytes(); + u8 * const rom = memregion("igs017_igs031:tilemaps")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); - memcpy(&tmp[0],rom,length); - for (int i = 0; i < length; i++) + memcpy(&tmp[0], rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr = (i & ~0xff) | bitswap<8>(i,7,4,5,6,3,2,1,0); rom[i] = tmp[addr]; @@ -1446,13 +1784,14 @@ void igs017_state::slqz2_decrypt_tiles() void igs017_state::init_slqz2() { - u16 *src = (u16 *) (memregion("maincpu")->base()); - int rom_size = 0x80000; + const int rom_size = memregion("maincpu")->bytes(); + u16 * const rom = (u16 *)memregion("maincpu")->base(); + for (int i = 0; i < rom_size / 2; i++) { - u16 x = src[i]; + u16 x = rom[i]; - /* bit 0 xor layer */ + // bit 0 xor layer if (i & 0x20/2) { @@ -1470,7 +1809,7 @@ void igs017_state::init_slqz2() } } - /* bit 14 xor layer */ + // bit 14 xor layer if (i & 0x1000/2) { @@ -1514,18 +1853,15 @@ void igs017_state::init_slqz2() } } - src[i] = x; + rom[i] = x; } slqz2_decrypt_tiles(); lhzb2_decrypt_sprites(); - slqz2_patch_rom(); - // install and configure protection device(s) -// m_maincpu->space(AS_PROGRAM).install_readwrite_handler(0xda5610, 0xda5613, read16_delegate(*m_igs025, FUNC(igs025_device::killbld_igs025_prot_r)), write16_delegate(*m_igs025, FUNC(igs025_device::killbld_igs025_prot_w))); -// m_igs025->m_kb_source_data = dw3_source_data; -// m_igs025->m_kb_source_data_offset = 0; -// m_igs025->m_kb_game_id = 0x00060000; +// slqz2_patch_rom(); + +// m_igs_string->dump("slqz2_string.key", 0x7b214, 0x7b128, true); } @@ -1533,13 +1869,13 @@ void igs017_state::init_slqz2() void igs017_state::spkrform_decrypt_sprites() { - int length = memregion("igs017_igs031:sprites")->bytes(); - u8 *rom = memregion("igs017_igs031:sprites")->base(); - std::unique_ptr tmp = std::make_unique(length); + const int rom_size = memregion("igs017_igs031:sprites")->bytes(); + u8 * const rom = memregion("igs017_igs031:sprites")->base(); + std::unique_ptr tmp = std::make_unique(rom_size); // address lines swap - memcpy(tmp.get(), rom, length); - for (int i = 0; i < length; i++) + memcpy(tmp.get(), rom, rom_size); + for (int i = 0; i < rom_size; i++) { int addr; if (i & 0x80000) @@ -1551,18 +1887,61 @@ void igs017_state::spkrform_decrypt_sprites() } } +void igs017_state::spkrform_patch_rom() +{ + u8 * const rom = memregion("maincpu")->base(); + + rom[0x32ea9] = 0; // enable poker ($e9be = 0) + rom[0x32ef9] = 0; // start with poker ($e9bf = 0) +} + void igs017_state::init_spkrform() { decrypt_program_rom(0x14, 7, 6, 5, 4, 3, 0, 1, 2); spkrform_decrypt_sprites(); -} + spkrform_patch_rom(); + +// m_igs_string->dump("spkrform_string.key", 0x9dec, 0x9d00, false); +} /*************************************************************************** Memory Maps ***************************************************************************/ +// Common MUX maps + +// 0x03 r, 0x40 - 0x47 w, 0x48 w, 0x50 w, 0x80 - 0x87 w, 0xa0 w +void igs017_state::igs_bitswap_mux_map(address_map &map) +{ + map(0x03, 0x03).r(m_igs_bitswap, FUNC(igs_bitswap_device::result_r)); + map(0x40, 0x40).w(m_igs_bitswap, FUNC(igs_bitswap_device::word_w)); + map(0x41, 0x47).nopw(); + map(0x48, 0x48).w(m_igs_bitswap, FUNC(igs_bitswap_device::mode_f_w)); + map(0x50, 0x50).w(m_igs_bitswap, FUNC(igs_bitswap_device::mode_3_w)); + map(0x80, 0x87).w(m_igs_bitswap, FUNC(igs_bitswap_device::do_bitswap_w)); + map(0xa0, 0xa0).w(m_igs_bitswap, FUNC(igs_bitswap_device::reset_w)); +} + +// 0x05 r, 0x20 - 0x27 w, 0x40 r +void igs017_state::igs_string_mux_map(address_map &map) +{ + map(0x05, 0x05).r(m_igs_string, FUNC(igs_string_device::result_r)); + map(0x20, 0x27).w(m_igs_string, FUNC(igs_string_device::do_bitswap_w)); + map(0x40, 0x40).r(m_igs_string, FUNC(igs_string_device::advance_string_offs_r)); +} + +// 0x20 - 0x34: read fixed data +void igs017_state::igs_fixed_data_mux_map(address_map &map) +{ + map(0x20, 0x34).rom().region("igs_fixed_data", 0); + map(0x23, 0x23).unmapr(); + map(0x29, 0x29).unmapr(); + map(0x2f, 0x2f).unmapr(); +} + + // iqblocka, iqblockf, genius6 void igs017_state::iqblocka_map(address_map &map) @@ -1575,31 +1954,10 @@ void igs017_state::iqblocka_map(address_map &map) void igs017_state::decrypted_opcodes_map(address_map &map) { - map(0x00000, 0x3ffff).rom().share("decrypted_opcodes"); + map(0x00000, 0x3ffff).readonly().share(m_decrypted_opcodes); } -void igs017_state::input_select_w(u8 data) -{ - m_input_select = data; -} - -void igs017_state::iqblocka_keyin_w(u8 data) -{ - machine().bookkeeping().coin_counter_w(0, data & 0x80); // key in (in gambling mode) -// popmessage("PORT0 %02X", data); - if (data & ~0x80) - logerror("%s: warning, unknown bits written in keyin_w = %02x\n", machine().describe_context(), data); -} - -void igs017_state::iqblockf_keyout_w(u8 data) -{ - machine().bookkeeping().coin_counter_w(1, data & 0x80); // key out (in gambling mode, only iqblockf/genius6) -// popmessage("PORT1 %02X", data); - if (data & ~0x80) - logerror("%s: warning, unknown bits written in keyout_w = %02x\n", machine().describe_context(), data); -} - -void igs017_state::iqblocka_remap_addr_w(offs_t offset, u8 data) +void igs017_state::incdec_remap_addr_w(offs_t offset, u8 data) { if (offset == 0) { @@ -1612,7 +1970,7 @@ void igs017_state::iqblocka_remap_addr_w(offs_t offset, u8 data) prg_space.unmap_write(m_remap_addr + 0x3, m_remap_addr + 0x3); prg_space.unmap_read (m_remap_addr + 0x5, m_remap_addr + 0x5); - logerror("%s: incdec protection unmapped from %04x\n", machine().describe_context(), m_remap_addr); + LOGMASKED(LOG_PROT_REMAP, "%s: incdec protection unmapped from %04x\n", machine().describe_context(), m_remap_addr); } m_remap_addr = (m_remap_addr & 0xff00) | data; @@ -1626,22 +1984,21 @@ void igs017_state::iqblocka_remap_addr_w(offs_t offset, u8 data) prg_space.install_write_handler(m_remap_addr + 0x0, m_remap_addr + 0x0, write8smo_delegate(*m_igs_incdec, FUNC(igs_incdec_device::reset_w))); prg_space.install_write_handler(m_remap_addr + 0x1, m_remap_addr + 0x1, write8smo_delegate(*m_igs_incdec, FUNC(igs_incdec_device::dec_w))); prg_space.install_write_handler(m_remap_addr + 0x3, m_remap_addr + 0x3, write8smo_delegate(*m_igs_incdec, FUNC(igs_incdec_device::inc_w))); - prg_space.install_read_handler (m_remap_addr + 0x5, m_remap_addr + 0x5, read8smo_delegate (*m_igs_incdec, FUNC(igs_incdec_device::val_r))); + prg_space.install_read_handler (m_remap_addr + 0x5, m_remap_addr + 0x5, read8smo_delegate (*m_igs_incdec, FUNC(igs_incdec_device::result_r))); - logerror("%s: incdec protection remapped at %04x\n", machine().describe_context(), m_remap_addr); + LOGMASKED(LOG_PROT_REMAP, "%s: incdec protection remapped at %04x\n", machine().describe_context(), m_remap_addr); } } void igs017_state::iqblocka_io(address_map &map) { map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); - map(0x0000, 0x003f).ram(); // internal regs - map(0x2010, 0x2011).w(FUNC(igs017_state::iqblocka_remap_addr_w)); + map(0x2010, 0x2011).w(FUNC(igs017_state::incdec_remap_addr_w)); - map(0x8000, 0x8000).w ("igs_bitswap", FUNC(igs_bitswap_device::address_w)); - map(0x8001, 0x8001).rw("igs_bitswap", FUNC(igs_bitswap_device::data_r), FUNC(igs_bitswap_device::data_w)); + map(0x8000, 0x8000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0x8001, 0x8001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); map(0x9000, 0x9000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); @@ -1650,6 +2007,230 @@ void igs017_state::iqblocka_io(address_map &map) map(0xb000, 0xb001).w("ymsnd", FUNC(ym2413_device::write)); } +void igs017_state::iqblocka_mux_map(address_map &map) +{ + map(0x00, 0x00).portr("PLAYER1").w(NAME((&igs017_state::counter_w<7, 0x7f, 0>))); // coin in + map(0x01, 0x01).portr("PLAYER2"); + map(0x02, 0x02).portr("COINS"); + + igs_bitswap_mux_map(map); // 0x03 r, 0x40 - 0x47 w, 0x48 w, 0x50 w, 0x80 - 0x87 w, 0xa0 w + + igs_fixed_data_mux_map(map); // 0x20 - 0x34: read fixed data +} + +void igs017_state::iqblockf_mux_map(address_map &map) +{ + iqblocka_mux_map(map); + + map(0x01, 0x01).w(NAME((&igs017_state::counter_w<7, 0x7f, 1>))); // coin out (in gambling mode, only iqblockf/genius6) +} + +// starzan + +void igs017_state::starzan_io(address_map &map) +{ + map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); + map(0x0000, 0x003f).ram(); // internal regs + + map(0x2010, 0x2011).w(FUNC(igs017_state::incdec_remap_addr_w)); + + map(0x8000, 0x8000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0x8001, 0x8001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); + + map(0x9000, 0x9000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); +} + +// cpoker2, happyksl, starzan +void igs017_state::starzan_counter_w(u8 data) +{ + // BIT(data, 0) // always on in cpoker2/happyskl? + m_hopper->motor_w( BIT(data, 1)); // hopper + // BIT(data, 2) // unused? + machine().bookkeeping().coin_counter_w(0, BIT(data, 3)); // key out + machine().bookkeeping().coin_counter_w(1, BIT(data, 4)); // payout + machine().bookkeeping().coin_counter_w(2, BIT(data, 5)); // coin C + machine().bookkeeping().coin_counter_w(3, BIT(data, 6)); // key in + machine().bookkeeping().coin_counter_w(4, BIT(data, 7)); // coin A +// popmessage("COUNTER %02X", data); + if (BIT(data, 2)) + logerror("%s: warning, unknown bits written in counter_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::starzan_lamps_sound_w(u8 data) +{ + m_lamps[0] = BIT(data, 2); // stop 1 + m_lamps[1] = BIT(data, 0); // stop 2 + m_lamps[2] = BIT(data, 4); // stop 3 + m_lamps[3] = BIT(data, 1); // stop 4 + m_lamps[4] = BIT(data, 3); // bet/stop + m_lamps[5] = BIT(data, 5); // start +// BIT(data, 6); // unused? + m_oki->set_rom_bank(BIT(data, 7)); + +// popmessage("LAMPS/SOUND %02X", data); + + if (BIT(data, 6)) + logerror("%s: warning, unknown bits written in lamps_sound_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::starzan_mux_map(address_map &map) +{ + map(0x00, 0x00).w(FUNC(igs017_state::starzan_counter_w)); + map(0x01, 0x01).portr("PLAYER2"); + map(0x02, 0x02).w(FUNC(igs017_state::starzan_lamps_sound_w)); + map(0x03, 0x03).w(FUNC(igs017_state::dsw_select_w)); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r +} + + +// happyksl + +void igs017_state::happyskl_io(address_map &map) +{ + map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); + map(0x0000, 0x003f).ram(); // internal regs + + map(0x8000, 0x8000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0x8001, 0x8001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); + + map(0x9000, 0x9000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); +} + +void igs017_state::happyskl_lamps_sound_w(u8 data) +{ + m_lamps[0] = BIT(data, 4); // hold 1 + m_lamps[1] = BIT(data, 0); // hold 2 + m_lamps[2] = BIT(data, 1); // hold 3 + m_lamps[3] = BIT(data, 2); // hold 4 + m_lamps[4] = BIT(data, 3); // hold 5 + m_lamps[5] = BIT(data, 5); // start +// BIT(data, 6); // unused? + m_oki->set_rom_bank(BIT(data, 7)); + +// popmessage("LAMPS/SOUND %02X", data); + + if (BIT(data, 6)) + logerror("%s: warning, unknown bits written in lamps_sound_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::happyskl_mux_map(address_map &map) +{ + map(0x00, 0x00).w(FUNC(igs017_state::starzan_counter_w)); + map(0x01, 0x01).portr("PLAYER2"); + map(0x02, 0x02).w(FUNC(igs017_state::happyskl_lamps_sound_w)); + map(0x03, 0x03).w(FUNC(igs017_state::dsw_select_w)); +} + + +// cpoker2 + +void igs017_state::cpoker2_map(address_map &map) +{ + iqblocka_map(map); + + map(0x0a400, 0x0a400).w(m_igs_inc, FUNC(igs_inc_device::inc_w)); + map(0x0a420, 0x0a420).w(m_igs_inc, FUNC(igs_inc_device::reset_w)); + map(0x0a460, 0x0a460).r(m_igs_inc, FUNC(igs_inc_device::result_r)); +} + +void igs017_state::cpoker2_io(address_map &map) +{ + map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); + map(0x0000, 0x003f).ram(); // internal regs + + map(0x2010, 0x2011).w(FUNC(igs017_state::incdec_remap_addr_w)); + + map(0x8000, 0x8000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0x8001, 0x8001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); + + map(0x9000, 0x9000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); +} + +void igs017_state::cpoker2_lamps_sound_w(u8 data) +{ + m_lamps[0] = BIT(data, 0); // hold 1 + m_lamps[1] = BIT(data, 1); // hold 2 + m_lamps[2] = BIT(data, 4); // hold 3 + m_lamps[3] = BIT(data, 2); // hold 4 + m_lamps[4] = BIT(data, 3); // hold 5 + m_lamps[5] = BIT(data, 5); // start +// BIT(data, 6); // unused? + m_oki->set_rom_bank(BIT(data, 7)); + +// popmessage("LAMPS/SOUND %02X", data); + + if (BIT(data, 6)) + logerror("%s: warning, unknown bits written in lamps_sound_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::cpoker2_mux_map(address_map &map) +{ + map(0x00, 0x00).w(FUNC(igs017_state::starzan_counter_w)); + map(0x01, 0x01).portr("PLAYER2"); + map(0x02, 0x02).w(FUNC(igs017_state::cpoker2_lamps_sound_w)); + map(0x03, 0x03).w(FUNC(igs017_state::dsw_select_w)); +} + + +// tarzan + +void igs017_state::tarzan_incdec_remap_addr_w(offs_t offset, u8 data) +{ + incdec_remap_addr_w(offset, data ^ ((offset == 1) ? 0x40 : 0)); +} + +void igs017_state::tarzan_io(address_map &map) +{ + starzan_io(map); + + map(0x2010, 0x2011).w(FUNC(igs017_state::tarzan_incdec_remap_addr_w)); +} + +u8 igs017_state::tarzan_keys_joy_r() +{ + if (BIT(m_input_select, 3, 5) == 0x1f) return m_io_joy->read(); // f8 (joystick mode) + + u8 ret = 0xff; + if (!BIT(m_input_select, 3)) ret &= m_io_key[0]->read(); // f0 (keyboard mode) + if (!BIT(m_input_select, 4)) ret &= m_io_key[1]->read(); // e8 "" + if (!BIT(m_input_select, 5)) ret &= m_io_key[2]->read(); // d8 "" + if (!BIT(m_input_select, 6)) ret &= m_io_key[3]->read(); // b8 "" + if (!BIT(m_input_select, 7)) ret &= m_io_key[4]->read(); // 78 "" (unused) + return ret; +} + +void igs017_state::tarzan_counter_w(u8 data) +{ + m_hopper->motor_w( BIT(data, 1)); // hopper + machine().bookkeeping().coin_counter_w(0, BIT(data, 2)); // key out + machine().bookkeeping().coin_counter_w(1, BIT(data, 3)); // key in +// popmessage("COUNTER %02X", data); + if (data & ~0x0c) + logerror("%s: warning, unknown bits written in counter_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::tarzan_dsw_sound_w(u8 data) +{ + // bits 0,1,2: DSW select + // bit 7: Sound bank + m_dsw_select = data; + m_oki->set_rom_bank(BIT(data, 7)); +// popmessage("DSW %02X", data); + if (data & ~0x87) + logerror("%s: warning, unknown bits written in dsw_sound_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::tarzan_mux_map(address_map &map) +{ + map(0x00, 0x00).w(FUNC(igs017_state::input_select_w<0x07>)); + map(0x01, 0x01).w(FUNC(igs017_state::tarzan_counter_w)); + map(0x02, 0x02).r(FUNC(igs017_state::dsw_r)); + map(0x03, 0x03).w(FUNC(igs017_state::tarzan_dsw_sound_w)); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r +} + // mgcs @@ -1657,23 +2238,23 @@ void igs017_state::iqblocka_io(address_map &map) // Sound banking and DSW are accessed through it. It also performs some game specific calculations. void igs017_state::mgcs_igs029_run() { - logerror("%s: running igs029 command ", machine().describe_context()); + LOGMASKED(LOG_PROT_IGS029, "%s: running igs029 command ", machine().describe_context()); for (int i = 0; i < m_igs029_send_len; i++) - logerror("%02x ", m_igs029_send_buf[i]); + LOGMASKED(LOG_PROT_IGS029, "%02x ", m_igs029_send_buf[i]); - if (m_igs029_send_buf[0] == 0x05 && m_igs029_send_buf[1] == 0x5a) + if (m_igs029_send_buf[0] == 0x05 && m_igs029_send_buf[1] == 0x5a) // 'Z' { u8 data = m_igs029_send_buf[2]; u8 port = m_igs029_send_buf[3]; - logerror("PORT %02x = %02x\n", port, data); + LOGMASKED(LOG_PROT_IGS029, "PORT %02x = %02x\n", port, data); switch (port) { case 0x01: - m_oki->set_rom_bank((data >> 4) & 1); - machine().bookkeeping().coin_counter_w(0, (~data) & 0x20); // coin in - machine().bookkeeping().coin_counter_w(1, (~data) & 0x40); // coin out + m_oki->set_rom_bank( BIT(data, 4)); // oki + machine().bookkeeping().coin_counter_w(0, !BIT(data, 5)); // coin in + machine().bookkeeping().coin_counter_w(1, !BIT(data, 6)); // coin out // popmessage("PORT1 %02X", data); @@ -1699,9 +2280,9 @@ void igs017_state::mgcs_igs029_run() m_igs029_recv_len = 0; m_igs029_recv_buf[m_igs029_recv_len++] = 0x01; } - else if (m_igs029_send_buf[0] == 0x03 && m_igs029_send_buf[1] == 0x55) + else if (m_igs029_send_buf[0] == 0x03 && m_igs029_send_buf[1] == 0x55) // 'U' { - logerror("MIN BET?\n"); + LOGMASKED(LOG_PROT_IGS029, "MIN BET?\n"); // No inputs. Returns 1 long @@ -1714,26 +2295,22 @@ void igs017_state::mgcs_igs029_run() m_igs029_recv_buf[m_igs029_recv_len++] = min_bets[ (~m_io_dsw[1]->read()) & 3 ]; m_igs029_recv_buf[m_igs029_recv_len++] = 0x05; } - else if (m_igs029_send_buf[0] == 0x03 && m_igs029_send_buf[1] == 0x39) + else if (m_igs029_send_buf[0] == 0x03 && m_igs029_send_buf[1] == 0x39) // '9' { - logerror("READ DSW\n"); + LOGMASKED(LOG_PROT_IGS029, "READ DSW\n"); - u8 ret; - if (~m_dsw_select & 0x01) ret = m_io_dsw[0]->read(); - else if (~m_dsw_select & 0x02) ret = m_io_dsw[1]->read(); - else - { - logerror("%s: warning, reading dsw with dsw_select = %02x\n", machine().describe_context(), m_dsw_select); - ret = 0xff; - } + u8 ret = 0xff; + if (!BIT(m_dsw_select, 0)) ret &= m_io_dsw[0]->read(); + else if (!BIT(m_dsw_select, 1)) ret &= m_io_dsw[1]->read(); + else logerror("%s: warning, reading dsw with dsw_select = %02x\n", machine().describe_context(), m_dsw_select); m_igs029_recv_len = 0; m_igs029_recv_buf[m_igs029_recv_len++] = ret; m_igs029_recv_buf[m_igs029_recv_len++] = 0x02; } - else if (m_igs029_send_buf[0] == 0x07 && m_igs029_send_buf[1] == 0x2c) + else if (m_igs029_send_buf[0] == 0x07 && m_igs029_send_buf[1] == 0x2c) // ',' { - logerror("?? (2C)\n"); // ?? + LOGMASKED(LOG_PROT_IGS029, "?? (2C)\n"); // ?? // 4 inputs. Returns 1 long @@ -1743,12 +2320,12 @@ void igs017_state::mgcs_igs029_run() m_igs029_recv_buf[m_igs029_recv_len++] = 0x00; m_igs029_recv_buf[m_igs029_recv_len++] = 0x00; m_igs029_recv_buf[m_igs029_recv_len++] = 0x00; - m_igs029_recv_buf[m_igs029_recv_len++] = 0x01; // ?? + m_igs029_recv_buf[m_igs029_recv_len++] = 0x01; // ?? m_igs029_recv_buf[m_igs029_recv_len++] = 0x05; } else if (m_igs029_send_buf[0] == 0x07 && m_igs029_send_buf[1] == 0x15) { - logerror("SET LONG\n"); + LOGMASKED(LOG_PROT_IGS029, "SET LONG\n"); m_igs029_mgcs_long = (m_igs029_send_buf[2] << 24) | (m_igs029_send_buf[3] << 16) | (m_igs029_send_buf[4] << 8) | m_igs029_send_buf[5]; @@ -1757,7 +2334,7 @@ void igs017_state::mgcs_igs029_run() } else if (m_igs029_send_buf[0] == 0x03 && m_igs029_send_buf[1] == 0x04) { - logerror("GET LONG\n"); + LOGMASKED(LOG_PROT_IGS029, "GET LONG\n"); m_igs029_recv_len = 0; m_igs029_recv_buf[m_igs029_recv_len++] = (m_igs029_mgcs_long >> 0) & 0xff; @@ -1768,7 +2345,7 @@ void igs017_state::mgcs_igs029_run() } else { - logerror("UNKNOWN\n"); + LOGMASKED(LOG_PROT_IGS029, "UNKNOWN\n"); m_igs029_recv_len = 0; m_igs029_recv_buf[m_igs029_recv_len++] = 0x01; @@ -1777,394 +2354,234 @@ void igs017_state::mgcs_igs029_run() m_igs029_send_len = 0; } -void igs017_state::magic_w(offs_t offset, u16 data, u16 mem_mask) +void igs017_state::mgcs_keys_hopper_igs029_w(u8 data) { - COMBINE_DATA(&m_igs_magic); -} + // 7654 3--- Keys + // ---- -2-- IRQ on IGS029 + // ---- --1- + // ---- ---0 Hopper Motor + const bool igs029_irq = !BIT(m_input_select, 2) && BIT(data, 2); // 0 -> 1 + m_input_select = data; + m_hopper->motor_w(BIT(data, 0)); -u16 igs017_state::magic_r() -{ - return m_igs_magic; -} - -void igs017_state::mgcs_magic_w(offs_t offset, u16 data, u16 mem_mask) -{ - switch (m_igs_magic) + if (igs029_irq) { - case 0x00: - if (ACCESSING_BITS_0_7) - { - bool igs029_irq = !(m_input_select & 0x04) && (data & 0x04); // 0->1 - - // 7654 3--- Keys - // ---- -2-- IRQ on IGS029 - // ---- --1- - // ---- ---0 Hopper Motor - m_input_select = data & 0xff; - - m_hopperdev->motor_w(BIT(data, 0)); - - if (igs029_irq) - { - if (!m_igs029_recv_len) - { - // SEND - if (m_igs029_send_len < sizeof(m_igs029_send_buf)) - m_igs029_send_buf[m_igs029_send_len++] = m_igs029_send_data; - - logerror("%s: igs029 send ", machine().describe_context()); - for (int i = 0; i < m_igs029_send_len; i++) - logerror("%02x ", m_igs029_send_buf[i]); - logerror("\n"); - - if (m_igs029_send_buf[0] == m_igs029_send_len) - mgcs_igs029_run(); - } - - if (m_igs029_recv_len) - { - // RECV - logerror("%s: igs029 recv ", machine().describe_context()); - for (int i = 0; i < m_igs029_recv_len; i++) - logerror("%02x ", m_igs029_recv_buf[i]); - logerror("\n"); - - if (m_igs029_recv_len) - --m_igs029_recv_len; - - m_igs029_recv_data = m_igs029_recv_buf[m_igs029_recv_len]; - } - } - } - - if (m_input_select & ~0xfd) - logerror("%s: warning, unknown bits written in input_select = %02x\n", machine().describe_context(), m_input_select); - - break; - - case 0x01: - if (ACCESSING_BITS_0_7) - { - m_scramble_data = data & 0xff; -// logerror("%s: writing %02x to igs_magic = %02x\n", machine().describe_context(), data & 0xff, m_igs_magic); - } - break; - - // case 0x02: ? - - case 0x03: - if (ACCESSING_BITS_0_7) - { - m_igs029_send_data = data & 0xff; -// logerror("%s: writing %02x to igs_magic = %02x\n", machine().describe_context(), data & 0xff, m_igs_magic); - } - break; - - default: - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_igs_magic, data); - } -} - -u16 igs017_state::mgcs_magic_r() -{ - switch (m_igs_magic) - { - case 0x00: - return m_input_select | 0x02; - - case 0x01: + if (!m_igs029_recv_len) { - u16 ret = bitswap<8>( (bitswap<8>(m_scramble_data, 0,1,2,3,4,5,6,7) + 1) & 3, 4,5,6,7, 0,1,2,3); - logerror("%s: reading %02x from igs_magic = %02x\n", machine().describe_context(), ret, m_igs_magic); - return ret; + // SEND + if (m_igs029_send_len < sizeof(m_igs029_send_buf)) + m_igs029_send_buf[m_igs029_send_len++] = m_igs029_send_data; + + LOGMASKED(LOG_PROT_IGS029, "%s: igs029 send", machine().describe_context()); + for (int i = 0; i < m_igs029_send_len; i++) + LOGMASKED(LOG_PROT_IGS029, " %02x", m_igs029_send_buf[i]); + LOGMASKED(LOG_PROT_IGS029, "\n"); + + if (m_igs029_send_buf[0] == m_igs029_send_len) + mgcs_igs029_run(); } - case 0x02: + if (m_igs029_recv_len) { - u8 ret = m_igs029_recv_data; - logerror("%s: reading %02x from igs_magic = %02x\n", machine().describe_context(), ret, m_igs_magic); - return ret; + // RECV + LOGMASKED(LOG_PROT_IGS029, "%s: igs029 recv", machine().describe_context()); + for (int i = 0; i < m_igs029_recv_len; i++) + LOGMASKED(LOG_PROT_IGS029, " %02x", m_igs029_recv_buf[i]); + LOGMASKED(LOG_PROT_IGS029, "\n"); + + if (m_igs029_recv_len) + --m_igs029_recv_len; + + m_igs029_recv_data = m_igs029_recv_buf[m_igs029_recv_len]; } - -// case 0x05: ??? - - default: - logerror("%s: warning, reading with igs_magic = %02x\n", machine().describe_context(), m_igs_magic); - break; } - return 0xffff; + if (m_input_select & ~0xfd) + logerror("%s: warning, unknown bits written in input_select = %02x\n", machine().describe_context(), m_input_select); } -u8 igs017_state::mgcs_keys_r() +void igs017_state::mgcs_scramble_data_w(u8 data) { - if (~m_input_select & 0x08) return m_io_key[0]->read(); - if (~m_input_select & 0x10) return m_io_key[1]->read(); - if (~m_input_select & 0x20) return m_io_key[2]->read(); - if (~m_input_select & 0x40) return m_io_key[3]->read(); - if (~m_input_select & 0x80) return m_io_key[4]->read(); + m_scramble_data = data; + LOGMASKED(LOG_PROT_SCRAMBLE, "%s: writing scrambled data %02x to igs_mux\n", machine().describe_context(), data); +} - logerror("%s: warning, reading key with input_select = %02x\n", machine().describe_context(), m_input_select); - return 0xff; +u8 igs017_state::mgcs_scramble_data_r() +{ + u8 ret = bitswap<8>( (bitswap<8>(m_scramble_data, 0,1,2,3,4,5,6,7) + 1) & 3, 4,5,6,7, 0,1,2,3 ); + LOGMASKED(LOG_PROT_SCRAMBLE, "%s: reading scrambled data %02x from igs_mux\n", machine().describe_context(), ret); + return ret; +} + +u8 igs017_state::mgcs_igs029_data_r() +{ + u8 ret = m_igs029_recv_data; + LOGMASKED(LOG_PROT_IGS029, "%s: reading IGS029 data %02x from igs_mux\n", machine().describe_context(), ret); + return ret; +} + +void igs017_state::mgcs_igs029_data_w(u8 data) +{ + m_igs029_send_data = data; + LOGMASKED(LOG_PROT_IGS029, "%s: writing %02x to igs_mux\n", machine().describe_context(), data & 0xff); +} + +u8 igs017_state::mgcs_keys_joy_r() +{ + u8 ret = 0xff; + if (!BIT(m_input_select, 0, 3)) ret &= (m_io_joy->read() | 0x3f); // f8 (joystick mode, top 2 bits) + if (!BIT(m_input_select, 3)) ret &= m_io_key[0]->read(); // f7 (keyboard mode) + if (!BIT(m_input_select, 4)) ret &= m_io_key[1]->read(); // ef "" + if (!BIT(m_input_select, 5)) ret &= m_io_key[2]->read(); // df "" + if (!BIT(m_input_select, 6)) ret &= m_io_key[3]->read(); // bf "" + if (!BIT(m_input_select, 7)) ret &= m_io_key[4]->read(); // f7 "" + return ret; } void igs017_state::mgcs_map(address_map &map) { map(0x000000, 0x07ffff).rom(); map(0x300000, 0x303fff).ram(); - map(0x49c000, 0x49c001).rw(FUNC(igs017_state::magic_r), FUNC(igs017_state::magic_w)); - map(0x49c002, 0x49c003).rw(FUNC(igs017_state::mgcs_magic_r), FUNC(igs017_state::mgcs_magic_w)); + + map(0x49c000, 0x49c001).nopr().w(m_igs_mux, FUNC(igs_mux_device::address_w)).umask16(0x00ff); // clr.w dummy read + map(0x49c002, 0x49c003).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)).umask16(0x00ff); map(0xa00000, 0xa0ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0xa12001, 0xa12001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); - // oki banking through protection (code at $1a350)? + // oki banking through protection (code at $1a350) +} + +void igs017_state::mgcs_mux_map(address_map &map) +{ + map(0x00, 0x00).lr8(NAME([this](){ return m_input_select | 0x02; })).w(FUNC(igs017_state::mgcs_keys_hopper_igs029_w)); + map(0x01, 0x01).r(FUNC(igs017_state::mgcs_scramble_data_r)).w(FUNC(igs017_state::mgcs_scramble_data_w)); + map(0x02, 0x02).r(FUNC(igs017_state::mgcs_igs029_data_r)); + map(0x03, 0x03).w(FUNC(igs017_state::mgcs_igs029_data_w)); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r } // sdmg2 -u8 igs017_state::sdmg2_keys_r() -{ - if (~m_input_select & 0x01) return m_io_key[0]->read(); - if (~m_input_select & 0x02) return m_io_key[1]->read(); - if (~m_input_select & 0x04) return m_io_key[2]->read(); - if (~m_input_select & 0x08) return m_io_key[3]->read(); - if (~m_input_select & 0x10) return m_io_key[4]->read(); - - if (m_input_select == 0x1f) return m_io_key[0]->read(); // in joystick mode - - logerror("%s: warning, reading key with input_select = %02x\n", machine().describe_context(), m_input_select); - return 0xff; -} - -void igs017_state::sdmg2_magic_w(offs_t offset, u16 data, u16 mem_mask) -{ - switch (m_igs_magic) - { - // case 0x00: ? 0x80 - - case 0x01: - if (ACCESSING_BITS_0_7) - { - m_input_select = data & 0x1f; - machine().bookkeeping().coin_counter_w(0, data & 0x20); - // coin out data & 0x40 - m_hopper = data & 0x80; - } - break; - - case 0x02: - if (ACCESSING_BITS_0_7) - { - m_oki->set_rom_bank((data >> 7) & 1); - } - break; - - default: - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_igs_magic, data); - } -} - -u16 igs017_state::sdmg2_magic_r() -{ - switch (m_igs_magic) - { - case 0x00: - { - u16 hopper_bit = (m_hopper && ((m_screen->frame_number()/10)&1)) ? 0x0000 : 0x0001; - return m_io_coins->read() | hopper_bit; - } - - case 0x02: - return sdmg2_keys_r(); - - default: - logerror("%s: warning, reading with igs_magic = %02x\n", machine().describe_context(), m_igs_magic); - break; - } - - return 0xffff; -} - void igs017_state::sdmg2_map(address_map &map) { map(0x000000, 0x07ffff).rom(); + + // incdec protection + map(0x002001, 0x002001).w(m_igs_incdec, FUNC(igs_incdec_device::reset_w)); + map(0x002003, 0x002003).w(m_igs_incdec, FUNC(igs_incdec_device::dec_w)); + map(0x002007, 0x002007).w(m_igs_incdec, FUNC(igs_incdec_device::inc_w)); + map(0x00200b, 0x00200b).r(m_igs_incdec, FUNC(igs_incdec_device::result_r)); + map(0x1f0000, 0x1fffff).ram(); map(0x200000, 0x20ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0x210001, 0x210001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); - map(0x300000, 0x300001).w(FUNC(igs017_state::magic_w)); - map(0x300002, 0x300003).rw(FUNC(igs017_state::sdmg2_magic_r), FUNC(igs017_state::sdmg2_magic_w)); + + map(0x300000, 0x300001).nopr().w(m_igs_mux, FUNC(igs_mux_device::address_w)).umask16(0x00ff); // clr.w dummy read + map(0x300002, 0x300003).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)).umask16(0x00ff); } +u8 igs017_state::sdmg2_keys_joy_r() +{ + if (BIT(m_input_select, 0, 5) == 0x1f) return m_io_joy->read(); // 1f/uninitialized in test screen (joystick mode) + + u8 ret = 0xff; + if (!BIT(m_input_select, 0)) ret &= m_io_key[0]->read(); // 1e (keyboard mode) + if (!BIT(m_input_select, 1)) ret &= m_io_key[1]->read(); // 1d "" + if (!BIT(m_input_select, 2)) ret &= m_io_key[2]->read(); // 1b "" + if (!BIT(m_input_select, 3)) ret &= m_io_key[3]->read(); // 17 "" + if (!BIT(m_input_select, 4)) ret &= m_io_key[4]->read(); // 0f "" + return ret; +} + +void igs017_state::sdmg2_keys_hopper_w(u8 data) +{ + m_input_select = BIT(data, 0, 5); // keys + machine().bookkeeping().coin_counter_w(0, BIT(data, 5)); // coin in + machine().bookkeeping().coin_counter_w(1, BIT(data, 6)); // coin out + m_hopper->motor_w( BIT(data, 7)); // hopper +} + +void igs017_state::sdmg2_mux_map(address_map &map) +{ + map(0x00, 0x00).portr("COINS"); + map(0x01, 0x01).w(FUNC(igs017_state::sdmg2_keys_hopper_w)); + map(0x02, 0x02).r(FUNC(igs017_state::sdmg2_keys_joy_r)).w(NAME((&igs017_state::oki_sound_bank_w<7, 0x7f>))); +} // mgdh, mgdha -u8 igs017_state::mgdh_keys_r() -{ - if (~m_input_select & 0x04) return m_io_key[0]->read(); - if (~m_input_select & 0x08) return m_io_key[1]->read(); - if (~m_input_select & 0x10) return m_io_key[2]->read(); - if (~m_input_select & 0x20) return m_io_key[3]->read(); - if (~m_input_select & 0x40) return m_io_key[4]->read(); - - if ((m_input_select & 0xfc) == 0xfc) return m_io_dsw[0]->read(); - - logerror("%s: warning, reading key with input_select = %02x\n", machine().describe_context(), m_input_select); - return 0xff; -} - -void igs017_state::mgdha_magic_w(offs_t offset, u16 data, u16 mem_mask) -{ - switch (m_igs_magic) - { - case 0x00: - if (ACCESSING_BITS_0_7) - { - // coin out data & 0x40 - machine().bookkeeping().coin_counter_w(0, data & 0x80); - } - - if (data & ~0xc0) - logerror("%s: warning, unknown bits written to igs_magic 00 = %02x\n", machine().describe_context(), data); - - break; - - case 0x01: - if (ACCESSING_BITS_0_7) - { - m_input_select = data & 0xff; - m_hopper = data & 0x01; - } - - if (m_input_select & ~0xfd) - logerror("%s: warning, unknown bits written in input_select = %02x\n", machine().describe_context(), m_input_select); - - break; - - case 0x03: - if (ACCESSING_BITS_0_7) - { - // bit 7? - m_oki->set_rom_bank((data >> 6) & 1); - } - break; - - default: -/* - 04aba0: warning, writing to igs_magic 08 = d0 - 04abb0: warning, writing to igs_magic 09 = 76 - 04abc0: warning, writing to igs_magic 0a = 97 - 04abd0: warning, writing to igs_magic 0b = bf - 04abe0: warning, writing to igs_magic 0c = ff - 04abf0: warning, writing to igs_magic 04 = 3f - 04ac00: warning, writing to igs_magic 05 = 82 - 04ac10: warning, writing to igs_magic 06 = ff - 04ac20: warning, writing to igs_magic 07 = 3f -*/ - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_igs_magic, data); - } -} - -u16 igs017_state::mgdha_magic_r() -{ - switch (m_igs_magic) - { - case 0x00: - return mgdh_keys_r(); - - case 0x01: - return m_io_buttons->read(); - - case 0x02: - return bitswap<8>(m_io_dsw[1]->read(), 0,1,2,3,4,5,6,7); - - case 0x03: - { - u16 hopper_bit = (m_hopper && ((m_screen->frame_number()/10)&1)) ? 0x0000 : 0x0001; - return m_io_coins->read() | hopper_bit; - } - - default: - logerror("%s: warning, reading with igs_magic = %02x\n", machine().describe_context(), m_igs_magic); - break; - } - - return 0xffff; -} - -void igs017_state::mgdha_map(address_map &map) +void igs017_state::mgdh_map(address_map &map) { map(0x000000, 0x07ffff).rom(); map(0x600000, 0x603fff).ram(); - map(0x876000, 0x876001).w(FUNC(igs017_state::magic_w)); - map(0x876002, 0x876003).rw(FUNC(igs017_state::mgdha_magic_r), FUNC(igs017_state::mgdha_magic_w)); + + map(0x876000, 0x876001).nopr().w(m_igs_mux, FUNC(igs_mux_device::address_w)).umask16(0x00ff); // clr.w dummy read + map(0x876002, 0x876003).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)).umask16(0x00ff); map(0xa00000, 0xa0ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0xa10001, 0xa10001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); } +u8 igs017_state::mgdh_keys_r() +{ + u8 ret = 0xff; + if (!BIT(m_input_select, 2)) ret &= m_io_key[0]->read(); // f8 (keyboard mode / joystick mode) + if (!BIT(m_input_select, 3)) ret &= m_io_key[1]->read(); // f4 (keyboard mode) + if (!BIT(m_input_select, 4)) ret &= m_io_key[2]->read(); // ec "" + if (!BIT(m_input_select, 5)) ret &= m_io_key[3]->read(); // dc "" + if (!BIT(m_input_select, 6)) ret &= m_io_key[4]->read(); // bc "" + return ret; +} + +void igs017_state::mgdh_keys_hopper_w(u8 data) +{ + m_input_select = data; + m_hopper->motor_w(BIT(data, 0)); + + if (m_input_select & ~0xfd) + logerror("%s: warning, unknown bits written in keys_hopper_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::mgdh_counter_w(u8 data) +{ + machine().bookkeeping().coin_counter_w(0, BIT(data, 6)); // coin out + machine().bookkeeping().coin_counter_w(1, BIT(data, 7)); // coin in + + if (data & ~0xc0) + logerror("%s: warning, unknown bits written in counter_w = %02x\n", machine().describe_context(), data); +} + +void igs017_state::mgdha_mux_map(address_map &map) +{ + map(0x00, 0x00).r(FUNC(igs017_state::mgdh_keys_r)).w(FUNC(igs017_state::mgdh_counter_w)); + map(0x01, 0x01).portr("BUTTONS").w(FUNC(igs017_state::mgdh_keys_hopper_w)); + map(0x02, 0x02).lr8(NAME([this](){ return bitswap<8>(m_io_dsw[1]->read(), 0,1,2,3,4,5,6,7); })); + map(0x03, 0x03).portr("COINS").w(NAME((&igs017_state::oki_sound_bank_w<6, 0x3f>))); // bit 7? always on +} + +void igs017_state::mgdh_mux_map(address_map &map) +{ + mgdha_mux_map(map); + +// igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r (actually unused except for the game id check?) +} + // tjsb -void igs017_state::tjsb_output_w(u8 data) -{ - switch (m_input_select) - { - case 0x00: - machine().bookkeeping().coin_counter_w(0, data & 0x80); // coin in - if (!(data & ~0x80)) - return; - break; - - case 0x01: - machine().bookkeeping().coin_counter_w(1, data & 0x01); // coin out - if (!(data & ~0x01)) - return; - break; - - case 0x02: - m_oki->set_rom_bank((data >> 4) & 1); // oki bank (0x20/0x30) - if (!(data & ~0x30)) - return; - break; - - case 0x03: - m_hopper = data & 0x40; - if (!(data & ~0x40)) - return; - break; - } - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_input_select, data); -} - -u8 igs017_state::tjsb_input_r() -{ - switch (m_input_select) - { - case 0x00: return m_io_player1->read(); - case 0x01: return m_io_player2->read(); - case 0x02: return m_io_coins->read(); - case 0x03: - { - u8 hopper_bit = (m_hopper && ((m_screen->frame_number()/10)&1)) ? 0x00 : 0x20; - return m_io_hopper->read() | hopper_bit; - } - - default: - logerror("%s: input %02x read\n", machine().describe_context(), m_input_select); - return 0xff; - } -} - void igs017_state::tjsb_map(address_map &map) { map(0x00000, 0x0dfff).rom(); - map(0x0e000, 0x0e000).w(FUNC(igs017_state::input_select_w)); - map(0x0e001, 0x0e001).rw(FUNC(igs017_state::tjsb_input_r), FUNC(igs017_state::tjsb_output_w)); + + map(0x0e000, 0x0e000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0x0e001, 0x0e001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); + map(0x0e002, 0x0efff).ram(); map(0x0f000, 0x0ffff).ram(); map(0x10000, 0x3ffff).rom(); @@ -2173,7 +2590,6 @@ void igs017_state::tjsb_map(address_map &map) void igs017_state::tjsb_io(address_map &map) { map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); - map(0x0000, 0x003f).ram(); // internal regs map(0x9000, 0x9000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); @@ -2181,149 +2597,124 @@ void igs017_state::tjsb_io(address_map &map) map(0xb000, 0xb001).w("ymsnd", FUNC(ym2413_device::write)); } +void igs017_state::tjsb_mux_map(address_map &map) +{ + map(0x00, 0x00).portr("PLAYER1").w(NAME((&igs017_state::counter_w<7, 0x7f, 0>))); // coin in + map(0x01, 0x01).portr("PLAYER2").w(NAME((&igs017_state::counter_w<0, 0xfe, 1>))); // coin out + map(0x02, 0x02).portr("COINS").w(NAME((&igs017_state::oki_sound_bank_w<4, 0xcf>))); // oki bank (0x20/0x30) + map(0x03, 0x03).portr("BUTTONS").w(NAME((&igs017_state::hopper_motor_w<6, 0xbf>))); + + // used ? + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r +} + // spkrform -void igs017_state::spkrform_map(address_map &map) -{ - map(0x00000, 0x0dfff).rom(); - map(0x0e000, 0x0efff).ram(); - map(0x0e9bf, 0x0e9bf).noprw(); // hack: uncomment to switch to Formosa - map(0x0f000, 0x0ffff).ram(); - map(0x10000, 0x3ffff).rom(); -} - -u8 igs017_state::spkrform_input_r() -{ - switch (m_input_select) - { - case 0x00: return m_io_player1->read(); - case 0x01: return m_io_player2->read(); - case 0x02: return m_io_coins->read(); - case 0x03: - { - return m_io_buttons->read(); - } - - default: - logerror("%s: input %02x read\n", machine().describe_context(), m_input_select); - return 0xff; - } -} - void igs017_state::spkrform_io(address_map &map) { map(0x0000, 0x7fff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)); - map(0x0000, 0x003f).ram(); // internal regs + map(0x2010, 0x2011).w(FUNC(igs017_state::incdec_remap_addr_w)); + map(0x8000, 0x8000).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); map(0x9000, 0x9001).w("ymsnd", FUNC(ym2413_device::write)); - map(0xa000, 0xa000).portr("A000"); // Game selection - map(0xa001, 0xa001).portr("A001"); +// map(0xa000, 0xa0??).ram(); // read/written during poker game enabling at boot (patched out) - map(0xb000, 0xb000).w(FUNC(igs017_state::input_select_w)); - map(0xb001, 0xb001).r(FUNC(igs017_state::spkrform_input_r)); + map(0xb000, 0xb000).w (m_igs_mux, FUNC(igs_mux_device::address_w)); + map(0xb001, 0xb001).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)); +} + +void igs017_state::spkrform_mux_map(address_map &map) +{ + map(0x00, 0x00).portr("PLAYER1").w(NAME((&igs017_state::counter_w<7, 0x7f, 0>))); // coin in + map(0x01, 0x01).portr("PLAYER2").w(NAME((&igs017_state::counter_w<7, 0x7f, 1>))); // coin out + map(0x02, 0x02).portr("COINS").w(NAME((&igs017_state::hopper_motor_w<4, 0xef>))); // bit 5 is related to poker game enabling + map(0x03, 0x03).portr("BUTTONS"); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r } // lhzb2 -void igs017_state::lhzb2_magic_w(offs_t offset, u16 data, u16 mem_mask) -{ - switch (m_igs_magic) - { - case 0x00: - if (ACCESSING_BITS_0_7) - { - m_input_select = data & 0xff; - } - - if (m_input_select & ~0x1f) - logerror("%s: warning, unknown bits written in input_select = %02x\n", machine().describe_context(), m_input_select); - break; - - case 0x01: - if (ACCESSING_BITS_0_7) - { - m_oki->set_rom_bank((data >> 7) & 1); - - if (data & 0x7f) - logerror("%s: warning, unknown bits written in oki bank = %04x\n", machine().describe_context(), data); - } - break; - - default: - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_igs_magic, data); - } -} - -u16 igs017_state::lhzb2_magic_r() -{ - switch (m_igs_magic) - { - case 0x01: - { - if (~m_input_select & 0x01) return m_io_key[0]->read(); - if (~m_input_select & 0x02) return m_io_key[1]->read(); - if (~m_input_select & 0x04) return m_io_key[2]->read(); - if (~m_input_select & 0x08) return m_io_key[3]->read(); - if (~m_input_select & 0x10) return m_io_key[4]->read(); - - logerror("%s: warning, reading key with input_select = %02x\n", machine().describe_context(), m_input_select); - return 0xffff; - } - - default: - logerror("%s: warning, reading with igs_magic = %02x\n", machine().describe_context(), m_igs_magic); - break; - } - - return 0xffff; -} - void igs017_state::lhzb2_map(address_map &map) { map(0x000000, 0x07ffff).rom(); + + map(0x100000, 0x103fff).ram().share("igs022:sharedprotram"); // Shared with protection device + map(0x500000, 0x503fff).ram(); - map(0x910000, 0x910001).w(FUNC(igs017_state::magic_w)); - map(0x910002, 0x910003).rw(FUNC(igs017_state::lhzb2_magic_r), FUNC(igs017_state::lhzb2_magic_w)); + + map(0x910000, 0x910001).nopr().w(m_igs_mux, FUNC(igs_mux_device::address_w)).umask16(0x00ff); // clr.w dummy read + map(0x910002, 0x910003).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)).umask16(0x00ff); map(0xb00000, 0xb0ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0xb10001, 0xb10001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); } +u8 igs017_state::lhzb2_keys_r() +{ + u8 ret = 0xff; + if (!BIT(m_input_select, 0)) ret &= m_io_key[0]->read(); + if (!BIT(m_input_select, 1)) ret &= m_io_key[1]->read(); + if (!BIT(m_input_select, 2)) ret &= m_io_key[2]->read(); + if (!BIT(m_input_select, 3)) ret &= m_io_key[3]->read(); + if (!BIT(m_input_select, 4)) ret &= m_io_key[4]->read(); + return ret; +} + +void igs017_state::lhzb2_keys_hopper_w(u8 data) +{ + m_input_select = BIT(data, 0, 5); // keys + m_hopper->motor_w( BIT(data, 5)); // hopper + machine().bookkeeping().coin_counter_w(1, BIT(data, 6)); // coin out counter + machine().bookkeeping().coin_counter_w(0, BIT(data, 7)); // coin in counter +} + +u8 igs017_state::lhzb2_scramble_data_r() +{ + u8 ret = bitswap<8>(m_scramble_data, 0,1,2,3,4,5,6,7); + LOGMASKED(LOG_PROT_SCRAMBLE, "%s: reading scrambled data %02x from igs_mux\n", machine().describe_context(), ret); + return ret; +} + +void igs017_state::lhzb2_igs022_execute_w(u8 data) +{ + m_oki->set_rom_bank(BIT(data, 7)); + igs022_execute_w<6, 0x3f>(data); +} + +void igs017_state::lhzb2_mux_map(address_map &map) +{ + map(0x00, 0x00).w(FUNC(igs017_state::lhzb2_keys_hopper_w)); + map(0x01, 0x01).r(FUNC(igs017_state::lhzb2_keys_r)).w(FUNC(igs017_state::lhzb2_igs022_execute_w)); + map(0x02, 0x02).r(FUNC(igs017_state::lhzb2_scramble_data_r)); + map(0x03, 0x03).w(FUNC(igs017_state::mgcs_scramble_data_w)); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r +} + // lhzb2a // To do: what devices are on this PCB? u16 igs017_state::lhzb2a_input_r(offs_t offset) { - switch (offset*2) + switch (offset * 2) { - case 0x00: // Keys - { - if (~m_input_select & 0x01) return m_io_key[0]->read() << 8; - if (~m_input_select & 0x02) return m_io_key[1]->read() << 8; - if (~m_input_select & 0x04) return m_io_key[2]->read() << 8; - if (~m_input_select & 0x08) return m_io_key[3]->read() << 8; - if (~m_input_select & 0x10) return m_io_key[4]->read() << 8; - - logerror("%s: warning, reading key with input_select = %02x\n", machine().describe_context(), m_input_select); - return 0xffff; - } + case 0x00: // Keys + return (lhzb2_keys_r() << 8) | 0xff; case 0x02: - { - u16 hopper_bit = (m_hopper && ((m_screen->frame_number()/10)&1)) ? 0x0000 : 0x0002; - return (m_io_dsw[0]->read() << 8) | m_io_coins->read() | hopper_bit; - } + return (m_io_dsw[0]->read() << 8) | m_io_coins->read(); case 0x04: - return m_io_dsw[1]->read(); + return 0xff00 | m_io_dsw[1]->read(); } return 0xffff; @@ -2333,7 +2724,7 @@ u16 igs017_state::lhzb2a_input_r(offs_t offset) An address base register (xx = F0 at reset) determines where the bitswap protection device, as well as game inputs and the address base register itself are mapped in memory: - inputs are mapped at xx8000, protection at xx4000 and base register at xxc000. + inputs are mapped at xx8000, protection at xx4000 and address base register at xxc000. ***************************************************************************/ @@ -2352,30 +2743,30 @@ void igs017_state::lhzb2a_remap_addr_w(address_space &space, u16 data) m_remap_addr = data & 0xff; // Add new memory ranges - space.install_write_handler (m_remap_addr * 0x10000 + 0x4001, m_remap_addr * 0x10000 + 0x4001, write8smo_delegate(*m_igs_bitswap, FUNC(igs_bitswap_device::address_w))); - space.install_readwrite_handler(m_remap_addr * 0x10000 + 0x4003, m_remap_addr * 0x10000 + 0x4003, read8smo_delegate (*m_igs_bitswap, FUNC(igs_bitswap_device::data_r)), write8smo_delegate(*m_igs_bitswap, FUNC(igs_bitswap_device::data_w))); + space.install_write_handler (m_remap_addr * 0x10000 + 0x4001, m_remap_addr * 0x10000 + 0x4001, write8smo_delegate(*m_igs_mux, FUNC(igs_mux_device::address_w))); + space.install_readwrite_handler(m_remap_addr * 0x10000 + 0x4003, m_remap_addr * 0x10000 + 0x4003, read8smo_delegate (*m_igs_mux, FUNC(igs_mux_device::data_r)), write8smo_delegate(*m_igs_mux, FUNC(igs_mux_device::data_w))); space.install_read_handler (m_remap_addr * 0x10000 + 0x8000, m_remap_addr * 0x10000 + 0x8005, read16sm_delegate (*this, FUNC(igs017_state::lhzb2a_input_r))); space.install_write_handler (m_remap_addr * 0x10000 + 0xc000, m_remap_addr * 0x10000 + 0xc001, write16mo_delegate(*this, FUNC(igs017_state::lhzb2a_remap_addr_w))); - logerror("%s: inputs and protection remapped at %02xxxxx\n", machine().describe_context(), m_remap_addr); + LOGMASKED(LOG_PROT_REMAP, "%s: inputs and protection remapped at %02xxxxx\n", machine().describe_context(), m_remap_addr); } -void igs017_state::lhzb2a_input_select_w(offs_t offset, u16 data, u16 mem_mask) +void igs017_state::lhzb2a_keys_hopper_w(offs_t offset, u16 data, u16 mem_mask) { if (ACCESSING_BITS_0_7) { - m_input_select = data & 0x1f; // keys - m_hopper = data & 0x20; // hopper motor - machine().bookkeeping().coin_counter_w(1, data & 0x40); // coin out counter - machine().bookkeeping().coin_counter_w(0, data & 0x80); // coin in counter + m_input_select = BIT(data, 0, 5); // keys + m_hopper->motor_w( BIT(data, 5)); // hopper + machine().bookkeeping().coin_counter_w(0, BIT(data, 6)); // coin out counter + machine().bookkeeping().coin_counter_w(1, BIT(data, 7)); // coin in counter } if (ACCESSING_BITS_8_15) { - m_oki->set_rom_bank((data >> 8) & 1); + m_oki->set_rom_bank(BIT(data, 7)); if (data & 0xfe00) - logerror("%s: warning, unknown bits written in input_select = %04x\n", machine().describe_context(), data); + logerror("%s: warning, unknown bits written in keys_hopper_w = %04x\n", machine().describe_context(), data); } } @@ -2384,10 +2775,10 @@ void igs017_state::lhzb2a_map(address_map &map) map(0x000000, 0x07ffff).rom(); // incdec protection - map(0x003200, 0x003201).w(m_igs_incdec, FUNC(igs_incdec_device::reset_w)); - map(0x003202, 0x003203).w(m_igs_incdec, FUNC(igs_incdec_device::dec_w)); - map(0x003206, 0x003207).w(m_igs_incdec, FUNC(igs_incdec_device::inc_w)); - map(0x00320a, 0x00320b).r(m_igs_incdec, FUNC(igs_incdec_device::val_r)); + map(0x003201, 0x003201).w(m_igs_incdec, FUNC(igs_incdec_device::reset_w)); + map(0x003203, 0x003203).w(m_igs_incdec, FUNC(igs_incdec_device::dec_w)); + map(0x003207, 0x003207).w(m_igs_incdec, FUNC(igs_incdec_device::inc_w)); + map(0x00320b, 0x00320b).r(m_igs_incdec, FUNC(igs_incdec_device::result_r)); map(0x500000, 0x503fff).ram(); // map(0x910000, 0x910003) accesses appear to be from leftover code where the final checks were disabled @@ -2395,78 +2786,65 @@ void igs017_state::lhzb2a_map(address_map &map) map(0xb00000, 0xb0ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0xb10001, 0xb10001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); - map(0xb12000, 0xb12001).w(FUNC(igs017_state::lhzb2a_input_select_w)); - // Inputs dynamically mapped at xx8000, protection at xx4000 (xx = f0 initially). xx written to xxc000 + map(0xb12000, 0xb12001).w(FUNC(igs017_state::lhzb2a_keys_hopper_w)); + + // Inputs dynamically mapped at xx8000, protection at xx4000 (xx = f0 initially). xx written to xxc000 +} + +void igs017_state::lhzb2a_mux_map(address_map &map) +{ + igs_bitswap_mux_map(map); // 0x03 r, 0x40 - 0x47 w, 0x48 w, 0x50 w, 0x80 - 0x87 w, 0xa0 w + + // used ? + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r } // slqz2 -void igs017_state::slqz2_magic_w(offs_t offset, u16 data, u16 mem_mask) -{ - switch (m_igs_magic) - { - case 0x00: - if (ACCESSING_BITS_0_7) - { - m_oki->set_rom_bank(data & 0x01); - -// m_hopper = data & 0x20; // hopper motor -// machine().bookkeeping().coin_counter_w(1, data & 0x40); // coin out counter - machine().bookkeeping().coin_counter_w(0, data & 0x80); // coin in counter - - if (data & 0x7e) - logerror("%s: warning, unknown bits written in oki bank = %04x\n", machine().describe_context(), data); - } - break; - - default: - logerror("%s: warning, writing to igs_magic %02x = %02x\n", machine().describe_context(), m_igs_magic, data); - } -} - -u16 igs017_state::slqz2_magic_r() -{ - switch (m_igs_magic) - { - case 0x00: - return m_io_player2->read(); - case 0x01: - return m_io_player1->read(); - case 0x02: - return m_io_buttons->read(); - - default: - logerror("%s: warning, reading with igs_magic = %02x\n", machine().describe_context(), m_igs_magic); - break; - } - - return 0xffff; -} - void igs017_state::slqz2_map(address_map &map) { map(0x000000, 0x07ffff).rom(); map(0x100000, 0x103fff).ram(); - map(0x602000, 0x602001).w(FUNC(igs017_state::magic_w)); - map(0x602002, 0x602003).rw(FUNC(igs017_state::slqz2_magic_r), FUNC(igs017_state::slqz2_magic_w)); + + map(0x300000, 0x303fff).ram().share("igs022:sharedprotram"); // Shared with protection device + + map(0x602000, 0x602001).nopr().w(m_igs_mux, FUNC(igs_mux_device::address_w)).umask16(0x00ff); // clr.w dummy read + map(0x602002, 0x602003).rw(m_igs_mux, FUNC(igs_mux_device::data_r), FUNC(igs_mux_device::data_w)).umask16(0x00ff); map(0x900000, 0x90ffff).rw(m_igs017_igs031, FUNC(igs017_igs031_device::read), FUNC(igs017_igs031_device::write)).umask16(0x00ff); map(0x910001, 0x910001).rw(m_oki, FUNC(okim6295_device::read), FUNC(okim6295_device::write)); } -u8 igs017_state::i8255_port_c_mux_r() +void igs017_state::slqz2_sound_hopper_w(u8 data) { - switch(m_i8255_portc_mux) - { - case 0x01: return m_io_dsw[2]->read(); - case 0x02: return m_io_dsw[1]->read(); - case 0x03: return m_io_dsw[0]->read(); - } + m_oki->set_rom_bank( BIT(data, 0)); + // + m_hopper->motor_w( BIT(data, 5)); // hopper + machine().bookkeeping().coin_counter_w(1, BIT(data, 6)); // coin out counter + machine().bookkeeping().coin_counter_w(0, BIT(data, 7)); // coin in counter - return 0xff; + if (data & 0x1e) + logerror("%s: warning, unknown bits written in sound_hopper_w = %04x\n", machine().describe_context(), data); +} + +u8 igs017_state::slqz2_scramble_data_r() +{ + u8 ret = m_scramble_data; + LOGMASKED(LOG_PROT_SCRAMBLE, "%s: reading scrambled data %02x from igs_mux\n", machine().describe_context(), ret); + return ret; +} + +void igs017_state::slqz2_mux_map(address_map &map) +{ + map(0x00, 0x00).portr("PLAYER2").w(FUNC(igs017_state::slqz2_sound_hopper_w)); + map(0x01, 0x01).portr("PLAYER1").w(NAME((&igs017_state::igs022_execute_w<6, 0xbf>))); + map(0x02, 0x02).r(FUNC(igs017_state::slqz2_scramble_data_r)); + map(0x03, 0x03).w(FUNC(igs017_state::mgcs_scramble_data_w)); + + igs_string_mux_map(map); // 0x05 r, 0x20 - 0x27 w, 0x40 r } @@ -2476,16 +2854,16 @@ u8 igs017_state::i8255_port_c_mux_r() static INPUT_PORTS_START( iqblocka ) PORT_START("DSW1") - PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "Hold Mode" ) + PORT_DIPNAME( 0x02, 0x02, "Hold Mode" ) PORT_DIPLOCATION("SW1:2") PORT_DIPSETTING( 0x02, "In Win" ) PORT_DIPSETTING( 0x00, "Always" ) - PORT_DIPNAME( 0x04, 0x04, "Max Credit" ) + PORT_DIPNAME( 0x04, 0x04, "Max Credit" ) PORT_DIPLOCATION("SW1:3") PORT_DIPSETTING( 0x04, "4000" ) PORT_DIPSETTING( 0x00, DEF_STR( None ) ) - PORT_DIPNAME( 0x38, 0x38, "Cigarette Bet" ) + PORT_DIPNAME( 0x38, 0x38, "Cigarette Bet" ) PORT_DIPLOCATION("SW1:4,5,6") PORT_DIPSETTING( 0x38, "1" ) PORT_DIPSETTING( 0x30, "10" ) PORT_DIPSETTING( 0x28, "20" ) @@ -2494,14 +2872,14 @@ static INPUT_PORTS_START( iqblocka ) PORT_DIPSETTING( 0x10, "100" ) PORT_DIPSETTING( 0x08, "120" ) PORT_DIPSETTING( 0x00, "150" ) - PORT_DIPNAME( 0xc0, 0xc0, "Min Bet" ) + PORT_DIPNAME( 0xc0, 0xc0, "Minimum Bet" ) PORT_DIPLOCATION("SW1:7,8") PORT_DIPSETTING( 0xc0, "1" ) PORT_DIPSETTING( 0x80, "10" ) PORT_DIPSETTING( 0x40, "20" ) PORT_DIPSETTING( 0x00, "50" ) PORT_START("DSW2") - PORT_DIPNAME( 0x07, 0x07, "Key In" ) + PORT_DIPNAME( 0x07, 0x07, "Key In" ) PORT_DIPLOCATION("SW2:1,2,3") PORT_DIPSETTING( 0x07, "10" ) PORT_DIPSETTING( 0x06, "20" ) PORT_DIPSETTING( 0x05, "40" ) @@ -2510,63 +2888,63 @@ static INPUT_PORTS_START( iqblocka ) PORT_DIPSETTING( 0x02, "200" ) PORT_DIPSETTING( 0x01, "250" ) PORT_DIPSETTING( 0x00, "500" ) - PORT_DIPNAME( 0x08, 0x08, "Key Out" ) + PORT_DIPNAME( 0x08, 0x08, "Key Out" ) PORT_DIPLOCATION("SW2:4") PORT_DIPSETTING( 0x08, "10" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) - PORT_DIPSETTING( 0x10, "Gaming" ) + PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) PORT_DIPLOCATION("SW2:5") + PORT_DIPSETTING( 0x10, "Gaming (Gambling)" ) PORT_DIPSETTING( 0x00, "Amuse" ) - PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) + PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0xc0, 0xc0, "Bonus Base" ) + PORT_DIPNAME( 0xc0, 0xc0, "Bonus Base" ) PORT_DIPLOCATION("SW2:7,8") PORT_DIPSETTING( 0xc0, "100" ) PORT_DIPSETTING( 0x80, "200" ) PORT_DIPSETTING( 0x40, "300" ) PORT_DIPSETTING( 0x00, "400" ) PORT_START("DSW3") - PORT_DIPNAME( 0x03, 0x03, "Win Up Pool" ) + PORT_DIPNAME( 0x03, 0x03, "Win Up Pool" ) PORT_DIPLOCATION("SW3:1,2") PORT_DIPSETTING( 0x03, "300" ) PORT_DIPSETTING( 0x02, "500" ) PORT_DIPSETTING( 0x01, "800" ) PORT_DIPSETTING( 0x00, "1000" ) - PORT_DIPNAME( 0x0c, 0x0c, "Max Double Up" ) + PORT_DIPNAME( 0x0c, 0x0c, "Max Double Up" ) PORT_DIPLOCATION("SW3:3,4") PORT_DIPSETTING( 0x0c, "20000" ) PORT_DIPSETTING( 0x08, "30000" ) PORT_DIPSETTING( 0x04, "40000" ) PORT_DIPSETTING( 0x00, "50000" ) - PORT_DIPNAME( 0x10, 0x10, "Cards" ) + PORT_DIPNAME( 0x10, 0x10, "Number Type" ) PORT_DIPLOCATION("SW3:5") PORT_DIPSETTING( 0x10, "A,J,Q,K" ) PORT_DIPSETTING( 0x00, "Number" ) - PORT_DIPNAME( 0x20, 0x20, "Title Name" ) - PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x20, DEF_STR( On ) ) - PORT_DIPNAME( 0x40, 0x40, "Double Up" ) + PORT_DIPNAME( 0x20, 0x20, "Show Title" ) PORT_DIPLOCATION("SW3:6") + PORT_DIPSETTING( 0x20, DEF_STR( Yes ) ) + PORT_DIPSETTING( 0x00, DEF_STR( No ) ) + PORT_DIPNAME( 0x40, 0x40, "Double Up" ) PORT_DIPLOCATION("SW3:7") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x40, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, "CG Select" ) + PORT_DIPNAME( 0x80, 0x80, "CG Select" ) PORT_DIPLOCATION("SW3:8") // Switches CG ROM (sprites). Unpopulated in this set PORT_DIPSETTING( 0x80, DEF_STR( Low ) ) PORT_DIPSETTING( 0x00, DEF_STR( High ) ) PORT_START("PLAYER1") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_NAME( "Start" ) // start, in videogame mode (keep pressed while booting for DSW and inputs test) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) // start, in videogame mode (keep pressed while booting for DSW and inputs test) PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_NAME( "Down / Collect Win" ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_NAME("%p Down / Collect Win") PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Hold 1 / Big / Help" ) // help = next tile becomes a wildcard (in videogame mode) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME( "Hold 2 / Double Up" ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_POKER_HOLD1 ) PORT_NAME("Hold 1 / Big / Help") // (1P A in test mode) help = next tile becomes a wildcard (in videogame mode) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD2 ) PORT_NAME("Hold 2 / Double Up") // (1P B in test mode) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START2 ) PORT_NAME( "Play / Last Bet" ) // play current bet or, if null, bet as last time (2P C in test mode) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_DEAL ) PORT_NAME("Deal / Last Bet") // play current bet or, if null, the last bet (START2 in test mode) PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2) // unused? shown in test mode PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2) // "" PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2) // "" PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2) // "" - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_NAME( "Hold 4 / Half Double" ) // (2P A in test mode) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON5 ) PORT_NAME( "Hold 5 / Tile in Double Up?" ) // (2P B in test mode) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_POKER_HOLD4 ) PORT_NAME("Hold 4 / Half Double") // (2P A in test mode) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD5 ) PORT_NAME("Hold 5 / Tile in Double Up?") // (2P B in test mode) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("COINS") @@ -2577,15 +2955,15 @@ static INPUT_PORTS_START( iqblocka ) PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_SERVICE_NO_TOGGLE( 0x40, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME( "Toggle Gambling" ) // this toggles between videogame and gambling + PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Toggle Gambling") // this toggles between videogame and gambling PORT_START("BUTTONS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_NAME( "Hold 3 / Small" ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // no coin. Hopper sensor? impulse prevents coin error in gambling mode (1P D in test mode) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON6 ) // unused? (1P E in test mode) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_START3 ) PORT_NAME( "Bet" ) // Bet 1 credit (2P C in test mode) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_PLAYER(2) // unused? (2P D in test mode) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON5 ) PORT_PLAYER(2) // unused? (2P E in test mode) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_POKER_HOLD3 ) PORT_NAME("Hold 3 / Small") // (1P C in test mode) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // no coin. Hopper sensor? impulse prevents coin error in gambling mode (1P D in test mode) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON4 ) // unused? (1P E in test mode) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_BET ) // Bet 1 credit (2P C in test mode) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_PLAYER(2) // unused? (2P D in test mode) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON5 ) PORT_PLAYER(2) // unused? (2P E in test mode) PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) INPUT_PORTS_END @@ -2594,195 +2972,200 @@ static INPUT_PORTS_START( iqblockf ) PORT_INCLUDE( iqblocka ) PORT_MODIFY("DSW1") - PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "Hold Mode" ) + PORT_DIPNAME( 0x02, 0x02, "Hold Mode" ) PORT_DIPLOCATION("SW1:2") PORT_DIPSETTING( 0x02, "In Win" ) PORT_DIPSETTING( 0x00, "Always" ) - PORT_DIPNAME( 0x0c, 0x0c, "Coin In" ) + PORT_DIPNAME( 0x0c, 0x0c, "Coin In" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "1" ) PORT_DIPSETTING( 0x08, "5" ) PORT_DIPSETTING( 0x04, "10" ) PORT_DIPSETTING( 0x00, "20" ) - PORT_DIPNAME( 0x30, 0x30, "Key In" ) + PORT_DIPNAME( 0x30, 0x30, "Key In" ) PORT_DIPLOCATION("SW1:5,6") PORT_DIPSETTING( 0x30, "10" ) PORT_DIPSETTING( 0x20, "100" ) PORT_DIPSETTING( 0x10, "200" ) PORT_DIPSETTING( 0x00, "500" ) - PORT_DIPNAME( 0xc0, 0xc0, "Min Bet" ) + PORT_DIPNAME( 0xc0, 0xc0, "Minimum Bet" ) PORT_DIPLOCATION("SW1:7,8") PORT_DIPSETTING( 0xc0, "1" ) PORT_DIPSETTING( 0x80, "2" ) PORT_DIPSETTING( 0x40, "5" ) PORT_DIPSETTING( 0x00, "10" ) PORT_MODIFY("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Max Bet" ) + PORT_DIPNAME( 0x03, 0x03, "Max Bet" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "5" ) PORT_DIPSETTING( 0x02, "10" ) PORT_DIPSETTING( 0x01, "20" ) PORT_DIPSETTING( 0x00, "50" ) - PORT_DIPNAME( 0x04, 0x04, "Register" ) + PORT_DIPNAME( 0x04, 0x04, "Register" ) PORT_DIPLOCATION("SW2:3") PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x08, 0x08, "Key Out Base" ) + PORT_DIPNAME( 0x08, 0x08, "Key Out Base" ) PORT_DIPLOCATION("SW2:4") PORT_DIPSETTING( 0x08, "1" ) PORT_DIPSETTING( 0x00, "10" ) - PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) - PORT_DIPSETTING( 0x10, "Gaming" ) + PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) PORT_DIPLOCATION("SW2:5") + PORT_DIPSETTING( 0x10, "Gaming (Gambling)" ) PORT_DIPSETTING( 0x00, "Amuse" ) - PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) + PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPUNUSED( 0x40, 0x40 ) - PORT_DIPUNUSED( 0x80, 0x80 ) + PORT_DIPUNUSED_DIPLOC( 0x40, 0x40, "SW2:7" ) + PORT_DIPUNUSED_DIPLOC( 0x80, 0x80, "SW2:8" ) PORT_MODIFY("DSW3") - PORT_DIPUNUSED( 0x01, 0x01 ) - PORT_DIPUNUSED( 0x02, 0x02 ) - PORT_DIPUNUSED( 0x04, 0x04 ) - PORT_DIPUNUSED( 0x08, 0x08 ) - PORT_DIPNAME( 0x10, 0x10, "Cards" ) + PORT_DIPUNUSED_DIPLOC( 0x01, 0x01, "SW3:1" ) + PORT_DIPUNUSED_DIPLOC( 0x02, 0x02, "SW3:2" ) + PORT_DIPUNUSED_DIPLOC( 0x04, 0x04, "SW3:3" ) + PORT_DIPUNUSED_DIPLOC( 0x08, 0x08, "SW3:4" ) + PORT_DIPNAME( 0x10, 0x10, "Number Type" ) PORT_DIPLOCATION("SW3:5") PORT_DIPSETTING( 0x10, "A,J,Q,K" ) PORT_DIPSETTING( 0x00, "Number" ) - PORT_DIPUNUSED( 0x20, 0x20 ) - PORT_DIPUNUSED( 0x40, 0x40 ) - PORT_DIPNAME( 0x80, 0x80, "CG Select" ) + PORT_DIPUNUSED_DIPLOC( 0x20, 0x20, "SW3:6" ) + PORT_DIPUNUSED_DIPLOC( 0x40, 0x40, "SW3:7" ) + PORT_DIPNAME( 0x80, 0x80, "CG Select" ) PORT_DIPLOCATION("SW3:8") // Switches CG ROM (sprites). Unpopulated in this set PORT_DIPSETTING( 0x80, DEF_STR( Low ) ) PORT_DIPSETTING( 0x00, DEF_STR( High ) ) PORT_MODIFY("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START2 ) PORT_NAME( "Play / Last Bet / Toggle Gambling (8 Times)" ) // play current bet or, if null, bet as last time (2P C in test mode) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_DEAL ) PORT_NAME("Deal / Last Bet / Toggle Gambling (8 Times)") // play current bet or, if null, bet as last time (START2 in test mode) PORT_MODIFY("COINS") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // impulse prevents coin error in gambling mode PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) - // - PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME( "Start Gambling Toggle" ) // this starts toggling between videogame and gambling + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_SERVICE_NO_TOGGLE( 0x40, IP_ACTIVE_LOW ) // book-keeping after switching to gambling (TEST in test mode) + PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Start Gambling Toggle (Then Deal x 8)") // this starts toggling between videogame and gambling PORT_MODIFY("BUTTONS") - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) // (2P E in test mode) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) // (1P E in test mode) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) // (2P E in test mode) INPUT_PORTS_END static INPUT_PORTS_START( genius6 ) PORT_INCLUDE( iqblockf ) PORT_MODIFY("DSW1") - PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "Auto Hold" ) + PORT_DIPNAME( 0x02, 0x02, "Auto Hold" ) PORT_DIPLOCATION("SW1:2") PORT_DIPSETTING( 0x02, DEF_STR( No ) ) PORT_DIPSETTING( 0x00, DEF_STR( Yes ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Coin In" ) + PORT_DIPNAME( 0x0c, 0x0c, "Coin In" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "1" ) PORT_DIPSETTING( 0x08, "10" ) PORT_DIPSETTING( 0x04, "20" ) PORT_DIPSETTING( 0x00, "50" ) - PORT_DIPNAME( 0x30, 0x30, "Key In" ) + PORT_DIPNAME( 0x30, 0x30, "Key In" ) PORT_DIPLOCATION("SW1:5,6") PORT_DIPSETTING( 0x30, "10" ) PORT_DIPSETTING( 0x20, "100" ) PORT_DIPSETTING( 0x10, "200" ) PORT_DIPSETTING( 0x00, "500" ) - PORT_DIPNAME( 0xc0, 0xc0, "Min Bet" ) + PORT_DIPNAME( 0xc0, 0xc0, "Minimum Bet" ) PORT_DIPLOCATION("SW1:7,8") PORT_DIPSETTING( 0xc0, "1" ) PORT_DIPSETTING( 0x80, "2" ) PORT_DIPSETTING( 0x40, "5" ) PORT_DIPSETTING( 0x00, "10" ) PORT_MODIFY("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Max Bet" ) + PORT_DIPNAME( 0x03, 0x03, "Max Bet" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "5" ) PORT_DIPSETTING( 0x02, "10" ) PORT_DIPSETTING( 0x01, "20" ) PORT_DIPSETTING( 0x00, "50" ) - PORT_DIPUNUSED( 0x04, 0x04 ) - PORT_DIPNAME( 0x08, 0x08, "Key Out" ) + PORT_DIPUNUSED_DIPLOC( 0x04, 0x04, "SW2:3" ) + PORT_DIPNAME( 0x08, 0x08, "Key Out" ) PORT_DIPLOCATION("SW2:4") PORT_DIPSETTING( 0x08, "1" ) PORT_DIPSETTING( 0x00, "10" ) - PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) - PORT_DIPSETTING( 0x10, "Gaming" ) + PORT_DIPNAME( 0x10, 0x10, "Open Mode" ) PORT_DIPLOCATION("SW2:5") + PORT_DIPSETTING( 0x10, "Gaming (Gambling)" ) PORT_DIPSETTING( 0x00, "Amuse" ) - PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) + PORT_DIPNAME( 0x20, 0x00, "Demo Game" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPUNUSED( 0x40, 0x40 ) - PORT_DIPUNUSED( 0x80, 0x80 ) + PORT_DIPUNUSED_DIPLOC( 0x40, 0x40, "SW2:7" ) + PORT_DIPUNUSED_DIPLOC( 0x80, 0x80, "SW2:8" ) PORT_MODIFY("DSW3") - PORT_DIPUNUSED( 0x01, 0x01 ) - PORT_DIPUNUSED( 0x02, 0x02 ) - PORT_DIPUNUSED( 0x04, 0x04 ) - PORT_DIPUNUSED( 0x08, 0x08 ) - PORT_DIPNAME( 0x10, 0x10, "Cards" ) + PORT_DIPUNUSED_DIPLOC( 0x01, 0x01, "SW3:1" ) // the input test screen prints garbage when not all off + PORT_DIPUNUSED_DIPLOC( 0x02, 0x02, "SW3:2" ) // "" + PORT_DIPUNUSED_DIPLOC( 0x04, 0x04, "SW3:3" ) // "" + PORT_DIPUNUSED_DIPLOC( 0x08, 0x08, "SW3:4" ) // "" + PORT_DIPNAME( 0x10, 0x10, "Number Type" ) PORT_DIPLOCATION("SW3:5") PORT_DIPSETTING( 0x10, "A,J,Q,K" ) PORT_DIPSETTING( 0x00, "Number" ) - PORT_DIPUNUSED( 0x20, 0x20 ) - PORT_DIPUNUSED( 0x40, 0x40 ) - PORT_DIPUNUSED( 0x80, 0x80 ) + PORT_DIPUNUSED_DIPLOC( 0x20, 0x20, "SW3:6" ) + PORT_DIPUNUSED_DIPLOC( 0x40, 0x40, "SW3:7" ) + PORT_DIPUNUSED_DIPLOC( 0x80, 0x80, "SW3:8" ) PORT_MODIFY("PLAYER2") - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON5 ) PORT_NAME( "Hold 5" ) // (2P B in test mode) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD5 ) // (2P B in test mode) INPUT_PORTS_END static INPUT_PORTS_START( lhzb2 ) PORT_START("DSW1") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW1:1,2") PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) + PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "10" ) PORT_DIPSETTING( 0x08, "20" ) PORT_DIPSETTING( 0x04, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) + PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "1000" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) + PORT_DIPNAME( 0x20, 0x20, "Money Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) + PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x80, DEF_STR( On ) ) PORT_START("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "500" ) PORT_DIPSETTING( 0x02, "1000" ) PORT_DIPSETTING( 0x01, "1500" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0c, "1" ) - PORT_DIPSETTING( 0x08, "2" ) - PORT_DIPSETTING( 0x04, "3" ) - PORT_DIPSETTING( 0x00, "5" ) - PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) + PORT_DIPNAME( 0x0c, 0x0c, "Minimum Bet" ) PORT_DIPLOCATION("SW2:3,4") + PORT_DIPSETTING( 0x0c, "1 (1)" ) + PORT_DIPSETTING( 0x08, "1 (2)" ) + PORT_DIPSETTING( 0x04, "1 (3)" ) + PORT_DIPSETTING( 0x00, "1 (4)" ) + PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) PORT_DIPLOCATION("SW2:5") PORT_DIPSETTING( 0x00, DEF_STR( No ) ) PORT_DIPSETTING( 0x10, DEF_STR( Yes ) ) - PORT_DIPNAME( 0x20, 0x20, "Number Type" ) + PORT_DIPNAME( 0x20, 0x20, "Number Type" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, "Number" ) PORT_DIPSETTING( 0x00, "Dice" ) - PORT_DIPNAME( 0x40, 0x40, "Symbols" ) + PORT_DIPNAME( 0x40, 0x40, "Symbols" ) PORT_DIPLOCATION("SW2:7") PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) // pigs, apples - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) // pigs, apples + PORT_DIPNAME( 0x80, 0x80, "Hide Gambling" ) PORT_DIPLOCATION("SW2:8") // press "Hide Gambling" to hide credits and bets PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_CUSTOM ) // hopper switch (unimplemented) - PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // service mode (keep pressed during boot too) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") // press with the above for sound test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_SERVICE3 ) // ? (shown in service mode) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // test mode (keep pressed during boot too) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // press with the above for sound test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("KEY0") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) @@ -2836,175 +3219,94 @@ static INPUT_PORTS_START( lhzb2 ) INPUT_PORTS_END static INPUT_PORTS_START( lhzb2a ) - PORT_START("DSW1") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) - PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) - PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) - PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) - PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) - PORT_DIPSETTING( 0x0c, "10" ) - PORT_DIPSETTING( 0x08, "20" ) - PORT_DIPSETTING( 0x04, "50" ) - PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) - PORT_DIPSETTING( 0x10, "1000" ) - PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) - PORT_DIPSETTING( 0x20, "Coins" ) - PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) - PORT_DIPSETTING( 0x40, "Coins" ) - PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) - PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x80, DEF_STR( On ) ) + PORT_INCLUDE( lhzb2 ) - PORT_START("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) - PORT_DIPSETTING( 0x03, "500" ) - PORT_DIPSETTING( 0x02, "1000" ) - PORT_DIPSETTING( 0x01, "1500" ) - PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0c, "1" ) - PORT_DIPSETTING( 0x08, "2" ) - PORT_DIPSETTING( 0x04, "3" ) - PORT_DIPSETTING( 0x00, "5" ) - PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) - PORT_DIPSETTING( 0x00, DEF_STR( No ) ) - PORT_DIPSETTING( 0x10, DEF_STR( Yes ) ) - PORT_DIPNAME( 0x20, 0x20, "Number Type" ) - PORT_DIPSETTING( 0x20, "Number" ) - PORT_DIPSETTING( 0x00, "Dice" ) - PORT_DIPNAME( 0x40, 0x40, "Symbols" ) - PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) // pigs, apples - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - - PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_CUSTOM ) // hopper switch - PORT_SERVICE_NO_TOGGLE( 0x04, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") // press with the above for sound test - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_SERVICE3 ) // shown in test mode - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - - PORT_START("KEY0") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - - PORT_START("KEY1") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_B ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_F ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_J ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_N ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_REACH ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_MAHJONG_BET ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - - PORT_START("KEY2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_C ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_G ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_K ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_CHI ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_RON ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - - PORT_START("KEY3") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_D ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_H ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_L ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_PON ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - - PORT_START("KEY4") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_LAST_CHANCE ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_SCORE ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_DOUBLE_UP ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_BIG ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_MAHJONG_SMALL ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_MODIFY("COINS") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x04, IP_ACTIVE_LOW ) // keep pressed while booting + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // press with the above for sound test + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) INPUT_PORTS_END static INPUT_PORTS_START( mgcs ) - // DSWs are read through a protection device (IGS029). See code at 1CF16 + // DSWs are read through a protection device (IGS029). See code at $1cf16 - PORT_START("DSW1") // $3009e2 - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) + PORT_START("DSW1") // $3009e2 + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW1:1,2") PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) + PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "10" ) PORT_DIPSETTING( 0x08, "20" ) PORT_DIPSETTING( 0x04, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) + PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "500" ) PORT_DIPSETTING( 0x00, "1000" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) + PORT_DIPNAME( 0x20, 0x20, "Money Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) + PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, "Double Up Limit" ) + PORT_DIPNAME( 0x80, 0x80, "Double Up Limit" ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x80, "1000" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_START("DSW2") // $3009e3 - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) + PORT_START("DSW2") // $3009e3 + PORT_DIPNAME( 0x03, 0x03, "Minimum Bet" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "1" ) PORT_DIPSETTING( 0x02, "2" ) PORT_DIPSETTING( 0x01, "3" ) PORT_DIPSETTING( 0x00, "5" ) - PORT_DIPNAME( 0x04, 0x04, "Double Up" ) + PORT_DIPNAME( 0x04, 0x04, "Double Up" ) PORT_DIPLOCATION("SW2:3") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x04, DEF_STR( On ) ) - PORT_DIPNAME( 0x10, 0x10, DEF_STR( Controls ) ) + PORT_DIPNAME( 0x08, 0x08, "Continue To Play" ) PORT_DIPLOCATION("SW2:4") + PORT_DIPSETTING( 0x08, DEF_STR( Yes ) ) + PORT_DIPSETTING( 0x00, DEF_STR( No ) ) + PORT_DIPNAME( 0x10, 0x10, DEF_STR( Controls ) ) PORT_DIPLOCATION("SW2:5") PORT_DIPSETTING( 0x10, "Keyboard" ) PORT_DIPSETTING( 0x00, DEF_STR( Joystick ) ) - PORT_DIPNAME( 0x20, 0x20, "Number Type" ) + PORT_DIPNAME( 0x20, 0x20, "Number Type" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, "Number" ) PORT_DIPSETTING( 0x00, "Tile" ) - PORT_DIPNAME( 0x40, 0x40, "Double Up Type" ) - PORT_DIPSETTING( 0x40, "Double" ) - PORT_DIPSETTING( 0x00, DEF_STR( Single ) ) - PORT_DIPNAME( 0x80, 0x80, "Bet Number" ) - PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x80, DEF_STR( On ) ) + PORT_DIPNAME( 0x40, 0x40, "Hide Gambling" ) PORT_DIPLOCATION("SW2:7") // press "Hide Gambling" to hide credits and bets + PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPUNUSED_DIPLOC( 0x80, 0x80, "SW2:8" ) - // the top 2 bits of COINS (port A) and KEYx (port B) are read and combined with the bottom 4 bits read from port C (see code at 1C83A) + // Joystick mode: the top 2 bits of COINS (i8255 port A) and JOY (i8255 port B) are read and combined with the bottom 4 bits read from port C (see code at $1c83a) + + PORT_START("JOY") + // Joystick mode: + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON1 ) // take tile or throw (as N in mahjong keyboard) + // i8255 port C input is 4 bits + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_START1 ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", ticket_dispenser_device, line_r) // hopper switch - PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // service mode (keep pressed during boot too) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") // press with the above for sound test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_SERVICE3 ) // ? must be high to display numbers (shown in service mode) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // test mode (keep pressed during boot too) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // press with the above for sound test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除) + // Keyboard mode: + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x10,EQUALS,0x10) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x10,EQUALS,0x10) + // Joystick mode: + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_CONDITION("DSW2",0x10,EQUALS,0x00) // bet + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_CONDITION("DSW2",0x10,EQUALS,0x00) // function PORT_START("KEY0") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) @@ -3059,87 +3361,85 @@ INPUT_PORTS_END static INPUT_PORTS_START( sdmg2 ) PORT_START("DSW1") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW1:1,2") PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) + PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "10" ) PORT_DIPSETTING( 0x08, "20" ) PORT_DIPSETTING( 0x04, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) + PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "2000" ) PORT_DIPSETTING( 0x00, "29999" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) + PORT_DIPNAME( 0x20, 0x20, "Money Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) + PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x80, DEF_STR( On ) ) PORT_START("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) + PORT_DIPNAME( 0x03, 0x03, "Minimum Bet" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "500" ) PORT_DIPSETTING( 0x02, "1000" ) PORT_DIPSETTING( 0x01, "1500" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:3,4") PORT_DIPSETTING( 0x0c, "1" ) PORT_DIPSETTING( 0x08, "2" ) PORT_DIPSETTING( 0x04, "3" ) PORT_DIPSETTING( 0x00, "5" ) - PORT_DIPNAME( 0x10, 0x10, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x10, 0x10, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:5") PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x20, 0x20, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x20, 0x20, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x40, 0x40, DEF_STR( Controls ) ) + PORT_DIPNAME( 0x40, 0x40, DEF_STR( Controls ) ) PORT_DIPLOCATION("SW2:7") PORT_DIPSETTING( 0x40, "Keyboard" ) PORT_DIPSETTING( 0x00, DEF_STR( Joystick ) ) - PORT_DIPNAME( 0x80, 0x80, "Number Type" ) + PORT_DIPNAME( 0x80, 0x80, "Number Type" ) PORT_DIPLOCATION("SW2:8") PORT_DIPSETTING( 0x80, "Number" ) PORT_DIPSETTING( 0x00, "Tile" ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) // hopper switch - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_SERVICE2 ) // shown in test mode - PORT_SERVICE_NO_TOGGLE( 0x04, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN1 ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除), does not work in game? + PORT_SERVICE_NO_TOGGLE( 0x04, IP_ACTIVE_LOW ) // keep pressed while booting + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN1 ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) // Keyboard mode: - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_SERVICE3 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) // shown in test mode + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_SERVICE3 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) // shown in test mode ('O' appears, or it might be a 0) // Joystick mode: - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_START("JOY") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // related to joystick BUTTON3 PORT_START("KEY0") - // Keyboard mode: - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x40,EQUALS,0x40) - // Joystick mode: - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x40,EQUALS,0x00) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("KEY1") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_B ) @@ -3184,45 +3484,45 @@ INPUT_PORTS_END static INPUT_PORTS_START( mgdh ) PORT_START("DSW1") - PORT_DIPNAME( 0x01, 0x01, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x06, 0x06, "Credits Per Note" ) + PORT_DIPNAME( 0x06, 0x06, "Credits Per Note" ) PORT_DIPLOCATION("SW1:2,3") PORT_DIPSETTING( 0x06, "5" ) PORT_DIPSETTING( 0x04, "10" ) PORT_DIPSETTING( 0x02, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x08, 0x08, "Max Note Credits" ) + PORT_DIPNAME( 0x08, 0x08, "Max Note Credits" ) PORT_DIPLOCATION("SW1:4") PORT_DIPSETTING( 0x08, "100" ) PORT_DIPSETTING( 0x00, "500" ) - PORT_DIPNAME( 0x10, 0x10, "Money Type" ) + PORT_DIPNAME( 0x10, 0x10, "Money Type" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x20, 0x20, "Pay Out Type" ) + PORT_DIPNAME( 0x20, 0x20, "Pay Out Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0xc0, 0xc0, "Min Bet" ) + PORT_DIPNAME( 0xc0, 0xc0, "Minimum Bet" ) PORT_DIPLOCATION("SW1:7,8") PORT_DIPSETTING( 0xc0, "1" ) PORT_DIPSETTING( 0x80, "2" ) PORT_DIPSETTING( 0x40, "3" ) PORT_DIPSETTING( 0x00, "5" ) - PORT_START("DSW2") // bitswapped - PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) + PORT_START("DSW2") // bitswapped + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW2:1") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x01, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, DEF_STR( Controls ) ) + PORT_DIPNAME( 0x02, 0x02, DEF_STR( Controls ) ) PORT_DIPLOCATION("SW2:2") PORT_DIPSETTING( 0x02, "Keyboard" ) PORT_DIPSETTING( 0x00, DEF_STR( Joystick ) ) - PORT_DIPNAME( 0x04, 0x04, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x18, 0x18, DEF_STR( Coinage ) ) + PORT_DIPNAME( 0x04, 0x04, "Continue To Play" ) PORT_DIPLOCATION("SW2:3") + PORT_DIPSETTING( 0x04, DEF_STR( Yes ) ) + PORT_DIPSETTING( 0x00, DEF_STR( No ) ) + PORT_DIPNAME( 0x18, 0x18, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW2:4,5") PORT_DIPSETTING( 0x00, DEF_STR( 2C_1C ) ) PORT_DIPSETTING( 0x18, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x10, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x08, DEF_STR( 1C_3C ) ) - PORT_DIPNAME( 0xe0, 0xe0, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0xe0, 0xe0, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:6,7,8") PORT_DIPSETTING( 0xe0, "1" ) PORT_DIPSETTING( 0xc0, "2" ) PORT_DIPSETTING( 0xa0, "5" ) @@ -3233,34 +3533,34 @@ static INPUT_PORTS_START( mgdh ) PORT_DIPSETTING( 0x00, "10" ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) // hopper switch - PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // service mode (keep pressed during boot too) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") // press with the above for sound test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_SERVICE3 ) // ? (shown in service mode) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // test mode (keep pressed during boot too) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // press with the above for sound test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除), does not work in game? + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("KEY0") // Keyboard mode: - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x02) // Joystick mode: - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW2",0x02,EQUALS,0x00) PORT_START("KEY1") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_B ) @@ -3315,62 +3615,62 @@ INPUT_PORTS_END static INPUT_PORTS_START( slqz2 ) PORT_START("DSW1") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW1:1,2") PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) + PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "10" ) PORT_DIPSETTING( 0x08, "20" ) PORT_DIPSETTING( 0x04, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) + PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "1000" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) + PORT_DIPNAME( 0x20, 0x20, "Money Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) + PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x80, DEF_STR( On ) ) PORT_START("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) + PORT_DIPNAME( 0x03, 0x03, "Double Up Limit" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "500" ) PORT_DIPSETTING( 0x02, "1000" ) PORT_DIPSETTING( 0x01, "1500" ) PORT_DIPSETTING( 0x00, "2000" ) - PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x0c, 0x0c, "Minimum Bet" ) PORT_DIPLOCATION("SW2:3,4") PORT_DIPSETTING( 0x0c, "1" ) PORT_DIPSETTING( 0x08, "2" ) PORT_DIPSETTING( 0x04, "3" ) PORT_DIPSETTING( 0x00, "5" ) - PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) + PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) PORT_DIPLOCATION("SW2:5") PORT_DIPSETTING( 0x00, DEF_STR( No ) ) PORT_DIPSETTING( 0x10, DEF_STR( Yes ) ) - PORT_DIPNAME( 0x20, 0x20, "Number Type" ) + PORT_DIPNAME( 0x20, 0x20, "Number Type" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, "Number" ) PORT_DIPSETTING( 0x00, "Dice" ) - PORT_DIPNAME( 0x40, 0x40, "Symbols" ) + PORT_DIPNAME( 0x40, 0x40, "Symbols" ) PORT_DIPLOCATION("SW2:7") PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) // pigs, apples - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) // pigs, apples + PORT_DIPNAME( 0x80, 0x80, "Hide Gambling" ) PORT_DIPLOCATION("SW2:8") // press "Hide Gambling" to hide credits and bets PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_CUSTOM ) // hopper switch (unimplemented) - PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // service mode (keep pressed during boot too) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") // press with the above for sound test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON3 ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // test mode (keep pressed during boot too) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // press with the above for sound test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin error otherwise + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_UNKNOWN ) // needs to be 0 for "clear" input below to work + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_START("PLAYER1") PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_NAME("Start / Don Den") @@ -3378,82 +3678,72 @@ static INPUT_PORTS_START( slqz2 ) PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "Help / Big" ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME("Help / Big") PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START2 ) PORT_NAME( "Bet" ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_PLAYER(2) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_PLAYER(2) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_PLAYER(2) - - PORT_START("BUTTONS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_1_PAD) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_2_PAD) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_3_PAD) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_4_PAD) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_5_PAD) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_6_PAD) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_7_PAD) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("0") PORT_CODE(KEYCODE_8_PAD) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) INPUT_PORTS_END static INPUT_PORTS_START( tjsb ) PORT_START("DSW1") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("SW1:1,2") PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) PORT_DIPSETTING( 0x02, DEF_STR( 1C_2C ) ) PORT_DIPSETTING( 0x01, DEF_STR( 1C_3C ) ) PORT_DIPSETTING( 0x00, DEF_STR( 1C_5C ) ) - PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) + PORT_DIPNAME( 0x0c, 0x0c, "Credits Per Note" ) PORT_DIPLOCATION("SW1:3,4") PORT_DIPSETTING( 0x0c, "10" ) PORT_DIPSETTING( 0x08, "20" ) PORT_DIPSETTING( 0x04, "50" ) PORT_DIPSETTING( 0x00, "100" ) - PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) + PORT_DIPNAME( 0x10, 0x10, "Max Note Credits" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "1000" ) PORT_DIPSETTING( 0x00, "5000" ) - PORT_DIPNAME( 0x20, 0x20, "Money Type" ) + PORT_DIPNAME( 0x20, 0x20, "Money Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) // 2/4 + PORT_DIPNAME( 0x40, 0x40, "Pay Out Type" ) PORT_DIPLOCATION("SW1:7") // 2/4 PORT_DIPSETTING( 0x40, "Coins" ) PORT_DIPSETTING( 0x00, "Notes" ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) PORT_DIPSETTING( 0x80, DEF_STR( On ) ) PORT_START("DSW2") - PORT_DIPNAME( 0x03, 0x03, "Min Bet" ) + PORT_DIPNAME( 0x03, 0x03, "Minimum Bet" ) PORT_DIPLOCATION("SW2:1,2") PORT_DIPSETTING( 0x03, "1000" ) PORT_DIPSETTING( 0x02, "2000" ) PORT_DIPSETTING( 0x01, "3000" ) PORT_DIPSETTING( 0x00, "4000" ) - PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x0c, 0x0c, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:3,4") PORT_DIPSETTING( 0x0c, "1" ) PORT_DIPSETTING( 0x08, "3" ) PORT_DIPSETTING( 0x04, "5" ) PORT_DIPSETTING( 0x00, "10" ) - PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) // show bonus round in demo mode -> protection check + PORT_DIPNAME( 0x10, 0x10, "Bonus Round" ) PORT_DIPLOCATION("SW2:5") // show bonus round in demo mode -> protection check PORT_DIPSETTING( 0x00, DEF_STR( No ) ) PORT_DIPSETTING( 0x10, DEF_STR( Yes ) ) - PORT_DIPNAME( 0x20, 0x20, "Number Type" ) + PORT_DIPNAME( 0x20, 0x20, "Number Type" ) PORT_DIPLOCATION("SW2:6") PORT_DIPSETTING( 0x20, "Number" ) PORT_DIPSETTING( 0x00, "Dice" ) - PORT_DIPNAME( 0x40, 0x40, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x40, 0x40, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:7") PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) PORT_DIPLOCATION("SW2:8") PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_START("DSW3") // check: (val^ff) & 9a == 0a - PORT_DIPNAME( 0xff, 0xf5, "Bonus Round Protection Check" ) + PORT_START("DSW3") // the protection check is skipped if (DSW3 ^ 0xff) & 0x9a == 0x0a + PORT_DIPNAME( 0xff, 0xf5, "Bonus Round Protection Check" ) PORT_DIPLOCATION("SW3:1,2,3,4,5,6,7,8") PORT_DIPSETTING( 0xf5, DEF_STR( Off ) ) PORT_DIPSETTING( 0xff, DEF_STR( On ) ) @@ -3478,141 +3768,299 @@ static INPUT_PORTS_START( tjsb ) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Statistics") - PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_COIN1 ) + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // keep pressed while booting + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_COIN1 ) - PORT_START("HOPPER") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON3 ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) // ? shown in test mode - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_START("BUTTONS") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON3 ) + PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除), does not work in game? + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) +INPUT_PORTS_END + +static INPUT_PORTS_START( spkrform ) + PORT_START("DSW1") + PORT_DIPNAME( 0x01, 0x00, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") + PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPUNKNOWN_DIPLOC( 0x02, 0x02, "SW1:2" ) + PORT_DIPNAME( 0x01c, 0x1c, "Credits Per Coin" ) PORT_DIPLOCATION("SW1:3,4,5") + PORT_DIPSETTING( 0x1c, "1" ) + PORT_DIPSETTING( 0x18, "4" ) + PORT_DIPSETTING( 0x14, "5" ) + PORT_DIPSETTING( 0x10, "10" ) + PORT_DIPSETTING( 0x0c, "20" ) + PORT_DIPSETTING( 0x08, "40" ) + PORT_DIPSETTING( 0x04, "50" ) + PORT_DIPSETTING( 0x00, "100" ) + PORT_DIPNAME( 0x20, 0x20, "Hopper" ) PORT_DIPLOCATION("SW1:6") + PORT_DIPSETTING( 0x20, DEF_STR( No ) ) + PORT_DIPSETTING( 0x00, DEF_STR( Yes ) ) + PORT_DIPUNKNOWN_DIPLOC( 0x40, 0x40, "SW1:7" ) + PORT_DIPUNKNOWN_DIPLOC( 0x80, 0x80, "SW1:8" ) + + PORT_START("DSW2") + PORT_DIPNAME( 0x03, 0x03, "Minimum Bet" ) PORT_DIPLOCATION("SW2:1,2") + PORT_DIPSETTING( 0x03, "1" ) + PORT_DIPSETTING( 0x02, "5" ) + PORT_DIPSETTING( 0x01, "10" ) + PORT_DIPSETTING( 0x00, "20" ) + PORT_DIPNAME( 0x1c, 0x1c, "Credits Per Note" ) PORT_DIPLOCATION("SW2:3,4,5") + PORT_DIPSETTING( 0x1c, "10" ) + PORT_DIPSETTING( 0x18, "20" ) + PORT_DIPSETTING( 0x14, "40" ) + PORT_DIPSETTING( 0x10, "50" ) + PORT_DIPSETTING( 0x0c, "100" ) + PORT_DIPSETTING( 0x08, "200" ) + PORT_DIPSETTING( 0x04, "250" ) + PORT_DIPSETTING( 0x00, "500" ) + PORT_DIPUNKNOWN_DIPLOC( 0x20, 0x20, "SW2:6" ) + PORT_DIPUNKNOWN_DIPLOC( 0x40, 0x40, "SW2:7" ) + PORT_DIPUNKNOWN_DIPLOC( 0x80, 0x80, "SW2:8" ) + + PORT_START("DSW3") + PORT_DIPNAME( 0x03, 0x03, "?" ) PORT_DIPLOCATION("SW3:1,2") + PORT_DIPSETTING( 0x03, "100" ) + PORT_DIPSETTING( 0x02, "200" ) + PORT_DIPSETTING( 0x01, "300" ) + PORT_DIPSETTING( 0x00, "400" ) + PORT_DIPNAME( 0x0c, 0x0c, "Win Up Pool" ) PORT_DIPLOCATION("SW3:3,4") + PORT_DIPSETTING( 0x0c, "300" ) + PORT_DIPSETTING( 0x08, "500" ) + PORT_DIPSETTING( 0x04, "800 (1)" ) + PORT_DIPSETTING( 0x00, "800 (2)" ) + PORT_DIPUNKNOWN_DIPLOC( 0x10, 0x10, "SW3:5" ) + PORT_DIPUNKNOWN_DIPLOC( 0x20, 0x20, "SW3:6" ) + PORT_DIPUNKNOWN_DIPLOC( 0x40, 0x40, "SW3:7" ) + PORT_DIPUNKNOWN_DIPLOC( 0x80, 0x80, "SW3:8" ) + + PORT_START("PLAYER1") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SERVICE1 ) PORT_NAME("Hide Gambling (Switch To Formosa)") + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_START2 ) PORT_NAME("Start (Formosa)") + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) // up (Formosa) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_START ) PORT_NAME("Start / Draw / Take / %p Down (Formosa)") + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("PLAYER2") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_POKER_HOLD4 ) PORT_NAME("Hold 4 / Half") + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_POKER_HOLD5 ) // hold 5 + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_BET ) PORT_NAME("Bet / W-Up") + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) // right (Formosa) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_POKER_HOLD1 ) PORT_NAME("Hold 1 / High / Button (Formosa)") + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD2 ) PORT_NAME("Hold 2 / Double Up") + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("COINS") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) // left (Formosa) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_POKER_HOLD3 ) PORT_NAME("Hold 3 / Low") + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) // key in + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) // key out + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("BUTTONS") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // coin 1 (impulse prevents coin error in gambling mode) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // coin 2 "" + PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) // payout + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_SERVICE3 ) PORT_NAME("Return To Gambling (From Formosa). Then Bet, Hold 1..5") // To switch back to poker from Formosa, start the sequence pressing this key (memory $f4a3 holds the sequence number) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // book + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) +INPUT_PORTS_END + +static INPUT_PORTS_START( tarzan ) + PORT_START("DSW1") + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") + PORT_DIPSETTING( 0x00, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x01, DEF_STR( On ) ) + PORT_DIPNAME( 0x0e, 0x0e, "Coin Value" ) PORT_DIPLOCATION("SW1:2,3,4") + PORT_DIPSETTING( 0x0e, "1" ) + PORT_DIPSETTING( 0x0c, "2" ) + PORT_DIPSETTING( 0x0a, "4" ) + PORT_DIPSETTING( 0x08, "5" ) + PORT_DIPSETTING( 0x06, "10" ) + PORT_DIPSETTING( 0x04, "20" ) + PORT_DIPSETTING( 0x02, "50" ) + PORT_DIPSETTING( 0x00, "100" ) + PORT_DIPNAME( 0x30, 0x30, "Key Value" ) PORT_DIPLOCATION("SW1:5,6") + PORT_DIPSETTING( 0x30, "100" ) + PORT_DIPSETTING( 0x20, "200" ) + PORT_DIPSETTING( 0x10, "500" ) + PORT_DIPSETTING( 0x00, "1000" ) + PORT_DIPNAME( 0xc0, 0xc0, "Point Value" ) PORT_DIPLOCATION("SW1:7,8") + PORT_DIPSETTING( 0xc0, "1" ) + PORT_DIPSETTING( 0x80, "10" ) + PORT_DIPSETTING( 0x40, "100" ) + PORT_DIPSETTING( 0x00, "100 (2)" ) + + PORT_START("DSW2") + PORT_DIPNAME( 0x01, 0x01, "Coin Type" ) PORT_DIPLOCATION("SW2:1") + PORT_DIPSETTING( 0x01, "Coin" ) + PORT_DIPSETTING( 0x00, "Key" ) + PORT_DIPNAME( 0x0e, 0x0e, "Minimum Bet" ) PORT_DIPLOCATION("SW2:2,3,4") + PORT_DIPSETTING( 0x0e, "5" ) + PORT_DIPSETTING( 0x0c, "25" ) + PORT_DIPSETTING( 0x0a, "50" ) + PORT_DIPSETTING( 0x08, "75" ) + PORT_DIPSETTING( 0x06, "100" ) + PORT_DIPSETTING( 0x04, "125" ) + PORT_DIPSETTING( 0x02, "125 (2)" ) + PORT_DIPSETTING( 0x00, "125 (3)" ) + PORT_DIPNAME( 0x30, 0x30, "Bonus Bet" ) PORT_DIPLOCATION("SW2:5,6") + PORT_DIPSETTING( 0x30, "75" ) + PORT_DIPSETTING( 0x20, "125" ) + PORT_DIPSETTING( 0x10, "200" ) + PORT_DIPSETTING( 0x00, "250" ) + PORT_DIPNAME( 0xc0, 0xc0, "Continue To Play" ) PORT_DIPLOCATION("SW2:7,8") + PORT_DIPSETTING( 0xc0, "50k" ) + PORT_DIPSETTING( 0x80, "100k" ) + PORT_DIPSETTING( 0x40, "150k" ) + PORT_DIPSETTING( 0x00, "200k" ) + + PORT_START("DSW3") + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Controls ) ) PORT_DIPLOCATION("SW3:1") + PORT_DIPSETTING( 0x01, "Keyboard" ) + PORT_DIPSETTING( 0x00, DEF_STR( Joystick ) ) + PORT_DIPNAME( 0x02, 0x00, "Back Color" ) PORT_DIPLOCATION("SW3:2") + PORT_DIPSETTING( 0x02, "Black" ) + PORT_DIPSETTING( 0x00, "Color" ) + PORT_DIPNAME( 0x04, 0x04, "Hide Gambling" ) PORT_DIPLOCATION("SW3:3") // Press "Hide Gambling" to hide credits and bets + PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x08, 0x08, "Number Type" ) PORT_DIPLOCATION("SW3:4") + PORT_DIPSETTING( 0x08, "Number" ) + PORT_DIPSETTING( 0x00, "Mahjong Tile" ) + PORT_DIPNAME( 0x10, 0x10, "Continue To Play" ) PORT_DIPLOCATION("SW3:5") + PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x20, 0x20, "Payout" ) PORT_DIPLOCATION("SW3:6") + PORT_DIPSETTING( 0x20, "Hopper" ) + PORT_DIPSETTING( 0x00, "Points" ) + PORT_DIPUNUSED_DIPLOC(0x40, 0x40, "SW3:7") + PORT_DIPUNUSED_DIPLOC(0x80, 0x80, "SW3:8") + + PORT_START("COINS") + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_SERVICE_NO_TOGGLE( 0x02, IP_ACTIVE_LOW ) // Service + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // Book + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // Coin/Key in (coin error in coin mode) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) // Coin/Key out + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_SERVICE1 ) PORT_NAME("Hide Gambling") // shown in test mode as "clear" (清除) + // Keyboard mode: + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW3",0x01,EQUALS,0x01) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_CONDITION("DSW3",0x01,EQUALS,0x01) + // Joystick mode: + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_CONDITION("DSW3",0x01,EQUALS,0x00) PORT_NAME("%p Button 2 / Bet / Same Double Up" ) // Button B (test mode) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_CONDITION("DSW3",0x01,EQUALS,0x00) PORT_NAME("%p Button 3 / Small / Half Double Up") // Button C (test mode) + + PORT_START("JOY") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) PORT_NAME("Start / Take") // Exit (test mode) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) // Up (test mode) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) // Down (test mode) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) // Left (test mode) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) // Right (test mode) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME("%p Button 1 / Help / Big / Double Up") // Button A (test mode) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("KEY0") + // Keyboard mode: + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_A ) PORT_NAME("%p Mahjong A / Help / Double Up") + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_E ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_I ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_M ) PORT_NAME("%p Mahjong M / Small") + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_KAN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START ) PORT_NAME("%p Mahjong Start / Take") + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("KEY1") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_B ) // B (test mode) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_F ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_J ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_N ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_REACH ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_MAHJONG_BET ) // Bet + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("KEY2") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_C ) PORT_NAME("%p Mahjong C / Half Double Up") + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_G ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_K ) PORT_NAME("%p Mahjong K / Big") + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_CHI ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_RON ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("KEY3") + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_D ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_H ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_L ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_MAHJONG_PON ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) + + PORT_START("KEY4") // never read and not shown in test mode + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_MAHJONG_LAST_CHANCE ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_MAHJONG_SCORE ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_MAHJONG_DOUBLE_UP ) PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("Pay Out") PORT_CODE(KEYCODE_O) - PORT_BIT( 0x20, IP_ACTIVE_HIGH,IPT_CUSTOM ) // hopper switch + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_MAHJONG_BIG ) + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_MAHJONG_SMALL ) PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) INPUT_PORTS_END -// to do: -static INPUT_PORTS_START( spkrform ) - PORT_START("DSW1") - PORT_DIPUNKNOWN( 0x01, 0x01 ) - PORT_DIPUNKNOWN( 0x02, 0x02 ) - PORT_DIPUNKNOWN( 0x04, 0x04 ) - PORT_DIPUNKNOWN( 0x08, 0x08 ) - PORT_DIPUNKNOWN( 0x10, 0x10 ) - PORT_DIPUNKNOWN( 0x20, 0x20 ) - PORT_DIPUNKNOWN( 0x40, 0x40 ) - PORT_DIPUNKNOWN( 0x80, 0x80 ) - - PORT_START("DSW2") - PORT_DIPUNKNOWN( 0x01, 0x01 ) - PORT_DIPUNKNOWN( 0x02, 0x02 ) - PORT_DIPUNKNOWN( 0x04, 0x04 ) - PORT_DIPUNKNOWN( 0x08, 0x08 ) - PORT_DIPUNKNOWN( 0x10, 0x10 ) - PORT_DIPUNKNOWN( 0x20, 0x20 ) - PORT_DIPUNKNOWN( 0x40, 0x40 ) - PORT_DIPUNKNOWN( 0x80, 0x80 ) - - PORT_START("DSW3") - PORT_DIPNAME( 0x03, 0x03, "Win Up Pool" ) - PORT_DIPSETTING( 0x03, "300" ) - PORT_DIPSETTING( 0x02, "500" ) - PORT_DIPSETTING( 0x01, "800" ) - PORT_DIPSETTING( 0x00, "800" ) - PORT_DIPUNKNOWN( 0x04, 0x04 ) - PORT_DIPUNKNOWN( 0x08, 0x08 ) - PORT_DIPUNKNOWN( 0x10, 0x10 ) - PORT_DIPUNKNOWN( 0x20, 0x20 ) - PORT_DIPUNKNOWN( 0x40, 0x40 ) - PORT_DIPUNKNOWN( 0x80, 0x80 ) - - PORT_START("PLAYER1") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) // ?? exit poker - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON1 ) // start (formosa) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON2 ) // up - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON3 ) // down / start - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON4 ) - - PORT_START("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_PLAYER(2) // right / bet - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_PLAYER(2) // button1 / hold1 - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_BUTTON3 ) PORT_PLAYER(2) // hold2 - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_BUTTON4 ) PORT_PLAYER(2) - - PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_START1 ) // left - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_START2 ) // hold3 - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_START3 ) // credit in - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_START4 ) // credit out - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_COIN1 ) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_COIN2 ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_COIN3 ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_COIN4 ) - - PORT_START("BUTTONS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SERVICE1 ) // coin (coin error) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_SERVICE2 ) // coin (coin error) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SERVICE3 ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_SERVICE4 ) // hopper error - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("1") PORT_CODE(KEYCODE_1_PAD) - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("2") PORT_CODE(KEYCODE_2_PAD) // record - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("3") PORT_CODE(KEYCODE_3_PAD) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_OTHER ) PORT_NAME("4") PORT_CODE(KEYCODE_4_PAD) - - PORT_START("A000") - PORT_DIPNAME( 0xff, 0xff, "A000" ) - PORT_DIPSETTING( 0xff, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - - PORT_START("A001") - PORT_DIPNAME( 0xff, 0xff, "A001" ) - PORT_DIPSETTING( 0xff, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) -INPUT_PORTS_END - static INPUT_PORTS_START( starzan ) PORT_START("DSW1") - PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") + PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") PORT_DIPSETTING( 0x02, "Unlimited" ) PORT_DIPSETTING( 0x00, "Limited" ) - PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") + PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x08, 0x08, "Back Color" ) PORT_DIPLOCATION("SW1:4") + PORT_DIPNAME( 0x08, 0x00, "Back Color" ) PORT_DIPLOCATION("SW1:4") PORT_DIPSETTING( 0x08, "Black" ) PORT_DIPSETTING( 0x00, "Color" ) - PORT_DIPNAME( 0x10, 0x10, "Stop Status" ) PORT_DIPLOCATION("SW1:5") + PORT_DIPNAME( 0x10, 0x10, "Stop Status" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, "Non Stop" ) PORT_DIPSETTING( 0x00, "Auto Stop" ) - PORT_DIPNAME( 0x20, 0x20, "Key" ) PORT_DIPLOCATION("SW1:6") + PORT_DIPNAME( 0x20, 0x20, "Key" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Mode 1" ) - PORT_DIPSETTING( 0x00, "Mode 2" ) - PORT_DIPNAME( 0x40, 0x40, "Credit Level" ) PORT_DIPLOCATION("SW1:7") + PORT_DIPSETTING( 0x00, "Mode 2" ) // To Do + PORT_DIPNAME( 0x40, 0x40, "Credit Level" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, "Odds Table" ) PORT_DIPLOCATION("SW1:8") + PORT_DIPNAME( 0x80, 0x80, "Odds Table" ) PORT_DIPLOCATION("SW1:8") PORT_DIPSETTING( 0x80, "Show" ) PORT_DIPSETTING( 0x00, "No Show" ) PORT_START("DSW2") - PORT_DIPNAME( 0x01, 0x01, "Normal Level" ) PORT_DIPLOCATION("SW2:1") + PORT_DIPNAME( 0x01, 0x01, "Normal Level" ) PORT_DIPLOCATION("SW2:1") PORT_DIPSETTING( 0x01, DEF_STR( Low ) ) PORT_DIPSETTING( 0x00, DEF_STR( High ) ) PORT_DIPUNUSED_DIPLOC(0x02, 0x02, "SW2:2") // not used from here on according to test mode, PCB does have 3 8-dip banks @@ -3634,97 +4082,94 @@ static INPUT_PORTS_START( starzan ) PORT_DIPUNUSED_DIPLOC(0x80, 0x80, "SW3:8") PORT_START("PLAYER1") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "HP SW" ) // called like this in key test, not clear what it does - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_SLOT_STOP3 ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_SLOT_STOP_ALL ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) PORT_NAME("Start / HW-Up") + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_SLOT_STOP3 ) PORT_NAME("Stop Reel 3 / Low") + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_SLOT_STOP_ALL ) PORT_NAME("Stop All Reels / Bet / 2W-Up") PORT_START("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SLOT_STOP2 ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_SLOT_STOP4 ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SLOT_STOP1 ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_SLOT_STOP2 ) PORT_NAME("Stop Reel 2 / High") + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_SLOT_STOP4 ) PORT_NAME("Stop Reel 4 / W-Up") + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_SLOT_STOP1 ) PORT_NAME("Stop Reel 1 / Take") + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // 'gettone C' - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // 'gettone A' - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) - PORT_SERVICE_NO_TOGGLE( 0x20, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // enters book-keeping menu - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - - PORT_START("BUTTONS") - PORT_BIT( 0xff, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // 'coin C' + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // 'coin A' + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) + PORT_SERVICE_NO_TOGGLE( 0x20, IP_ACTIVE_LOW ) // keep pressed while booting + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // enters book-keeping menu + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test INPUT_PORTS_END -// Test mode is in Italian (probably machine translated given how literal it is). +// Test mode is in Italian (probably machine translated given how literal it is) static INPUT_PORTS_START( happyskl ) PORT_START("DSW1") - PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") // 'demo audio' + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") // 'demo audio' PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") // 'lim. sistema' + PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") // 'lim. sistema' PORT_DIPSETTING( 0x02, "Unlimited" ) PORT_DIPSETTING( 0x00, "Limited" ) - PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") // 'gioco radd.' + PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") // 'gioco radd.' PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x08, 0x08, "Game Speed" ) PORT_DIPLOCATION("SW1:4") // 'velocitá gioco' + PORT_DIPNAME( 0x08, 0x08, "Game Speed" ) PORT_DIPLOCATION("SW1:4") // 'velocitá gioco' PORT_DIPSETTING( 0x08, DEF_STR( Normal ) ) PORT_DIPSETTING( 0x00, "Quick" ) - PORT_DIPNAME( 0x10, 0x10, "Replay Game" ) PORT_DIPLOCATION("SW1:5") // not translated for some reason + PORT_DIPNAME( 0x10, 0x10, "Replay Game" ) PORT_DIPLOCATION("SW1:5") // not translated for some reason PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x20, 0x20, "Show Table" ) PORT_DIPLOCATION("SW1:6") // 'vedi tabella' + PORT_DIPNAME( 0x20, 0x20, "Show Table" ) PORT_DIPLOCATION("SW1:6") // 'vedi tabella' PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x40, 0x40, "Skill" ) PORT_DIPLOCATION("SW1:7") // 'abilitá' + PORT_DIPNAME( 0x40, 0x40, "Skill" ) PORT_DIPLOCATION("SW1:7") // 'abilitá' PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, "Payment Type" ) PORT_DIPLOCATION("SW1:8") // 'tipo pagam.' + PORT_DIPNAME( 0x80, 0x80, "Payment Type" ) PORT_DIPLOCATION("SW1:8") // 'tipo pagam.' PORT_DIPSETTING( 0x80, DEF_STR( Normal ) ) PORT_DIPSETTING( 0x00, "Automatic" ) PORT_START("DSW2") - PORT_DIPNAME( 0x01, 0x01, "Auto Payment" ) PORT_DIPLOCATION("SW2:1") // 'pagam. autom.' + PORT_DIPNAME( 0x01, 0x01, "Auto Payment" ) PORT_DIPLOCATION("SW2:1") // 'pagam. autom.' PORT_DIPSETTING( 0x01, "1" ) PORT_DIPSETTING( 0x00, "10" ) - PORT_DIPNAME( 0x06, 0x06, "Enable Payment" ) PORT_DIPLOCATION("SW2:2,3") // 'abilitá pagam.', they probably meant "abilita" instead of "abilitá" + PORT_DIPNAME( 0x06, 0x06, "Enable Payment" ) PORT_DIPLOCATION("SW2:2,3") // 'abilitá pagam.', they probably meant "abilita" instead of "abilitá" PORT_DIPSETTING( 0x06, "Everything" ) // 'tutto' PORT_DIPSETTING( 0x04, "1/Tickets" ) PORT_DIPSETTING( 0x02, "10/Tickets" ) PORT_DIPSETTING( 0x00, "1/Tickets" ) // same as 0x04, why? - PORT_DIPNAME( 0x08, 0x08, "Select Balls" ) PORT_DIPLOCATION("SW2:4") // 'sel. palloni' + PORT_DIPNAME( 0x08, 0x08, "Select Balls" ) PORT_DIPLOCATION("SW2:4") // 'sel. palloni' PORT_DIPSETTING( 0x08, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x10, 0x10, "Select Cubes" ) PORT_DIPLOCATION("SW2:5") // 'sel. cubi' + PORT_DIPNAME( 0x10, 0x10, "Select Cubes" ) PORT_DIPLOCATION("SW2:5") // 'sel. cubi' PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x20, 0x20, "Select Cans" ) PORT_DIPLOCATION("SW2:6") // 'sel. lattine' + PORT_DIPNAME( 0x20, 0x20, "Select Cans" ) PORT_DIPLOCATION("SW2:6") // 'sel. lattine' PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x40, 0x40, "Select Cards" ) PORT_DIPLOCATION("SW2:7") // 'sel. carte' + PORT_DIPNAME( 0x40, 0x40, "Select Cards" ) PORT_DIPLOCATION("SW2:7") // 'sel. carte' PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, "Credit Limit" ) PORT_DIPLOCATION("SW2:8") // 'lim. crediti' + PORT_DIPNAME( 0x80, 0x80, "Credit Limit" ) PORT_DIPLOCATION("SW2:8") // 'lim. crediti' PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) PORT_START("DSW3") - PORT_DIPNAME( 0x01, 0x01, "Level Limit" ) PORT_DIPLOCATION("SW3:1") // 'lim. livello' + PORT_DIPNAME( 0x01, 0x01, "Level Limit" ) PORT_DIPLOCATION("SW3:1") // 'lim. livello' PORT_DIPSETTING( 0x01, DEF_STR( Low ) ) PORT_DIPSETTING( 0x00, DEF_STR( High ) ) - PORT_DIPNAME( 0x02, 0x02, "Background" ) PORT_DIPLOCATION("SW3:2") // 'sfondo' + PORT_DIPNAME( 0x02, 0x02, "Background" ) PORT_DIPLOCATION("SW3:2") // 'sfondo' PORT_DIPSETTING( 0x02, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) PORT_DIPUNUSED_DIPLOC(0x04, 0x04, "SW3:3") // not used from here on according to test mode @@ -3735,40 +4180,37 @@ static INPUT_PORTS_START( happyskl ) PORT_DIPUNUSED_DIPLOC(0x80, 0x80, "SW3:8") PORT_START("PLAYER1") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME( "HP SW" ) // called like this in key test, not clear what it does - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START ) - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD1 ) - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_POKER_HOLD5 ) + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_DEVICE_MEMBER("hopper", hopper_device, line_r) // hopper switch + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_START1 ) + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_POKER_HOLD1 ) + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_POKER_HOLD5 ) PORT_START("PLAYER2") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_POKER_HOLD2 ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_POKER_HOLD3 ) - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_POKER_HOLD4 ) - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_POKER_HOLD2 ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_POKER_HOLD3 ) + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_POKER_HOLD4 ) + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test PORT_START("COINS") - PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) - PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // 'gettone C' - PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // 'gettone A' - PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) - PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) - PORT_SERVICE_NO_TOGGLE( 0x20, IP_ACTIVE_LOW ) // keep pressed while booting - PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // enters book-keeping menu - PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test - - PORT_START("BUTTONS") - PORT_BIT( 0xff, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test + PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_GAMBLE_KEYIN ) + PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_COIN2 ) PORT_IMPULSE(5) // 'gettone C' (shows 'ricarica in corso') + PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_COIN1 ) PORT_IMPULSE(5) // 'gettone A' + PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_GAMBLE_PAYOUT ) + PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_GAMBLE_KEYOUT ) + PORT_SERVICE_NO_TOGGLE( 0x20, IP_ACTIVE_LOW ) // keep pressed while booting + PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_GAMBLE_BOOK ) // enters book-keeping menu + PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_UNKNOWN ) // no effects in key test INPUT_PORTS_END -static INPUT_PORTS_START( unkigs ) +static INPUT_PORTS_START( cpoker2 ) PORT_INCLUDE(happyskl) PORT_MODIFY("PLAYER1") @@ -3780,38 +4222,38 @@ static INPUT_PORTS_START( unkigs ) // dips definitions taken from test mode, to be verified when the game will be playable PORT_MODIFY("DSW1") - PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") + PORT_DIPNAME( 0x01, 0x01, DEF_STR( Demo_Sounds ) ) PORT_DIPLOCATION("SW1:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") + PORT_DIPNAME( 0x02, 0x02, "System Limit" ) PORT_DIPLOCATION("SW1:2") PORT_DIPSETTING( 0x02, "Unlimited" ) PORT_DIPSETTING( 0x00, "Limited" ) - PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") + PORT_DIPNAME( 0x04, 0x04, "W-Up Game" ) PORT_DIPLOCATION("SW1:3") PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x08, 0x08, "W-Up Type" ) PORT_DIPLOCATION("SW1:4") + PORT_DIPNAME( 0x08, 0x08, "W-Up Type" ) PORT_DIPLOCATION("SW1:4") PORT_DIPSETTING( 0x08, "Big-Small" ) PORT_DIPSETTING( 0x00, "Red-Black" ) - PORT_DIPNAME( 0x10, 0x10, "Game Speed" ) PORT_DIPLOCATION("SW1:5") + PORT_DIPNAME( 0x10, 0x10, "Game Speed" ) PORT_DIPLOCATION("SW1:5") PORT_DIPSETTING( 0x10, DEF_STR( Normal ) ) PORT_DIPSETTING( 0x00, "Quick" ) - PORT_DIPNAME( 0x20, 0x20, "Card Type" ) PORT_DIPLOCATION("SW1:6") + PORT_DIPNAME( 0x20, 0x20, "Card Type" ) PORT_DIPLOCATION("SW1:6") PORT_DIPSETTING( 0x20, "Poker" ) PORT_DIPSETTING( 0x00, "Symbol" ) - PORT_DIPNAME( 0x40, 0x40, "Sexy Girl" ) PORT_DIPLOCATION("SW1:7") + PORT_DIPNAME( 0x40, 0x40, "Sexy Girl" ) PORT_DIPLOCATION("SW1:7") PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, "Title Name" ) PORT_DIPLOCATION("SW1:8") - PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x80, 0x00, "Show Title" ) PORT_DIPLOCATION("SW1:8") + PORT_DIPSETTING( 0x00, DEF_STR( Yes ) ) + PORT_DIPSETTING( 0x80, DEF_STR( No ) ) PORT_MODIFY("DSW2") - PORT_DIPNAME( 0x01, 0x01, "Show Hold" ) PORT_DIPLOCATION("SW2:1") + PORT_DIPNAME( 0x01, 0x01, "Show Hold" ) PORT_DIPLOCATION("SW2:1") PORT_DIPSETTING( 0x01, DEF_STR( Off ) ) PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x02, 0x02, "Number Type" ) PORT_DIPLOCATION("SW2:2") + PORT_DIPNAME( 0x02, 0x02, "Number Type" ) PORT_DIPLOCATION("SW2:2") PORT_DIPSETTING( 0x02, "Number" ) - PORT_DIPSETTING( 0x00, "AJQK" ) + PORT_DIPSETTING( 0x00, "A,J,Q,K" ) PORT_DIPUNUSED_DIPLOC(0x04, 0x04, "SW2:3") // not used from here on according to test mode, PCB does have 3 8-dip banks PORT_DIPUNUSED_DIPLOC(0x08, 0x08, "SW2:4") PORT_DIPUNUSED_DIPLOC(0x10, 0x10, "SW2:5") @@ -3823,56 +4265,17 @@ static INPUT_PORTS_START( unkigs ) PORT_DIPUNUSED_DIPLOC(0x01, 0x01, "SW3:1") PORT_DIPUNUSED_DIPLOC(0x02, 0x02, "SW3:2") INPUT_PORTS_END + /*************************************************************************** Machine Drivers ***************************************************************************/ -TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::iqblocka_interrupt) +void igs017_state::base_machine_oki(machine_config &config, const XTAL &xtal_oki) { - int scanline = param; - - if (scanline == 240 && m_igs017_igs031->get_irq_enable()) - m_maincpu->set_input_line(0, HOLD_LINE); - - if (scanline == 0 && m_igs017_igs031->get_nmi_enable()) - m_maincpu->pulse_input_line(INPUT_LINE_NMI, attotime::zero); -} - -MACHINE_RESET_MEMBER(igs017_state,iqblocka) -{ - machine_reset(); - m_input_select = 0; -} - -void igs017_state::iqblocka(machine_config &config) -{ - HD64180RP(config, m_maincpu, XTAL(16'000'000)); - m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); - m_maincpu->set_addrmap(AS_IO, &igs017_state::iqblocka_io); - TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); - - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,iqblocka) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("DSW1"); - ppi.in_pb_callback().set_ioport("DSW2"); - ppi.in_pc_callback().set_ioport("DSW3"); + IGS_MUX(config, m_igs_mux, 0); - // protection - IGS_BITSWAP(config, m_igs_bitswap, 0); - m_igs_bitswap->in_pa_callback().set_ioport("PLAYER1"); - m_igs_bitswap->in_pb_callback().set_ioport("PLAYER2"); - m_igs_bitswap->in_pc_callback().set_ioport("COINS"); - m_igs_bitswap->out_pa_callback().set(FUNC(igs017_state::iqblocka_keyin_w)); - m_igs_bitswap->set_val_xor(0x15d6); - m_igs_bitswap->set_mf_bits(3, 5, 9, 11); - m_igs_bitswap->set_m3_bits<0>(~5, 8, ~10, ~15); - m_igs_bitswap->set_m3_bits<1>( 3, ~8, ~12, ~15); - m_igs_bitswap->set_m3_bits<2>( 2, ~6, ~11, ~15); - m_igs_bitswap->set_m3_bits<3>( 0, ~1, ~3, ~15); - - IGS_INCDEC(config, m_igs_incdec, 0); + I8255A(config, m_ppi); // video SCREEN(config, m_screen, SCREEN_TYPE_RASTER); @@ -3888,17 +4291,61 @@ void igs017_state::iqblocka(machine_config &config) // sound SPEAKER(config, "mono").front_center(); - YM2413(config, "ymsnd", XTAL(3'579'545)).add_route(ALL_OUTPUTS, "mono", 0.5); + OKIM6295(config, m_oki, xtal_oki, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); +} - OKIM6295(config, m_oki, XTAL(16'000'000) / 16, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); + +// iqblocka, iqblockf, genius6 + +TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::iqblocka_interrupt) +{ + int scanline = param; + + if (scanline == 240 && m_igs017_igs031->get_irq_enable()) + m_maincpu->set_input_line(0, HOLD_LINE); + + if (scanline == 0 && m_igs017_igs031->get_nmi_enable()) + m_maincpu->pulse_input_line(INPUT_LINE_NMI, attotime::zero); +} + +void igs017_state::iqblocka(machine_config &config) +{ + base_machine_oki(config, 16_MHz_XTAL / 16); + + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::iqblocka_io); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::iqblocka_mux_map); + + m_ppi->in_pa_callback().set_ioport("DSW1"); + m_ppi->in_pb_callback().set_ioport("DSW2"); + m_ppi->in_pc_callback().set_ioport("DSW3"); + + // protection + IGS_BITSWAP(config, m_igs_bitswap, 0); + m_igs_bitswap->set_val_xor(0x15d6); + m_igs_bitswap->set_mf_bits(3, 5, 9, 11); + m_igs_bitswap->set_m3_bits<0>(~5, 8, ~10, ~15); + m_igs_bitswap->set_m3_bits<1>( 3, ~8, ~12, ~15); + m_igs_bitswap->set_m3_bits<2>( 2, ~6, ~11, ~15); + m_igs_bitswap->set_m3_bits<3>( 0, ~1, ~3, ~15); + + IGS_INCDEC(config, m_igs_incdec, 0); + + // sound + YM2413(config, "ymsnd", 3.579545_MHz_XTAL).add_route(ALL_OUTPUTS, "mono", 0.5); } void igs017_state::iqblockf(machine_config &config) { iqblocka(config); + m_igs_mux->set_addrmap(0, &igs017_state::iqblockf_mux_map); + // tweaked protection bitswap - m_igs_bitswap->out_pb_callback().set(FUNC(igs017_state::iqblockf_keyout_w)); m_igs_bitswap->set_mf_bits(0, 5, 9, 13); } @@ -3914,26 +4361,191 @@ void igs017_state::genius6(machine_config &config) m_igs_bitswap->set_m3_bits<3>( 3, ~5, ~6, ~15); } + +// tarzan + void igs017_state::tarzan(machine_config &config) { - iqblocka(config); + base_machine_oki(config, 16_MHz_XTAL / 16); + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::tarzan_io); m_maincpu->set_addrmap(AS_OPCODES, &igs017_state::decrypted_opcodes_map); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::tarzan_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set(FUNC(igs017_state::tarzan_keys_joy_r)); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_STRING(config, m_igs_string, 0); + + IGS_INCDEC(config, m_igs_incdec, 0); + + // video + m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tarzan_palette_bitswap)); + + // sound + YM2413(config, "ymsnd", 3.579545_MHz_XTAL).add_route(ALL_OUTPUTS, "mono", 0.5); } + +// starzan + void igs017_state::starzan(machine_config &config) { - tarzan(config); + base_machine_oki(config, 16_MHz_XTAL / 16); - subdevice("ppi8255")->in_pa_callback().set_ioport("COINS"); - subdevice("ppi8255")->in_pb_callback().set_ioport("PLAYER1"); - subdevice("ppi8255")->in_pc_callback().set(FUNC(igs017_state::i8255_port_c_mux_r)); + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::starzan_io); + m_maincpu->set_addrmap(AS_OPCODES, &igs017_state::decrypted_opcodes_map); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); - m_igs_bitswap->in_pa_callback().set_constant(0xff); - m_igs_bitswap->in_pc_callback().set_constant(0xff); - m_igs_bitswap->out_pd_callback().set([this](u8 data){ m_i8255_portc_mux = data >> 1; }); + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::starzan_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set_ioport("PLAYER1"); + m_ppi->in_pc_callback().set(FUNC(igs017_state::dsw_r)); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_STRING(config, m_igs_string, 0); + + IGS_INCDEC(config, m_igs_incdec, 0); + + // video + m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tarzan_palette_bitswap)); + + // sound + YM2413(config, "ymsnd", 3.579545_MHz_XTAL).add_route(ALL_OUTPUTS, "mono", 0.5); } + +// happyskl + +void igs017_state::happyskl(machine_config &config) +{ + base_machine_oki(config, 16_MHz_XTAL / 16); + + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::happyskl_io); + m_maincpu->set_addrmap(AS_OPCODES, &igs017_state::decrypted_opcodes_map); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::happyskl_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set_ioport("PLAYER1"); + m_ppi->in_pc_callback().set(FUNC(igs017_state::dsw_r)); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // video + m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tarzan_palette_bitswap)); +} + + +// cpoker2 + +void igs017_state::cpoker2(machine_config &config) +{ + base_machine_oki(config, 16_MHz_XTAL / 16); + + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::cpoker2_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::cpoker2_io); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::cpoker2_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set_ioport("PLAYER1"); + m_ppi->in_pc_callback().set(FUNC(igs017_state::dsw_r)); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_INCDEC(config, m_igs_incdec, 0); + + IGS_INC(config, m_igs_inc, 0); + + // video + m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tarzan_palette_bitswap)); +} + + +// tjsb + +void igs017_state::tjsb(machine_config &config) +{ + base_machine_oki(config, 16_MHz_XTAL / 16); + + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::tjsb_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::tjsb_io); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::tjsb_mux_map); + + m_ppi->in_pa_callback().set_ioport("DSW1"); + m_ppi->in_pb_callback().set_ioport("DSW2"); + m_ppi->in_pc_callback().set_ioport("DSW3"); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_STRING(config, m_igs_string, 0); + + // video + m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tjsb_palette_bitswap)); + + // sound + YM2413(config, "ymsnd", 3.579545_MHz_XTAL).add_route(ALL_OUTPUTS, "mono", 0.5); +} + + +// spkrform + +void igs017_state::spkrform(machine_config &config) +{ + base_machine_oki(config, 16_MHz_XTAL / 16); + + HD64180RP(config, m_maincpu, 16_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::iqblocka_map); + m_maincpu->set_addrmap(AS_IO, &igs017_state::spkrform_io); + TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + + // i/o + m_igs_mux->set_addrmap(0, &igs017_state::spkrform_mux_map); + + m_ppi->in_pa_callback().set_ioport("DSW1"); + m_ppi->in_pb_callback().set_ioport("DSW2"); + m_ppi->in_pc_callback().set_ioport("DSW3"); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_STRING(config, m_igs_string, 0); + + IGS_INCDEC(config, m_igs_incdec, 0); + + // sound + YM2413(config, "ymsnd", 3.579545_MHz_XTAL).add_route(ALL_OUTPUTS, "mono", 0.5); +} + + // mgcs TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::mgcs_interrupt) @@ -3947,45 +4559,28 @@ TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::mgcs_interrupt) m_maincpu->set_input_line(2, HOLD_LINE); } -MACHINE_RESET_MEMBER(igs017_state,mgcs) -{ - MACHINE_RESET_CALL_MEMBER( iqblocka ); - - m_scramble_data = 0; - m_igs_magic = 0; -} - void igs017_state::mgcs(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); + base_machine_oki(config, 8_MHz_XTAL / 8); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::mgcs_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgcs_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,mgcs) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("COINS"); - ppi.in_pb_callback().set(FUNC(igs017_state::mgcs_keys_r)); + m_igs_mux->set_addrmap(0, &igs017_state::mgcs_mux_map); - TICKET_DISPENSER(config, m_hopperdev, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW ); + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set(FUNC(igs017_state::mgcs_keys_joy_r)); + m_ppi->in_pc_callback().set_ioport("JOY"); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); + + // protection + IGS_STRING(config, m_igs_string, 0); // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 240-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::mgcs_palette_bitswap)); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(8'000'000) / 8, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); } @@ -3993,63 +4588,59 @@ void igs017_state::mgcs(machine_config &config) void igs017_state::lhzb2(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); + base_machine_oki(config, 8_MHz_XTAL / 8); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::lhzb2_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgcs_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,mgcs) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("COINS"); - ppi.in_pb_callback().set_ioport("DSW1"); - ppi.in_pc_callback().set_ioport("DSW2"); + m_igs_mux->set_addrmap(0, &igs017_state::lhzb2_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set_ioport("DSW1"); + m_ppi->in_pc_callback().set_ioport("DSW2"); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); // protection - IGS025(config, m_igs025, 0); - m_igs025->set_external_cb(FUNC(igs017_state::igs025_to_igs022_callback)); + IGS_STRING(config, m_igs_string, 0); IGS022(config, m_igs022, 0); // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 240-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::lhzb2a_palette_bitswap)); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(8'000'000) / 8, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); } // lhzb2a -MACHINE_RESET_MEMBER(igs017_state,lhzb2a) +MACHINE_RESET_MEMBER(igs017_state, lhzb2a) { - MACHINE_RESET_CALL_MEMBER( mgcs ); + machine_reset(); lhzb2a_remap_addr_w(m_maincpu->space(AS_PROGRAM), 0xf0); } void igs017_state::lhzb2a(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); + base_machine_oki(config, 8_MHz_XTAL / 8); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::lhzb2a_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgcs_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,lhzb2a) + MCFG_MACHINE_RESET_OVERRIDE(igs017_state, lhzb2a) // i/o -// I8255A(config, "ppi8255", 0); + m_igs_mux->set_addrmap(0, &igs017_state::lhzb2a_mux_map); + + // ppi8255 not used for i/o (just video enable)? + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); // protection + IGS_STRING(config, m_igs_string, 0); + IGS_BITSWAP(config, m_igs_bitswap, 0); m_igs_bitswap->set_val_xor(0x289a); m_igs_bitswap->set_mf_bits(4, 7, 10, 13); @@ -4061,21 +4652,7 @@ void igs017_state::lhzb2a(machine_config &config) IGS_INCDEC(config, m_igs_incdec, 0); // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); // VSync 60Hz, HSync 15.3kHz - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 256-16-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::lhzb2a_palette_bitswap)); -// m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(22'000'000) / 22, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); } @@ -4083,40 +4660,28 @@ void igs017_state::lhzb2a(machine_config &config) void igs017_state::slqz2(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); + base_machine_oki(config, 8_MHz_XTAL / 8); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::slqz2_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgcs_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,mgcs) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("COINS"); - ppi.in_pb_callback().set_ioport("DSW1"); - ppi.in_pc_callback().set_ioport("DSW2"); + m_igs_mux->set_addrmap(0, &igs017_state::slqz2_mux_map); + + m_ppi->in_pa_callback().set_ioport("COINS"); + m_ppi->in_pb_callback().set_ioport("DSW1"); + m_ppi->in_pc_callback().set_ioport("DSW2"); + + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); // protection - IGS025(config, m_igs025, 0); - m_igs025->set_external_cb(FUNC(igs017_state::igs025_to_igs022_callback)); + IGS_STRING(config, m_igs_string, 0); IGS022(config, m_igs022, 0); // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 240-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::slqz2_palette_bitswap)); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(8'000'000) / 8, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); } @@ -4124,36 +4689,27 @@ void igs017_state::slqz2(machine_config &config) void igs017_state::sdmg2(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); + base_machine_oki(config, 22_MHz_XTAL / 22); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::sdmg2_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgcs_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,mgcs) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("DSW1"); - ppi.in_pb_callback().set_ioport("DSW2"); + m_igs_mux->set_addrmap(0, &igs017_state::sdmg2_mux_map); - // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); // VSync 60Hz, HSync 15.3kHz - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 256-16-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); + m_ppi->in_pa_callback().set_ioport("DSW1"); + m_ppi->in_pb_callback().set_ioport("DSW2"); + // DSW3 is read but unused (it's not populated on the PCB) - IGS017_IGS031(config, m_igs017_igs031, 0); - m_igs017_igs031->set_i8255_tag("ppi8255"); + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(22'000'000) / 22, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); + // protection + IGS_INCDEC(config, m_igs_incdec, 0); } -// mgdh +// mgdh, mgdha TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::mgdh_interrupt) { @@ -4168,106 +4724,28 @@ TIMER_DEVICE_CALLBACK_MEMBER(igs017_state::mgdh_interrupt) void igs017_state::mgdha(machine_config &config) { - M68000(config, m_maincpu, XTAL(22'000'000) / 2); - m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::mgdha_map); + base_machine_oki(config, 22_MHz_XTAL / 22); + + M68000(config, m_maincpu, 22_MHz_XTAL / 2); + m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::mgdh_map); TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::mgdh_interrupt), "screen", 0, 1); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,mgcs) - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("DSW1"); + m_igs_mux->set_addrmap(0, &igs017_state::mgdha_mux_map); - // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 256-16-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); + m_ppi->in_pa_callback().set_ioport("DSW1"); - IGS017_IGS031(config, m_igs017_igs031, 0); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - OKIM6295(config, m_oki, XTAL(22'000'000) / 22, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); + HOPPER(config, m_hopper, attotime::from_msec(50), TICKET_MOTOR_ACTIVE_HIGH, TICKET_STATUS_ACTIVE_LOW); } - -// tjsb - -void igs017_state::tjsb(machine_config &config) +void igs017_state::mgdh(machine_config &config) { - HD64180RP(config, m_maincpu, XTAL(16'000'000)); - m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::tjsb_map); - m_maincpu->set_addrmap(AS_IO, &igs017_state::tjsb_io); - TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); + mgdha(config); - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,iqblocka) + m_igs_mux->set_addrmap(0, &igs017_state::mgdh_mux_map); - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("DSW1"); - ppi.in_pb_callback().set_ioport("DSW2"); - ppi.in_pc_callback().set_ioport("DSW3"); - - // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 240-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); - m_igs017_igs031->set_palette_scramble_cb(FUNC(igs017_state::tjsb_palette_bitswap)); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - YM2413(config, "ymsnd", XTAL(3'579'545)).add_route(ALL_OUTPUTS, "mono", 0.5); - - OKIM6295(config, m_oki, XTAL(16'000'000) / 16, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); -} - - -// spkrform - -void igs017_state::spkrform(machine_config &config) -{ - HD64180RP(config, m_maincpu, XTAL(16'000'000)); - m_maincpu->set_addrmap(AS_PROGRAM, &igs017_state::spkrform_map); - m_maincpu->set_addrmap(AS_IO, &igs017_state::spkrform_io); - TIMER(config, "scantimer").configure_scanline(FUNC(igs017_state::iqblocka_interrupt), "screen", 0, 1); - - MCFG_MACHINE_RESET_OVERRIDE(igs017_state,iqblocka) - - // i/o - i8255_device &ppi(I8255A(config, "ppi8255")); - ppi.in_pa_callback().set_ioport("DSW1"); - ppi.in_pb_callback().set_ioport("DSW2"); - ppi.in_pc_callback().set_ioport("DSW3"); - - // video - SCREEN(config, m_screen, SCREEN_TYPE_RASTER); - m_screen->set_refresh_hz(60); - m_screen->set_vblank_time(ATTOSECONDS_IN_USEC(0)); - m_screen->set_size(512, 256); - m_screen->set_visarea(0, 512-1, 0, 240-1); - m_screen->set_screen_update("igs017_igs031", FUNC(igs017_igs031_device::screen_update)); - m_screen->set_palette("igs017_igs031:palette"); - - IGS017_IGS031(config, m_igs017_igs031, 0); - m_igs017_igs031->set_i8255_tag("ppi8255"); - - // sound - SPEAKER(config, "mono").front_center(); - YM2413(config, "ymsnd", XTAL(3'579'545)).add_route(ALL_OUTPUTS, "mono", 0.5); - - OKIM6295(config, m_oki, XTAL(16'000'000) / 16, okim6295_device::PIN7_HIGH).add_route(ALL_OUTPUTS, "mono", 0.5); + // protection (only used for the game id check?) +// IGS_STRING(config, m_igs_string, 0); } @@ -4279,13 +4757,14 @@ void igs017_state::spkrform(machine_config &config) /*************************************************************************** -數字樂園 (Shùzì Lèyuán, V127M) +Shuzi Leyuan (V127M) +數字樂園 (Shùzì Lèyuán) IGS, 1996 PCB Layout ---------- -IGS PCB N0- 0131-4 +IGS PCB NO-0131-4 |---------------------------------------| |uPD1242H VOL U3567 3.579545MHz| | AR17961 | @@ -4325,14 +4804,21 @@ ROM_START( iqblocka ) ROM_REGION( 0x40000, "maincpu", 0 ) ROM_LOAD( "v.u18", 0x00000, 0x40000, CRC(2e2b7d43) SHA1(cc73f4c8f9a6e2219ee04c9910725558a80b4eb2) ) - ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "cg.u7", 0x000000, 0x080000, CRC(cb48a66e) SHA1(6d597193d1333a97957d5ceec8179a24bedfd928) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_REGION( 0x100000, "igs017_igs031:sprites", 0 ) + ROM_LOAD( "cg.u7", 0x000000, 0x080000, CRC(cb48a66e) SHA1(6d597193d1333a97957d5ceec8179a24bedfd928) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_FILL( 0x080000, 0x080000, 0xff ) // unpopulated ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0) ROM_LOAD( "text.u8", 0x000000, 0x080000, CRC(48c4f4e6) SHA1(b1e1ca62cf6a99c11a5cc56705eef7e22a3b2740) ) ROM_REGION( 0x40000, "oki", 0 ) ROM_LOAD( "speech.u17", 0x00000, 0x40000, CRC(d9e3d39f) SHA1(bec85d1ac2dfca77453cbca0e7dd53fee8fb438b) ) + + ROM_REGION( 0x2dd, "pld", ROMREGION_ERASE ) + ROM_LOAD( "cq.u24", 0x000, 0x2dd, NO_DUMP ) // PAL22CV10 + + ROM_REGION( 0x15, "igs_fixed_data", 0 ) + ROM_LOAD( "igs_fixed_data.key", 0x00, 0x15, CRC(9159ecbf) SHA1(b6bdb1f327944dfc7f6f71565a24e89517607490) ) ROM_END // English title (IQ Block) and year 1997: @@ -4341,22 +4827,31 @@ ROM_START( iqblockf ) ROM_REGION( 0x40000, "maincpu", 0 ) ROM_LOAD( "v113fr.u18", 0x00000, 0x40000, CRC(346c68af) SHA1(ceae4c0143c288dc9c1dd1e8a51f1e3371ffa439) ) - ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "cg.u7", 0x000000, 0x080000, CRC(cb48a66e) SHA1(6d597193d1333a97957d5ceec8179a24bedfd928) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_REGION( 0x100000, "igs017_igs031:sprites", 0 ) + ROM_LOAD( "cg.u7", 0x000000, 0x080000, CRC(cb48a66e) SHA1(6d597193d1333a97957d5ceec8179a24bedfd928) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_FILL( 0x080000, 0x080000, 0xff ) // unpopulated ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "text.u8", 0x000000, 0x080000, CRC(48c4f4e6) SHA1(b1e1ca62cf6a99c11a5cc56705eef7e22a3b2740) ) ROM_REGION( 0x40000, "oki", 0 ) ROM_LOAD( "sp.u17", 0x00000, 0x40000, CRC(71357845) SHA1(25f4f7aebdcc0706018f041d3696322df569b0a3) ) + + ROM_REGION( 0x2dd, "pld", ROMREGION_ERASE ) + ROM_LOAD( "cq.u24", 0x000, 0x2dd, NO_DUMP ) // PAL22CV10 + + ROM_REGION( 0x15, "igs_fixed_data", 0 ) + ROM_LOAD( "igs_fixed_data.key", 0x00, 0x15, CRC(9159ecbf) SHA1(b6bdb1f327944dfc7f6f71565a24e89517607490) ) ROM_END +// IQ Block V110F also exists (undumped) with IGS003e (not 8255) + /*************************************************************************** -Genius 6 +Genius 6 (V110F) IGS, 1998 -IGS PCB N0- 0131-4 +IGS PCB NO-0131-4 |---------------------------------------| |uPD1242H VOL U3567 3.579545MHz| | K668 | @@ -4388,13 +4883,19 @@ ROM_START( genius6 ) ROM_LOAD( "genius6_v110f.u18", 0x00000, 0x40000, CRC(2630ad44) SHA1(37002fa913ad60c59145f5a7692eef8862b9d6eb) ) ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "genius6_cg.u7", 0x000000, 0x080000, CRC(1842d021) SHA1(78bfb5108741d39bd19b603cc97623fba7b2a31e) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_LOAD( "genius6_cg.u7", 0x000000, 0x080000, CRC(1842d021) SHA1(78bfb5108741d39bd19b603cc97623fba7b2a31e) ) // FIXED BITS (xxxxxxxx0xxxxxxx) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "text.u8", 0x000000, 0x080000, CRC(48c4f4e6) SHA1(b1e1ca62cf6a99c11a5cc56705eef7e22a3b2740) ) // same as iqblocka ROM_REGION( 0x40000, "oki", 0 ) ROM_LOAD( "speech.u17", 0x00000, 0x40000, CRC(d9e3d39f) SHA1(bec85d1ac2dfca77453cbca0e7dd53fee8fb438b) ) // same as iqblocka + + ROM_REGION( 0x2dd, "pld", ROMREGION_ERASE ) + ROM_LOAD( "cq.u24", 0x000, 0x2dd, NO_DUMP ) // PAL22CV10 + + ROM_REGION( 0x15, "igs_fixed_data", 0 ) + ROM_LOAD( "igs_fixed_data.key", 0x00, 0x15, CRC(9159ecbf) SHA1(b6bdb1f327944dfc7f6f71565a24e89517607490) ) ROM_END // strangely identifies as V133F and has 1997 copyright, while the parent is V110F but with 1998 copyright @@ -4403,16 +4904,22 @@ ROM_START( genius6a ) ROM_LOAD( "genius6_v133.u18", 0x00000, 0x40000, CRC(b34ce8c6) SHA1(845e6c4f5b1f06229a4046cf085ce08802458bd8) ) ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "genius6_cg.u7", 0x000000, 0x080000, CRC(1842d021) SHA1(78bfb5108741d39bd19b603cc97623fba7b2a31e) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_LOAD( "genius6_cg.u7", 0x000000, 0x080000, CRC(1842d021) SHA1(78bfb5108741d39bd19b603cc97623fba7b2a31e) ) // FIXED BITS (xxxxxxxx0xxxxxxx) - ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) - ROM_LOAD( "text.u8", 0x000000, 0x040000, CRC(7716b601) SHA1(363cddd930fdec4821ebfaced64276f8fa943eae) ) // half sized if compared to the parent and identical to its 1st half, confirmed correct + ROM_REGION( 0x40000, "igs017_igs031:tilemaps", 0 ) + ROM_LOAD( "text.u8", 0x000000, 0x040000, CRC(7716b601) SHA1(363cddd930fdec4821ebfaced64276f8fa943eae) ) // half sized if compared to the parent and identical to its 1st half, confirmed correct (27c2048) ROM_REGION( 0x40000, "oki", 0 ) ROM_LOAD( "speech.u17", 0x00000, 0x40000, CRC(d9e3d39f) SHA1(bec85d1ac2dfca77453cbca0e7dd53fee8fb438b) ) // same as iqblocka + + ROM_REGION( 0x2dd, "pld", ROMREGION_ERASE ) + ROM_LOAD( "cq.u24", 0x000, 0x2dd, NO_DUMP ) // PAL22CV10 + + ROM_REGION( 0x15, "igs_fixed_data", 0 ) + ROM_LOAD( "igs_fixed_data.key", 0x00, 0x15, CRC(9159ecbf) SHA1(b6bdb1f327944dfc7f6f71565a24e89517607490) ) ROM_END -ROM_START( genius6b ) // PCB N0 - 0132, identical to V133F but for the main CPU ROM +ROM_START( genius6b ) // PCB NO-0132, identical to V133F but for the main CPU ROM ROM_REGION( 0x40000, "maincpu", 0 ) ROM_LOAD( "genius6_v-132f.u18", 0x00000, 0x40000, CRC(231be791) SHA1(1684395dc93902893dca32952c236617ccdbc269) ) @@ -4424,12 +4931,17 @@ ROM_START( genius6b ) // PCB N0 - 0132, identical to V133F but for the main CPU ROM_REGION( 0x40000, "oki", 0 ) ROM_LOAD( "speech.u17", 0x00000, 0x40000, CRC(d9e3d39f) SHA1(bec85d1ac2dfca77453cbca0e7dd53fee8fb438b) ) -ROM_END + ROM_REGION( 0x2dd, "pld", ROMREGION_ERASE ) + ROM_LOAD( "cq.u24", 0x000, 0x2dd, NO_DUMP ) // PAL22CV10 + + ROM_REGION( 0x15, "igs_fixed_data", 0 ) + ROM_LOAD( "igs_fixed_data.key", 0x00, 0x15, CRC(9159ecbf) SHA1(b6bdb1f327944dfc7f6f71565a24e89517607490) ) +ROM_END /*************************************************************************** -Mahjong Tian Jiang Shen Bing +Tian Jiang Shen Bing (V137C) 天將神兵 (Tiān Jiāng Shén Bīng) IGS, 1997 @@ -4439,7 +4951,7 @@ but the 8255 has been replaced with the IGS025 IC PCB Layout ---------- -IGS PCB N0- 0157-2 +IGS PCB NO-0157-2 |---------------------------------------| |uPD1242H VOL U3567 3.579545MHz| | AR17961 | @@ -4484,15 +4996,18 @@ ROM_START( tjsb ) ROM_LOAD( "a0701.u3", 0x00000, 0x400000, CRC(27502a0a) SHA1(cca79e253697f47b688ef781b1b6de9d2945f199) ) // FIXED BITS (xxxxxxxx0xxxxxxx) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) - ROM_LOAD( "text.u6", 0x00000, 0x80000, CRC(3be886b8) SHA1(15b3624ed076640c1828d065b01306a8656f5a9b) ) // BADADDR --xxxxxxxxxxxxxxxxx + ROM_LOAD( "text.u6", 0x00000, 0x80000, CRC(3be886b8) SHA1(15b3624ed076640c1828d065b01306a8656f5a9b) ) // BADADDR --xxxxxxxxxxxxxxxxx ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "s0703.u15", 0x00000, 0x80000, CRC(c6f94d29) SHA1(ec413580240711fc4977dd3c96c288501aa7ef6c) ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "tjsb_string.key", 0x00, 0xec, CRC(412c83a0) SHA1(c09618aabecdde4c77d2b5695799fc89dfb325bc) ) ROM_END /*************************************************************************** -Mahjong Man Guan Caishen +Man Guan Caishen (V103CS) 满贯财神 (Mǎn Guàn Cáishén) IGS, 1998 @@ -4539,18 +5054,21 @@ ROM_START( mgcs ) ROM_LOAD16_WORD_SWAP( "p1500.u8", 0x00000, 0x80000, CRC(a8cb5905) SHA1(37be7d926a1352869632d43943763accd4dec4b7) ) ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "m1501.u23", 0x000000, 0x400000, CRC(96fce058) SHA1(6b87f47d646bad9b3061bdc8a9af65467fdbbc9f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) + ROM_LOAD( "m1501.u23", 0x000000, 0x400000, CRC(96fce058) SHA1(6b87f47d646bad9b3061bdc8a9af65467fdbbc9f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "text.u25", 0x00000, 0x80000, CRC(a37f9613) SHA1(812f060ca98a34540c48a180c359c3d0f1c0b5bb) ) ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "s1502.u10", 0x00000, 0x80000, CRC(a8a6ba58) SHA1(59276a8ab4a31812600816c2a43b74bd71394419) ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "mgcs_string.key", 0x00, 0xec, CRC(6cdadd19) SHA1(c2b4ced5d45d0af1ddeeabd0e352fd5383995d32) ) ROM_END /*************************************************************************** -Mahjong Super Da Man Guan 2 +Super Da Man Guan II (China, V754C) IGS, 1997 PCB Layout @@ -4596,8 +5114,8 @@ ROM_START( sdmg2 ) ROM_LOAD16_WORD_SWAP( "p0900.u25", 0x00000, 0x80000,CRC(43366f51) SHA1(48dd965dceff7de15b43c2140226a8b17a792dbc) ) ROM_REGION( 0x280000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "m0901.u5", 0x000000, 0x200000, CRC(9699db24) SHA1(50fc2f173c20b48d10595f01f1e9545f1b13a61b) ) // FIXED BITS (xxxxxxxx0xxxxxxx) - ROM_LOAD( "m0902.u4", 0x200000, 0x080000, CRC(3298b13b) SHA1(13b21ddeed368b7f4fea1408c8fc511244342faf) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_LOAD( "m0901.u5", 0x000000, 0x200000, CRC(9699db24) SHA1(50fc2f173c20b48d10595f01f1e9545f1b13a61b) ) // FIXED BITS (xxxxxxxx0xxxxxxx) + ROM_LOAD( "m0902.u4", 0x200000, 0x080000, CRC(3298b13b) SHA1(13b21ddeed368b7f4fea1408c8fc511244342faf) ) // FIXED BITS (xxxxxxxx0xxxxxxx) ROM_REGION( 0x20000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "text.u6", 0x000000, 0x020000, CRC(cb34cbc0) SHA1(ceedbdda085fd1acc9a575502bdf7cf998f54f05) ) @@ -4608,7 +5126,7 @@ ROM_END /*************************************************************************** -Mahjong Long Hu Zhengba 2 +Long Hu Zhengba 2 (set 1) 龙虎争霸 (Lóng Hǔ Zhēngbà) IGS, 1998 @@ -4654,38 +5172,44 @@ ROM_START( lhzb2 ) ROM_REGION( 0x80000, "maincpu", 0 ) ROM_LOAD16_WORD_SWAP( "p1100.u30", 0x00000, 0x80000, CRC(68102b25) SHA1(6c1e8d204be0efda0e9b6c2f49b5c6760712475f) ) - ROM_REGION( 0x10000, "igs022", 0 ) // INTERNATIONAL GAMES SYSTEM CO.,LTD - ROM_LOAD( "m1104.u11",0x0000, 0x10000, CRC(794d0276) SHA1(ac903d2faa3fb315438dc8da22c5337611a8790d) ) + ROM_REGION( 0x10000, "igs022", 0 ) + ROM_LOAD( "m1104.u11",0x0000, 0x10000, CRC(794d0276) SHA1(ac903d2faa3fb315438dc8da22c5337611a8790d) ) // INTERNATIONAL GAMES SYSTEM CO.,LTD - ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) // address scrambling - ROM_LOAD16_WORD_SWAP( "m1101.u6", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) + ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) + ROM_LOAD16_WORD_SWAP( "m1101.u6", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) - ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) // address scrambling + ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD16_WORD_SWAP( "m1103.u8", 0x00000, 0x80000, CRC(4d3776b4) SHA1(fa9b311b1a6ad56e136b66d090bc62ed5003b2f2) ) ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "s1102.u23", 0x00000, 0x80000, CRC(51ffe245) SHA1(849011b186096add657ab20d49d260ec23363ef3) ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "lhzb2_string.key", 0x00, 0xec, CRC(c964dc35) SHA1(81036e0dfa9abad123701ae8939d0d5b6f91b015) ) ROM_END -/* alt hardware, no IGS022 (protection) chip */ +// VS221M: alt hardware, no IGS022 protection chip ROM_START( lhzb2a ) ROM_REGION( 0x80000, "maincpu", 0 ) ROM_LOAD16_WORD_SWAP( "p-4096", 0x00000, 0x80000, CRC(41293f32) SHA1(df4e993f4a458729ade13981e58f32d8116c0082) ) - ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) // address scrambling - ROM_LOAD16_WORD_SWAP( "m1101.u6", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) + ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) + ROM_LOAD16_WORD_SWAP( "m1101.u6", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) - ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) // address scrambling + ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD16_WORD_SWAP( "m1103.u8", 0x00000, 0x80000, CRC(4d3776b4) SHA1(fa9b311b1a6ad56e136b66d090bc62ed5003b2f2) ) ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "s1102.u23", 0x00000, 0x80000, CRC(51ffe245) SHA1(849011b186096add657ab20d49d260ec23363ef3) ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "lhzb2_string.key", 0x00, 0xec, CRC(c964dc35) SHA1(81036e0dfa9abad123701ae8939d0d5b6f91b015) ) ROM_END /*************************************************************************** -Mahjong Shuang Long Qiang Zhu 2 +Shuang Long Qiang Zhu 2 VS (China, VS203J) 双龙抢珠 (Shuāng Lóng Qiǎng Zhū) IGS, 1998 @@ -4730,29 +5254,32 @@ ROM_START( slqz2 ) ROM_REGION( 0x80000, "maincpu", 0 ) ROM_LOAD16_WORD_SWAP( "p1100.u28", 0x00000, 0x80000, CRC(0b8e5c9e) SHA1(16572bd1163bba4da8a76b10649d2f71e50ad369) ) - ROM_REGION( 0x10000, "igs022", 0 ) // INTERNATIONAL GAMES SYSTEM CO.,LTD - ROM_LOAD( "m1103.u12", 0x00000, 0x10000, CRC(9f3b8d65) SHA1(5ee1ad025474399c2826f21d970e76f25d0fa1fd) ) + ROM_REGION( 0x10000, "igs022", 0 ) + ROM_LOAD( "m1103.u12", 0x00000, 0x10000, CRC(9f3b8d65) SHA1(5ee1ad025474399c2826f21d970e76f25d0fa1fd) ) // INTERNATIONAL GAMES SYSTEM CO.,LTD - ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) // address scrambling - ROM_LOAD16_WORD_SWAP( "m1101.u4", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) + ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) + ROM_LOAD16_WORD_SWAP( "m1101.u4", 0x000000, 0x400000, CRC(0114e9d1) SHA1(5b16170d3cd8b8e1662c949b7234fbdd2ca927f7) ) // FIXED BITS (0xxxxxxxxxxxxxxx) - ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) // light address scrambling + ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "text.u6", 0x00000, 0x80000, CRC(40d21adf) SHA1(18b202d6330ac89026bec2c9c8224b52540dd48d) ) ROM_REGION( 0x80000, "oki", 0 ) - ROM_LOAD( "s1102.u20", 0x00000, 0x80000, CRC(51ffe245) SHA1(849011b186096add657ab20d49d260ec23363ef3) ) // = s1102.u23 Mahjong Long Hu Zhengba 2 + ROM_LOAD( "s1102.u20", 0x00000, 0x80000, CRC(51ffe245) SHA1(849011b186096add657ab20d49d260ec23363ef3) ) // = s1102.u23 Long Hu Zhengba 2 + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "slqz2_string.key", 0x00, 0xec, CRC(5ca22f9d) SHA1(a795415016fdcb6329623786dc992ac7b0877ddf) ) ROM_END /*************************************************************************** -Mahjong Man Guan Daheng (V123T1) +Man Guan Daheng (V123T1) 滿貫大亨 (Mǎn Guàn Dàhēng) (c) 1997 IGS PCB Layout ---------- -IGS PCB NO- 0252 +IGS PCB NO-0252 |----------------------------------| | S1002.U22 6264 62256 SW | |TDA1020 FLASH.U19 PAL BATT| @@ -4789,7 +5316,7 @@ ROM_START( mgdha ) ROM_LOAD16_WORD_SWAP( "flash.u19", 0x00000, 0x80000, CRC(ff3aed2c) SHA1(829140e6fc7e4dfc039b0e7b647ce26d59b23b3d) ) ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "m1001.u4", 0x000000, 0x400000, CRC(0cfb60d6) SHA1(e099aca730e7fd91a72915c27e569ad3d21f0d8f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) + ROM_LOAD( "m1001.u4", 0x000000, 0x400000, CRC(0cfb60d6) SHA1(e099aca730e7fd91a72915c27e569ad3d21f0d8f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) ROM_REGION( 0x20000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD16_WORD_SWAP( "text.u6", 0x00000, 0x20000, CRC(db50f8fc) SHA1(e2ce4a42f5bdc0b4b7988ad9e8d14661f17c3d51) ) @@ -4800,12 +5327,12 @@ ROM_END /*************************************************************************** -Mahjong Man Guan Da Heng (V125T1) +Man Guan Daheng (V125T1) 滿貫大亨 (Mǎn Guàn Dàhēng) (c) 1997 IGS No hardware info, no sprites rom for this set. -It has additional protection. +It has an additional game id check at the start. ***************************************************************************/ @@ -4815,10 +5342,10 @@ ROM_START( mgdh ) ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) // not in this set - ROM_LOAD( "m1001.u4", 0x000000, 0x400000, CRC(0cfb60d6) SHA1(e099aca730e7fd91a72915c27e569ad3d21f0d8f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) + ROM_LOAD( "m1001.u4", 0x000000, 0x400000, CRC(0cfb60d6) SHA1(e099aca730e7fd91a72915c27e569ad3d21f0d8f) ) // FIXED BITS (xxxxxxx0xxxxxxxx) ROM_REGION( 0x20000, "igs017_igs031:tilemaps", 0 ) - ROM_LOAD( "igs_512e.u6", 0x00000, 0x20000, CRC(db50f8fc) SHA1(e2ce4a42f5bdc0b4b7988ad9e8d14661f17c3d51) ) // == text.u6 + ROM_LOAD( "igs_512e.u6", 0x00000, 0x20000, CRC(db50f8fc) SHA1(e2ce4a42f5bdc0b4b7988ad9e8d14661f17c3d51) ) // == text.u6 ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "ig2_8836.u14", 0x00000, 0x80000, CRC(ac1f4da8) SHA1(789a2e0b58750292909dabca42c7e5ad72af3db5) ) @@ -4826,7 +5353,7 @@ ROM_END /*************************************************************************** -Taishan (Tarzan) Chuang Tian Guan +Taishan (Tarzan) Chuang Tian Guan (V109C) IGS 1999 PCB Layout @@ -4881,9 +5408,12 @@ ROM_START( tarzanc ) ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "igs_s2102_sp_v102.u14", 0x00000, 0x80000, CRC(90dda82d) SHA1(67fbc1e8d76b85e124136e2f1df09c8b6c5a8f97) ) - ROM_REGION( 0x2dd * 2, "plds", 0 ) + ROM_REGION( 0x2dd * 2, "plds", ROMREGION_ERASE ) ROM_LOAD( "eg.u20", 0x000, 0x2dd, NO_DUMP ) ROM_LOAD( "eg.u21", 0x2dd, 0x2dd, NO_DUMP ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "tarzan_string.key", 0x00, 0xec, CRC(595fe40c) SHA1(0b46983400d237d8bde97a72eaa99b718a03387e) ) ROM_END // sets below are guesswork, assembled from partial dumps... @@ -4893,7 +5423,7 @@ ROM_START( tarzan ) ROM_REGION( 0x40000, "maincpu", 0 ) // V109C TARZAN C (same as tarzanc set) ROM_LOAD( "0228-u16.bin", 0x00000, 0x40000, CRC(e6c552a5) SHA1(f156de9459833474c85a1f5b35917881b390d34c) ) - ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) + ROM_REGION( 0x80000, "igs017_igs031:sprites", ROMREGION_ERASE ) ROM_LOAD( "sprites.u15", 0x00000, 0x80000, NO_DUMP ) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) @@ -4905,14 +5435,18 @@ ROM_START( tarzan ) ROM_REGION( 0x2dd * 2, "plds", 0 ) ROM_LOAD( "pal1", 0x000, 0x2dd, NO_DUMP ) ROM_LOAD( "pal2", 0x2dd, 0x2dd, NO_DUMP ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "tarzan_string.key", 0x00, 0xec, CRC(595fe40c) SHA1(0b46983400d237d8bde97a72eaa99b718a03387e) ) ROM_END -// IGS NO-0228? +// IGS NO-0228? This allegedly has IGS029 protection ROM_START( tarzana ) - ROM_REGION( 0x80000, "maincpu", 0 ) // V107 TAISAN - ROM_LOAD( "0228-u21.bin", 0x00000, 0x80000, CRC(80aaece4) SHA1(07cad92492c5de36c3915867ed4c6544b1a30c07) ) // 1ST AND 2ND HALF IDENTICAL + ROM_REGION( 0x40000, "maincpu", 0 ) // V107 TAISAN + ROM_LOAD( "0228-u21.bin", 0x00000, 0x40000, CRC(80aaece4) SHA1(07cad92492c5de36c3915867ed4c6544b1a30c07) ) // 1ST AND 2ND HALF IDENTICAL + ROM_IGNORE( 0x40000 ) - ROM_REGION( 0x80000, "igs017_igs031:sprites", 0 ) + ROM_REGION( 0x80000, "igs017_igs031:sprites", ROMREGION_ERASE ) ROM_LOAD( "sprites.u17", 0x00000, 0x80000, NO_DUMP ) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) @@ -4921,9 +5455,12 @@ ROM_START( tarzana ) ROM_REGION( 0x40000, "oki", ROMREGION_ERASE ) ROM_LOAD( "sound.u16", 0x00000, 0x40000, NO_DUMP ) - ROM_REGION( 0x2dd * 2, "plds", 0 ) + ROM_REGION( 0x2dd * 2, "plds", ROMREGION_ERASE ) ROM_LOAD( "pal1", 0x000, 0x2dd, NO_DUMP ) ROM_LOAD( "pal2", 0x2dd, 0x2dd, NO_DUMP ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "tarzan_string.key", 0x00, 0xec, CRC(595fe40c) SHA1(0b46983400d237d8bde97a72eaa99b718a03387e) ) ROM_END /*************************************************************************** @@ -4977,37 +5514,48 @@ IGS PCB NO-0230-1 ROM_START( starzan ) ROM_REGION( 0x40000, "maincpu", 0 ) - ROM_LOAD( "v100i.u9", 0x00000, 0x40000, CRC(64180bff) SHA1(b08dbe8a17ca33024442ebee41f111c8f98a2109) ) + ROM_LOAD( "sp_tarzan_v100i.u9", 0x00000, 0x40000, CRC(64180bff) SHA1(b08dbe8a17ca33024442ebee41f111c8f98a2109) ) - ROM_REGION( 0x400000, "igs017_igs031:sprites", ROMREGION_ERASEFF ) - ROM_LOAD( "c0057209.u3", 0x00000, 0x400000, NO_DUMP ) // this is also probably the same as tarzanc. Current theory is the 0x400000 mask ROM at u3 is the same for all games of the same type, with EPROM at u2 providing an overlay for game specific sprites - ROM_LOAD( "cg.u2", 0x00000, 0x080000, CRC(884f95f5) SHA1(2e526aa966e90dc696a8b392a5a99e14f03c4bd4) ) // FIXED BITS (xxxxxxx0xxxxxxxx) + ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) + ROM_LOAD( "igs_a2104_cg_v110.u3", 0x000000, 0x400000, BAD_DUMP CRC(dcbff16f) SHA1(2bf77ef4448c26124c8d8d18bb7ffe4105cfa940) ) // FIXED BITS (xxxxxxx0xxxxxxxx), not dumped for this board, but same label as the one from tarzanc, assuming same contents for now + ROM_LOAD( "sp_tarzan_cg.u2", 0x200000, 0x080000, CRC(884f95f5) SHA1(2e526aa966e90dc696a8b392a5a99e14f03c4bd4) ) // FIXED BITS (xxxxxxx0xxxxxxxx), overlay (handwritten label) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) - ROM_LOAD( "t2105_cg_v110.u11", 0x00000, 0x80000, BAD_DUMP CRC(1d4be260) SHA1(6374c61735144b3ff54d5e490f26adac4a10b14d) ) // not dumped for this board, but same label as the one from tarzanc, assuming same contents for now + ROM_LOAD( "igs_t2105_cg_v110.u11", 0x00000, 0x80000, BAD_DUMP CRC(1d4be260) SHA1(6374c61735144b3ff54d5e490f26adac4a10b14d) ) // not dumped for this board, but same label as the one from tarzanc, assuming same contents for now ROM_REGION( 0x80000, "oki", 0 ) - ROM_LOAD( "s2102_sp_v102.u8", 0x00000, 0x80000, BAD_DUMP CRC(90dda82d) SHA1(67fbc1e8d76b85e124136e2f1df09c8b6c5a8f97) ) // not dumped for this board, but same label as the one from tarzanc, assuming same contents for now + ROM_LOAD( "igs_s2102_sp_v102.u8", 0x00000, 0x80000, BAD_DUMP CRC(90dda82d) SHA1(67fbc1e8d76b85e124136e2f1df09c8b6c5a8f97) ) // not dumped for this board, but same label as the one from tarzanc, assuming same contents for now - ROM_REGION( 0x2dd * 2, "plds", 0 ) - ROM_LOAD( "palce22v10h_tar97_u10-1.u10", 0x000, 0x2dd, NO_DUMP ) - ROM_LOAD( "palce22v10h_tar97_u20.u20", 0x2dd, 0x2dd, NO_DUMP ) + ROM_REGION( 0x2dd * 2, "plds", ROMREGION_ERASE ) + ROM_LOAD( "palce22v10h_tar97_u10-1.u10", 0x000, 0x2dd, NO_DUMP ) // read protected + ROM_LOAD( "palce22v10h_tar97_u20.u20", 0x2dd, 0x2dd, NO_DUMP ) // "" + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "starzan_string.key", 0x00, 0xec, CRC(b33f5050) SHA1(900d3c48944dbdd95d9e48d74c355e82e00ac012) ) ROM_END -// IGS PCB NO-0281 -// Main CPU is a Zilog Z180 clocked @16MHz (XTAL and EXTAL pins directly tied to a 16MHz crystal) -// OKI MSM6295 (actually a rebadged one marked 'K668 0003') clocked @1MHz, pin 7 is HIGH -// A QFP208 custom ASIC marked 'IGS 031' -// A PLCC68 custom IC marked 'IGS025 A9B2201 9931' -// A Ni-MH 3.6V battery as seen in other IGS hardware +/*************************************************************************** + +Happy Skill (Italy, V611IT) + +IGS PCB NO-0281 + +Main CPU is a Zilog Z180 clocked @16MHz (XTAL and EXTAL pins directly tied to a 16MHz crystal) +OKI MSM6295 (actually a rebadged one marked 'K668 0003') clocked @1MHz, pin 7 is HIGH +A QFP208 custom ASIC marked 'IGS 031' +A PLCC68 custom IC marked 'IGS025 A9B2201 9931' (label: '590H/S V300') +A Ni-MH 3.6V battery as seen in other IGS hardware + +***************************************************************************/ + ROM_START( happyskl ) ROM_REGION( 0x40000, "maincpu", 0 ) - ROM_LOAD( "v611.u8", 0x00000, 0x40000, CRC(1fb3da98) SHA1(60674af9f5c53298b8ef856f1986c905b9bd7b96) ) + ROM_LOAD( "v611.u9", 0x00000, 0x40000, CRC(1fb3da98) SHA1(60674af9f5c53298b8ef856f1986c905b9bd7b96) ) // handwritten label ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) - ROM_LOAD( "igs_a2701_cg_v100.u3", 0x00000, 0x400000, CRC(f3756a51) SHA1(8dd4677584f309cec4b068be9f9370a7a172a031) ) // FIXED BITS (xxxxxxx0xxxxxxxx) - 1xxxxxxxxxxxxxxxxxxxxx = 0x00 - ROM_LOAD( "happyskill_cg.u2", 0x00000, 0x080000, CRC(297a1893) SHA1(9be9e2cdaba1615ea376f3fb7087bf990e68b3b4) ) // FIXED BITS (xxxxxxx0xxxxxxxx) + ROM_LOAD( "igs_a2701_cg_v100.u3", 0x000000, 0x400000, CRC(f3756a51) SHA1(8dd4677584f309cec4b068be9f9370a7a172a031) ) // FIXED BITS (xxxxxxx0xxxxxxxx) - 1xxxxxxxxxxxxxxxxxxxxx = 0x00 + ROM_LOAD( "happyskill_cg.u2", 0x200000, 0x080000, CRC(297a1893) SHA1(9be9e2cdaba1615ea376f3fb7087bf990e68b3b4) ) // FIXED BITS (xxxxxxx0xxxxxxxx) ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) ROM_LOAD( "happyskill_text.u11", 0x00000, 0x80000, CRC(c6f51041) SHA1(81a9a03e92c1c67f299113dec9e05ba77395ea31) ) @@ -5015,55 +5563,56 @@ ROM_START( happyskl ) ROM_REGION( 0x80000, "oki", 0 ) ROM_LOAD( "igs_s2702_sp_v100.u8", 0x00000, 0x80000, CRC(0ec9b1b5) SHA1(b8c7e068ddf6777a184339e6796be33e442a3df4) ) - ROM_REGION( 0x2dd * 2, "plds", 0 ) - ROM_LOAD( "atf22v10c.u10", 0x000, 0x2dd, NO_DUMP ) - ROM_LOAD( "peel22cv10a.u20", 0x2dd, 0x2dd, NO_DUMP ) + ROM_REGION( 0x2dd * 2, "plds", ROMREGION_ERASE ) + ROM_LOAD( "atf22v10c.u10", 0x000, 0x2dd, NO_DUMP ) + ROM_LOAD( "et_u20-c.u20", 0x2dd, 0x2dd, NO_DUMP ) // peel22cv10a ROM_END // PCB was heavily corroded and not working -ROM_START( unkigs ) +ROM_START( cpoker2 ) ROM_REGION( 0x40000, "maincpu", 0 ) ROM_LOAD( "u9.bin", 0x00000, 0x40000, CRC(8d79eb4d) SHA1(9cad09013f83335ec78c3ff78715bc5d9a989eb7) ) ROM_REGION( 0x400000, "igs017_igs031:sprites", 0 ) // the following ROM wasn't readable on this PCB, but it's the same as the one in happyskl. Assuming same contents for now ROM_LOAD( "igs_a2701_cg_v100.u3", 0x00000, 0x400000, BAD_DUMP CRC(f3756a51) SHA1(8dd4677584f309cec4b068be9f9370a7a172a031) ) // FIXED BITS (xxxxxxx0xxxxxxxx) - 1xxxxxxxxxxxxxxxxxxxxx = 0x00 - //ROM_LOAD( "u2", 0x00000, 0x080000, NO_DUMP ) // not populated. Never there or removed? Possibly never there, current theory is the 0x400000 mask ROM at u3 is the same for all games of the same type, with EPROM at u2 providing an overlay for game specific sprites + // U2 (overlay) not populated - ROM_REGION( 0x40000, "igs017_igs031:tilemaps", 0 ) - ROM_LOAD( "u11.bin", 0x00000, 0x40000, CRC(34475c83) SHA1(376ff68d89c25471483b074dcf7542f42f954e67) ) - ROM_IGNORE(0x040000) // 1xxxxxxxxxxxxxxxxxx = 0x00 + ROM_REGION( 0x80000, "igs017_igs031:tilemaps", 0 ) + ROM_LOAD( "u11.bin", 0x00000, 0x80000, CRC(34475c83) SHA1(376ff68d89c25471483b074dcf7542f42f954e67) ) // 1xxxxxxxxxxxxxxxxxx = 0x00 - ROM_REGION( 0x80000, "oki", 0 ) // same as happyskl - ROM_LOAD( "igs_s2702_sp_v100.u8", 0x00000, 0x80000, CRC(0ec9b1b5) SHA1(b8c7e068ddf6777a184339e6796be33e442a3df4) ) + ROM_REGION( 0x80000, "oki", 0 ) + ROM_LOAD( "igs_s2702_sp_v100.u8", 0x00000, 0x80000, CRC(0ec9b1b5) SHA1(b8c7e068ddf6777a184339e6796be33e442a3df4) ) // same as happyskl - ROM_REGION( 0x2dd * 2, "plds", 0 ) - ROM_LOAD( "peel22cv10h.u10", 0x000, 0x2dd, NO_DUMP ) - ROM_LOAD( "peel22cv10h.u20", 0x2dd, 0x2dd, NO_DUMP ) + ROM_REGION( 0x2dd * 2, "plds", ROMREGION_ERASE ) + ROM_LOAD( "peel22cv10h.u10", 0x000, 0x2dd, NO_DUMP ) // PALCE22V10H-25P + ROM_LOAD( "peel22cv10h.u20", 0x2dd, 0x2dd, NO_DUMP ) // PALCE22V10H-25P ROM_END /*************************************************************************** -Super Poker (v100xD03) / Formosa +Super Poker (V100xD03) / Formosa PCB NO-0187 CPU Z8018008psc IGS017 -IGS025 +IGS025 (labels: B2 / FORMOSA) K668 (AD-65) UM3567 (YM2413) -Audio Xtal 3.579545 -CPU Xtal 16Mhz -3 x DSW8 +Audio Xtal 3.579545 MHz +CPU Xtal 16 MHz +3 x DSW8 (SW1-SW3) +Push Button (SW4) +3.6V Battery + Toggle Switch (SW5) ***************************************************************************/ ROM_START( spkrform ) ROM_REGION( 0x40000, "maincpu", 0 ) - ROM_LOAD( "super2in1-v100xd03.u29", 0x00000, 0x40000, CRC(e8f7476c) SHA1(e20241d68d22ee01a65f5d7921fe2291077f081f) ) + ROM_LOAD( "super2in1_v100xd03.u29", 0x00000, 0x40000, CRC(e8f7476c) SHA1(e20241d68d22ee01a65f5d7921fe2291077f081f) ) ROM_REGION( 0x100000, "igs017_igs031:sprites", 0 ) ROM_LOAD( "super2in1.u26", 0x00000, 0x80000, CRC(af3b1d9d) SHA1(ce84b076939d2c9d959cd430d4f5664f32735d60) ) // FIXED BITS (xxxxxxxx0xxxxxxx) @@ -5073,29 +5622,34 @@ ROM_START( spkrform ) ROM_LOAD( "super2in1.u24", 0x00000, 0x40000, CRC(54d68c49) SHA1(faad78779c3a5b4ecb1c733192d9477ce3324f71) ) ROM_REGION( 0x40000, "oki", 0 ) - ROM_LOAD( "super2in1sp.u28", 0x00000, 0x40000, CRC(33e6089d) SHA1(cd1ad01e92c18bbeab3fe3ea9152f8b0a3eb1b29) ) + ROM_LOAD( "super2in1_sp.u28", 0x00000, 0x40000, CRC(33e6089d) SHA1(cd1ad01e92c18bbeab3fe3ea9152f8b0a3eb1b29) ) + + ROM_REGION( 0x2dd, "plds", ROMREGION_ERASE ) + ROM_LOAD( "dn.u18", 0x000, 0x2dd, NO_DUMP ) + + ROM_REGION( 0xec, "igs_string", 0 ) + ROM_LOAD( "spkrform_string.key", 0x00, 0xec, CRC(17a9021a) SHA1(41943e08f9c9be49fc3705e6f2702d504ec6d078) ) ROM_END +} // anonymous namespace -GAME( 1996, iqblocka, iqblock, iqblocka, iqblocka, igs017_state, init_iqblocka, ROT0, "IGS", "Shuzi Leyuan (V127M, gambling)", 0 ) -GAME( 1997, iqblockf, iqblock, iqblockf, iqblockf, igs017_state, init_iqblocka, ROT0, "IGS", "IQ Block (V113FR, gambling)", 0 ) -GAME( 1997, mgdh, 0, mgdha, mgdh, igs017_state, init_mgdh, ROT0, "IGS", "Mahjong Man Guan Daheng (Taiwan, V125T1)", MACHINE_IMPERFECT_COLORS ) // wrong colors in betting screen -GAME( 1997, mgdha, mgdh, mgdha, mgdh , igs017_state, init_mgdha, ROT0, "IGS", "Mahjong Man Guan Daheng (Taiwan, V123T1)", 0 ) -GAME( 1997, sdmg2, 0, sdmg2, sdmg2, igs017_state, init_sdmg2, ROT0, "IGS", "Mahjong Super Da Man Guan II (China, V754C)", 0 ) -GAME( 1997, tjsb, 0, tjsb, tjsb, igs017_state, init_tjsb, ROT0, "IGS", "Mahjong Tian Jiang Shen Bing (V137C)", MACHINE_UNEMULATED_PROTECTION ) -GAME( 1998, genius6, 0, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V110F)", 0 ) -GAME( 1997, genius6a, genius6, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V133F)", 0 ) // clone because it has older copyright year -GAME( 1997, genius6b, genius6, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V132F)", 0 ) // " -GAME( 1998, mgcs, 0, mgcs, mgcs, igs017_state, init_mgcs, ROT0, "IGS", "Mahjong Man Guan Caishen (V103CS)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION | MACHINE_IMPERFECT_SOUND ) -GAME( 1998, lhzb2, 0, lhzb2, lhzb2, igs017_state, init_lhzb2, ROT0, "IGS", "Mahjong Long Hu Zhengba 2 (set 1)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) // 龙虎争霸2 -GAME( 1998, lhzb2a, lhzb2, lhzb2a, lhzb2a, igs017_state, init_lhzb2a, ROT0, "IGS", "Mahjong Long Hu Zhengba 2 (VS221M)", 0 ) // 龙虎争霸2 -GAME( 1998, slqz2, 0, slqz2, slqz2, igs017_state, init_slqz2, ROT0, "IGS", "Mahjong Shuang Long Qiang Zhu 2 (VS203J)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) -GAME( 1999, tarzanc, 0, tarzan, iqblocka, igs017_state, init_tarzan, ROT0, "IGS", "Tarzan Chuang Tian Guan (V109C, set 1)", MACHINE_NOT_WORKING ) // IGS031 protection's game specific parameters not emulated yet, sprites' decryption missing, inputs to be done -GAME( 1999, tarzan, tarzanc, tarzan, iqblocka, igs017_state, init_tarzan, ROT0, "IGS", "Tarzan Chuang Tian Guan (V109C, set 2)", MACHINE_NOT_WORKING ) // IGS031 protection's game specific parameters not emulated yet, sprites' decryption missing, inputs to be done -GAME( 1999, tarzana, tarzanc, tarzan, iqblocka, igs017_state, init_tarzana, ROT0, "IGS", "Tarzan (V107)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) // IGS029 needs to be emulated, sprites' decryption missing, inputs to be done -GAME( 2000?, starzan, 0, starzan, starzan, igs017_state, init_starzan, ROT0, "IGS (G.F. Gioca license)", "Super Tarzan (Italy, V100I)", MACHINE_NOT_WORKING ) // IGS031 protection's game specific parameters not emulated yet, incomplete dump, sprites' decryption missing -GAME( 2001?, happyskl, 0, starzan, happyskl, igs017_state, init_happyskl, ROT0, "IGS", "Happy Skill (Italy, V611IT)", MACHINE_NOT_WORKING ) // IGS031 protection's game specific parameters not emulated yet, sprites' decryption missing -GAME( 2001?, unkigs, happyskl, starzan, unkigs, igs017_state, init_unkigs, ROT0, "IGS", "unknown IGS game (V100A)", MACHINE_NOT_WORKING ) // possibly titled 'Champion 2', definitely derived from Happy Skill or vice versa, missing ROM, IGS031 protection's game specific parameters not emulated yet, sprites' decryption missing - -// Parent spk306us in driver spoker.cpp. Move this set to that driver? -GAME( ????, spkrform, spk306us, spkrform, spkrform, igs017_state, init_spkrform, ROT0, "IGS", "Super Poker (v100xD03) / Formosa", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) +GAME ( 1996, iqblocka, iqblock, iqblocka, iqblocka, igs017_state, init_iqblocka, ROT0, "IGS", "Shuzi Leyuan (China, V127M, gambling)", 0 ) // 數字樂園 +GAME ( 1997, iqblockf, iqblock, iqblockf, iqblockf, igs017_state, init_iqblocka, ROT0, "IGS", "IQ Block (V113FR, gambling)", 0 ) +GAME ( 1997, mgdh, 0, mgdh, mgdh, igs017_state, init_mgdh, ROT0, "IGS", "Man Guan Daheng (Taiwan, V125T1)", MACHINE_IMPERFECT_COLORS | MACHINE_UNEMULATED_PROTECTION) // 滿貫大亨, wrong colors in betting screen, game id check (patched out) +GAME ( 1997, mgdha, mgdh, mgdha, mgdh, igs017_state, init_mgdha, ROT0, "IGS", "Man Guan Daheng (Taiwan, V123T1)", 0 ) // 滿貫大亨 +GAME ( 1997, sdmg2, 0, sdmg2, sdmg2, igs017_state, init_sdmg2, ROT0, "IGS", "Super Da Man Guan II (China, V754C)", 0 ) +GAME ( 1997, tjsb, 0, tjsb, tjsb, igs017_state, init_tjsb, ROT0, "IGS", "Tian Jiang Shen Bing (China, V137C)", MACHINE_UNEMULATED_PROTECTION ) // 天將神兵, fails the bonus round protection check (if enabled via DSW), see e.g. demo mode +GAME ( 1998, genius6, 0, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V110F)", 0 ) // shows chinese text in puzzle game +GAME ( 1997, genius6a, genius6, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V133F)", 0 ) // clone because it has older copyright year +GAME ( 1997, genius6b, genius6, genius6, genius6, igs017_state, init_iqblocka, ROT0, "IGS", "Genius 6 (V132F)", 0 ) // " +GAME ( 1998, mgcs, 0, mgcs, mgcs, igs017_state, init_mgcs, ROT0, "IGS", "Man Guan Caishen (China, V103CS)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) // 满贯财神, finish IGS029 protection +GAME ( 1998, lhzb2, 0, lhzb2, lhzb2, igs017_state, init_lhzb2, ROT0, "IGS", "Long Hu Zhengba 2 (China, set 1)", MACHINE_UNEMULATED_PROTECTION ) // 龙虎争霸2, finish IGS022 protection +GAME ( 1998, lhzb2a, lhzb2, lhzb2a, lhzb2a, igs017_state, init_lhzb2a, ROT0, "IGS", "Long Hu Zhengba 2 (China, VS221M)", 0 ) // 龙虎争霸2 +GAME ( 1998, slqz2, 0, slqz2, slqz2, igs017_state, init_slqz2, ROT0, "IGS", "Shuang Long Qiang Zhu 2 VS (China, VS203J)", MACHINE_UNEMULATED_PROTECTION ) // 双龙抢珠, finish IGS022 protection +GAME ( 1999, tarzanc, 0, tarzan, tarzan, igs017_state, init_tarzanc, ROT0, "IGS", "Tarzan Chuang Tian Guan (China, V109C, set 1)", 0 ) +GAME ( 1999, tarzan, tarzanc, tarzan, tarzan, igs017_state, init_tarzan, ROT0, "IGS", "Tarzan Chuang Tian Guan (China, V109C, set 2)", MACHINE_NOT_WORKING ) // missing sprites and sound rom, imperfect tiles decryption +GAME ( 1999, tarzana, tarzanc, tarzan, tarzan, igs017_state, init_tarzana, ROT0, "IGS", "Tarzan (V107)", MACHINE_NOT_WORKING | MACHINE_UNEMULATED_PROTECTION ) // missing IGS029 protection, missing sprites and sound rom +GAMEL( 2000?, starzan, 0, starzan, starzan, igs017_state, init_starzan, ROT0, "IGS (G.F. Gioca license)", "Super Tarzan (Italy, V100I)", 0, layout_igsslot ) +GAMEL( 2000?, happyskl, 0, happyskl, happyskl, igs017_state, init_happyskl, ROT0, "IGS", "Happy Skill (Italy, V611IT)", 0, layout_igspoker ) +GAMEL( 2000?, cpoker2, 0, cpoker2, cpoker2, igs017_state, init_cpoker2, ROT0, "IGS", "Champion Poker 2 (V100A)", 0, layout_igspoker ) +GAME ( 2000?, spkrform, spk306us, spkrform, spkrform, igs017_state, init_spkrform, ROT0, "IGS", "Super Poker (V100xD03) / Formosa", MACHINE_UNEMULATED_PROTECTION ) // poker game enabling forced with a patch. Parent spk306us in driver spoker.cpp diff --git a/src/mame/layout/igsslot.lay b/src/mame/layout/igsslot.lay new file mode 100644 index 00000000000..8949bd86859 --- /dev/null +++ b/src/mame/layout/igsslot.lay @@ -0,0 +1,132 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/mame/machine/igs022.cpp b/src/mame/machine/igs022.cpp index 0fabcd00383..d6adb617ea8 100644 --- a/src/mame/machine/igs022.cpp +++ b/src/mame/machine/igs022.cpp @@ -1,17 +1,23 @@ // license:BSD-3-Clause // copyright-holders:David Haywood, ElSemi -/* +/************************************************************************************************************ - IGS022 is an encrypted DMA device, most likely an MCU of some sort - it can safely be swapped between games so doesn't appear to have - any kind of game specific programming + IGS022 is an encrypted DMA device, most likely an MCU of some sort. + It can safely be swapped between games, so doesn't appear to have any kind of game specific programming. -*/ +************************************************************************************************************/ #include "emu.h" #include "igs022.h" +#include -#include +#define LOG_DMA (1U << 1) +#define LOG_STACK (1U << 2) +#define LOG_CMD_6D (1U << 3) + +//#define VERBOSE (LOG_GENERAL | LOG_DMA | LOG_STACK | LOG_CMD_6D) +#define VERBOSE (0) +#include "logmacro.h" igs022_device::igs022_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock) : device_t(mconfig, IGS022, tag, owner, clock) @@ -22,76 +28,105 @@ igs022_device::igs022_device(const machine_config &mconfig, const char *tag, dev void igs022_device::device_start() { - // Reset stuff - std::fill(std::begin(m_kb_regs), std::end(m_kb_regs), 0); - - save_item(NAME(m_kb_regs)); + save_item(NAME(m_regs)); + save_item(NAME(m_stack)); + save_item(NAME(m_stack_ptr)); } void igs022_device::device_reset() { - //printf("igs022_device::device_reset()"); - if (!m_sharedprotram) - { - logerror("m_sharedprotram was not set\n"); - return; - } - IGS022_reset(); + fatalerror("%s: IGS022 sharedprotram was not set!\n", machine().describe_context()); - std::fill(std::begin(m_kb_regs), std::end(m_kb_regs), 0); + // the internal MCU boot code automatically does this DMA + // and puts the version # of the data rom in ram + + // reset regs and stack + std::fill(std::begin(m_regs), std::end(m_regs), 0); + std::fill(std::begin(m_stack), std::end(m_stack), 0); + m_stack_ptr = 0; + + // fill ram with 0xa55a pattern + for (int i = 0; i < 0x4000 / 2; i++) + m_sharedprotram[i] = 0xa55a; + + // the initial auto-DMA + const u16 * const PROTROM = (u16 *)m_rom->base(); + + u16 src = PROTROM[0x100 / 2]; + const u32 dst = PROTROM[0x102 / 2]; + const u16 size = PROTROM[0x104 / 2]; + u16 mode = PROTROM[0x106 / 2]; + + mode = (mode >> 8) | (mode << 8); + + src >>= 1; + + do_dma(src, dst, size, mode); + + // there is also a version ID? (or is it some kind of checksum) that is stored in the data rom, and gets copied.. + // Dragon World 3 checks it + // Setting 0x3002a0 to #3 causes Dragon World 3 to skip this check + m_sharedprotram[0x2a2 / 2] = PROTROM[0x114 / 2]; } - -void igs022_device::IGS022_do_dma(u16 src, u16 dst, u16 size, u16 mode) +// From IGS022 ROM to shared protection RAM +void igs022_device::do_dma(u16 src, u16 dst, u16 size, u16 mode) { - //printf("igs022_device::IGS022_do_dma\n"); + LOGMASKED(LOG_DMA, "%s: IGS022 DMA src %04x, dst %04x, size %04x, mode %04x\n", machine().describe_context(), src, dst, size, mode); /* - P_SRC =0x300290 (offset from prot rom base) - P_DST =0x300292 (words from 0x300000) - P_SIZE=0x300294 (words) - P_MODE=0x300296 + P_SRC = 0x300290 (offset from prot rom base) + P_DST = 0x300292 (words from 0x300000) + P_SIZE = 0x300294 (words) + P_MODE = 0x300296 - Mode 5 direct - Mode 6 swap nibbles and bytes - - 1,2,3 table based ops + Mode 0 plain copy + Mode 1,2,3 rom table based ops + Mode 4 fixed data ('IGS ') based ops + Mode 5 swap bytes + Mode 6 swap nibbles */ const u16 param = mode >> 8; - // the initial DMA on kilbld has 0x10 set, drgw3 has 0x18 set, not sure how they affect the operation. - if (mode & 0x00f8) printf("IGS022_do_dma mode bits %04x set\n", mode & 0x00f8); + // the initial auto-DMA on killbld/slqz2/lhzb2 has 0x10 set, drgw3 has 0x18 set, not sure how they affect the operation. + if (mode & 0x00f8) + logerror("%s: IGS022 unknown DMA mode bits %04x set\n", machine().describe_context(), mode & 0x00f8); - mode &= 0x7; // what are the other bits? + mode &= 0x7; // what are the other bits? - if ((mode == 0) || (mode == 1) || (mode == 2) || (mode == 3) || (mode == 4)) + const u16 * const PROTROM = (u16 *)m_rom->base(); + + switch (mode) { - /* mode3 applies a xor from a 0x100 byte table to the data being - transferred + case 0: case 1: case 2: case 3: case 4: + /* + modes 1-3 modify the data being transferred using a 0x100 byte table stored at the start of the protection rom. - the table is stored at the start of the protection rom. + The param used with the mode gives a start offset into the table. - the param used with the mode gives a start offset into the table - - odd offsets cause an overflow + Odd offsets cause an overflow. */ - - const u16 *PROTROM = (u16*)m_rom->base(); - for (int x = 0; x < size; x++) { - u16 dat2 = PROTROM[src + x]; + u16 dat = PROTROM[src + x]; - const u8 extraoffset = param & 0xff; - const u8* dectable = (u8*)m_rom->base(); // the basic decryption table is at the start of the mcu data rom! - const u8 taboff = ((x * 2) + extraoffset) & 0xff; // must allow for overflow in instances of odd offsets - u16 extraxor = ((dectable[taboff + 1]) << 8) | (dectable[taboff + 0] << 0); + const u8 extraoffset = param & 0xff; + const u8 * const dectable = (u8 *)m_rom->base(); // the basic decryption table is at the start of the mcu data rom! + const u8 taboff = ((x * 2) + extraoffset) & 0xff; // must allow for overflow in instances of odd offsets - if (mode == 4) + u16 extraxor = ((dectable[taboff + 1]) << 8) | (dectable[taboff + 0] << 0); + + switch (mode) { +// case 0: plain copy + case 1: dat -= extraxor; break; + case 2: dat += extraxor; break; + case 3: dat ^= extraxor; break; + case 4: extraxor = 0; + if ((x & 0x003) == 0x000) extraxor |= 0x0049; // 'I' if ((x & 0x003) == 0x001) extraxor |= 0x0047; // 'G' if ((x & 0x003) == 0x002) extraxor |= 0x0053; // 'S' @@ -101,166 +136,273 @@ void igs022_device::IGS022_do_dma(u16 src, u16 dst, u16 size, u16 mode) if ((x & 0x300) == 0x100) extraxor |= 0x4700; // 'G' if ((x & 0x300) == 0x200) extraxor |= 0x5300; // 'S' if ((x & 0x300) == 0x300) extraxor |= 0x2000; // ' ' + + LOGMASKED(LOG_DMA, "%s: IGS022 DMA mode 4 -> %06x | %04x (%04x)\n", machine().describe_context(), (dst + x) * 2, dat, (u16)(dat - extraxor)); + + dat -= extraxor; + break; } - // mode == 0 plain - if (mode == 3) dat2 ^= extraxor; - if (mode == 2) dat2 += extraxor; - if (mode == 1) dat2 -= extraxor; - - if (mode == 4) - { - //printf("%06x | %04x (%04x)\n", (dst+x)*2, dat2, (u16)(dat2-extraxor)); - - dat2 -= extraxor; - } - - m_sharedprotram[dst + x] = dat2; + m_sharedprotram[dst + x] = dat; } - } - else if (mode == 5) - { - /* mode 5 seems to be a byteswapped copy */ - const u16 *PROTROM = (u16*)m_rom->base(); + break; + + case 5: // byteswapped copy for (int x = 0; x < size; x++) { u16 dat = PROTROM[src + x]; + dat = ((dat &0x00ff) << 8) | ((dat &0xff00) >> 8); m_sharedprotram[dst + x] = dat; } - } - else if (mode == 6) - { - /* mode 6 seems to be a nibble swapped copy */ - const u16 *PROTROM = (u16*)m_rom->base(); + break; + + case 6: // nibble swapped copy for (int x = 0; x < size; x++) { u16 dat = PROTROM[src + x]; - dat = ((dat & 0xf0f0) >> 4)| - ((dat & 0x0f0f) << 4); + dat = ((dat & 0xf0f0) >> 4) | ((dat & 0x0f0f) << 4); m_sharedprotram[dst + x] = dat; } + break; + + case 7: + logerror("%s: IGS022 DMA unhandled copy mode %04x!\n", machine().describe_context(), mode); + // not used by killbld + // weird mode, the params get left in memory? - maybe it's a NOP? + break; + + default: + logerror("%s: IGS022 DMA unhandled copy mode!: %d, src: %04x, dst: %04x, size: %04x, param: %02x\n", machine().describe_context(), mode, src, dst, size, param); + // not used by killbld + // invalid? } - else if (mode == 7) +} + +void igs022_device::push_stack(u32 data) +{ + if (m_stack_ptr < STACK_SIZE - 1) + ++m_stack_ptr; + + m_stack[m_stack_ptr] = data; +} + +u32 igs022_device::pop_stack() +{ + const u32 data = m_stack[m_stack_ptr]; + + if (m_stack_ptr > 0) + --m_stack_ptr; + + return data; +} + +std::string igs022_device::stack_as_string() const +{ + std::ostringstream stream; + stream << "stack:"; + + for (int i = 0; i <= m_stack_ptr; ++i) + util::stream_format(stream, " %08x", m_stack[i]); + + return std::move(stream).str(); +} + +u32 igs022_device::read_reg(u16 offset) +{ + if (offset < NUM_REGS) { - printf("unhandled copy mode %04x!\n", mode); - // not used by killing blade - /* weird mode, the params get left in memory? - maybe it's a NOP? */ + return m_regs[offset]; + } + else if (offset == 0x400) + { + return pop_stack(); } else { - osd_printf_debug("unhandled copy mode %04x!\n", mode); - printf ("DMA MODE: %d, src: %4.4x, dst: %4.4x, size: %4.4x, param: %2.2x\n", mode, src, dst, size, param); - // not used by killing blade - /* invalid? */ + return 0; // Invalid! } } -// the internal MCU boot code automatically does this DMA -// and puts the version # of the data rom in ram -void igs022_device::IGS022_reset() +void igs022_device::write_reg(u16 offset, u32 data) { - const u16 *PROTROM = (u16*)m_rom->base(); - - // fill ram with A5 patern - for (int i = 0; i < 0x4000/2; i++) - m_sharedprotram[i] = 0xa55a; - - // the auto-dma - u16 src = PROTROM[0x100 / 2]; - const u32 dst = PROTROM[0x102 / 2]; - const u16 size = PROTROM[0x104 / 2]; - u16 mode = PROTROM[0x106 / 2]; - - mode &= 0xff; - - src >>= 1; - - IGS022_do_dma(src,dst,size,mode); - - // there is also a version ID? (or is it some kind of checksum) that is stored in the data rom, and gets copied.. - // Dragon World 3 checks it - // Setting $3002a0 to #3 causes Dragon World 3 to skip this check - m_sharedprotram[0x2a2/2] = PROTROM[0x114/2]; + if (offset < NUM_REGS) + { + m_regs[offset] = data; + } + else if (offset == 0x300) + { + push_stack(data); + } + else + { + // Invalid! + } } -void igs022_device::IGS022_handle_command() +// What does this do? write the completion byte for now... +void igs022_device::handle_incomplete_command(u16 cmd, u16 res) { - //printf("igs022_device::IGS022_handle_command\n"); + logerror("%s: IGS022 command %04x: INCOMPLETE (NOP)\n", machine().describe_context(), cmd); + m_sharedprotram[0x202 / 2] = res; +} - const u16 cmd = m_sharedprotram[0x200/2]; +void igs022_device::handle_command() +{ + const u16 cmd = m_sharedprotram[0x200 / 2]; - if (cmd == 0x6d) // Store values to asic ram + switch (cmd) { - const u32 p1 = (m_sharedprotram[0x298/2] << 16) | m_sharedprotram[0x29a/2]; - const u32 p2 = (m_sharedprotram[0x29c/2] << 16) | m_sharedprotram[0x29e/2]; - - if ((p2 & 0xffff) == 0x9) // Set value + case 0x12: // Push { - const int reg = (p2 >> 16) & 0xffff; + const u32 data = (m_sharedprotram[0x288 / 2] << 16) + m_sharedprotram[0x28a / 2]; - if (reg & 0x300) { // 300?? killbld expects 0x200, drgw3 expects 0x100? - m_kb_regs[reg & 0xff] = p1; - } + push_stack(data); + + LOGMASKED(LOG_STACK, "%s: IGS022 command %04x: PUSH {288, 28a} (%08x) %s\n", machine().describe_context(), cmd, data, stack_as_string()); + + m_sharedprotram[0x202 / 2] = 0x23; // this mode complete? + break; } - if ((p2 & 0xffff) == 0x6) // Add value - { - const int src1 = (p1 >> 16) & 0xff; - const int src2 = (p1 >> 0) & 0xff; - const int dst = (p2 >> 16) & 0xff; + case 0x2d: handle_incomplete_command(cmd, 0x3c); break; // killbld - m_kb_regs[dst] = m_kb_regs[src2] - m_kb_regs[src1]; +// case 0x42: break; // killbld + + case 0x45: // Pop + { + const u32 data = pop_stack(); + + m_sharedprotram[0x28c / 2] = (data >> 16) & 0xffff; + m_sharedprotram[0x28e / 2] = data & 0xffff; + + LOGMASKED(LOG_STACK, "%s: IGS022 command %04x: POP {28c, 28e} (%08x) %s\n", machine().describe_context(), cmd, data, stack_as_string()); + + m_sharedprotram[0x202 / 2] = 0x56; // this mode complete? + break; } - if ((p2 & 0xffff) == 0x1) // Add Imm? - { - const int reg = (p2 >> 16) & 0xff; - const int imm = (p1 >> 0) & 0xffff; +// case 0x47: // NOP? slqz2/lhzb2 +// break; - m_kb_regs[reg] += imm; + case 0x4f: // DMA from protection ROM (memcpy with encryption / scrambling) + { + LOGMASKED(LOG_DMA, "%s: IGS022 command %04x: DMA\n", machine().describe_context(), cmd); + + const u16 src = m_sharedprotram[0x290 / 2] >> 1; // External mcu data is 8 bit and addressed as such + const u32 dst = m_sharedprotram[0x292 / 2]; + const u16 size = m_sharedprotram[0x294 / 2]; + const u16 mode = m_sharedprotram[0x296 / 2]; + + do_dma(src, dst, size, mode); + + m_sharedprotram[0x202 / 2] = 0x5e; // this mode complete? + break; } - if ((p2 & 0xffff) == 0xa) // Get value - { - const int reg = (p1 >> 16) & 0xFF; + case 0x5a: handle_incomplete_command(cmd, 0x4b); break; // killbld, uses {284} as input - m_sharedprotram[0x29c/2] = (m_kb_regs[reg] >> 16) & 0xffff; - m_sharedprotram[0x29e/2] = m_kb_regs[reg] & 0xffff; - } + case 0x6d: // Set/Get values to/from ASIC RAM, arithmetic operations on them + handle_command_6d(); + break; - m_sharedprotram[0x202 / 2] = 0x7c; // this mode complete? - } - - // Is this actually what this is suppose to do? Complete guess. - if (cmd == 0x12) // copy?? - { - m_sharedprotram[0x28c / 2] = m_sharedprotram[0x288 / 2]; - m_sharedprotram[0x28e / 2] = m_sharedprotram[0x28a / 2]; - - m_sharedprotram[0x202 / 2] = 0x23; // this mode complete? - } - - // what do these do? write the completion byte for now... - if (cmd == 0x45) m_sharedprotram[0x202 / 2] = 0x56; - if (cmd == 0x5a) m_sharedprotram[0x202 / 2] = 0x4b; - if (cmd == 0x2d) m_sharedprotram[0x202 / 2] = 0x3c; - - if (cmd == 0x4f) // memcpy with encryption / scrambling - { - const u16 src = m_sharedprotram[0x290 / 2] >> 1; // External mcu data is 8 bit and addressed as such - const u32 dst = m_sharedprotram[0x292 / 2]; - const u16 size = m_sharedprotram[0x294 / 2]; - const u16 mode = m_sharedprotram[0x296 / 2]; - - IGS022_do_dma(src,dst,size,mode); - - m_sharedprotram[0x202 / 2] = 0x5e; // this mode complete? + default: + logerror("%s: IGS022 command %04x: UNKNOWN!\n", machine().describe_context(), cmd); } } +// Set/Get values to/from ASIC RAM, arithmetic operations on them +void igs022_device::handle_command_6d() +{ + const u32 p1 = (m_sharedprotram[0x298 / 2] << 16) | m_sharedprotram[0x29a / 2]; + const u32 p2 = (m_sharedprotram[0x29c / 2] << 16) | m_sharedprotram[0x29e / 2]; -DEFINE_DEVICE_TYPE(IGS022, igs022_device, "igs022", "IGS022") + std::ostringstream stream; + util::stream_format(stream, "%s: IGS022 command 006d: ASIC RAM %04x %04x %04x %04x ~ ", machine().describe_context(), + (p1 >> 16) & 0xffff, (p1 >> 0) & 0xffff, (p2 >> 16) & 0xffff, (p2 >> 0) & 0xffff + ); + + switch (p2 & 0xffff) + { + case 0x0: // Add values + { + const u16 src1 = p1 >> 16; + const u16 src2 = p1 >> 0; + const u16 dst = p2 >> 16; + + const u32 data1 = read_reg(src1); + const u32 data2 = read_reg(src2); + const u32 res = data1 + data2; + + write_reg(dst, res); + + util::stream_format(stream, "ADD [%04x] = [%04x] + [%04x] (%08x)\n", dst, src1, src2, res); + break; + } + + case 0x1: // Sub values (src1 - src2) + { + const u16 src1 = p1 >> 16; + const u16 src2 = p1 >> 0; + const u16 dst = p2 >> 16; + + const u32 data1 = read_reg(src1); + const u32 data2 = read_reg(src2); + const u32 res = data1 - data2; + + write_reg(dst, res); + + util::stream_format(stream, "SUB1 [%04x] = [%04x] - [%04x] (%08x)\n", dst, src1, src2, res); + break; + } + + case 0x6: // Sub values (src2 - src1) + { + const u16 src1 = p1 >> 16; + const u16 src2 = p1 >> 0; + const u16 dst = p2 >> 16; + + const u32 data1 = read_reg(src1); + const u32 data2 = read_reg(src2); + const u32 res = data2 - data1; + + write_reg(dst, res); + + util::stream_format(stream, "SUB2 [%04x] = [%04x] - [%04x] (%08x)\n", dst, src2, src1, res); + break; + } + + case 0x9: // Set value (Shared Protection RAM -> ASIC RAM) + { + const u16 dst = p2 >> 16; + + const u32 data = p1; + + write_reg(dst, data); + + util::stream_format(stream, "SET [%04x] = {298, 29a} (%08x)\n", dst, data); + break; + } + + case 0xa: // Get value (ASIC RAM -> Shared Protection RAM) + { + const u16 src = p1 >> 16; + + const u32 data = m_regs[src]; + + m_sharedprotram[0x29c / 2] = (data >> 16) & 0xffff; + m_sharedprotram[0x29e / 2] = data & 0xffff; + + util::stream_format(stream, "GET {29c, 29e} = [%04x] (%08x)\n", src, data); + break; + } + } + + LOGMASKED(LOG_CMD_6D, "%s", stream.str()); + m_sharedprotram[0x202 / 2] = 0x7c; // this mode complete? +} + +DEFINE_DEVICE_TYPE(IGS022, igs022_device, "igs022", "IGS022 encrypted DMA device") diff --git a/src/mame/machine/igs022.h b/src/mame/machine/igs022.h index 619b7a0fc86..5fb2bd9115c 100644 --- a/src/mame/machine/igs022.h +++ b/src/mame/machine/igs022.h @@ -1,33 +1,42 @@ // license:BSD-3-Clause // copyright-holders:David Haywood, ElSemi -/* IGS022 */ #ifndef MAME_MACHINE_IGS022_H #define MAME_MACHINE_IGS022_H #pragma once - class igs022_device : public device_t { public: igs022_device(const machine_config &mconfig, const char *tag, device_t *owner, u32 clock); - void IGS022_handle_command(); + void handle_command(); protected: virtual void device_start() override; virtual void device_reset() override; - u32 m_kb_regs[0x100]; - - void IGS022_do_dma(u16 src, u16 dst, u16 size, u16 mode); - void IGS022_reset(); - private: + static constexpr u16 NUM_REGS = 0x300, STACK_SIZE = 0x100; + u32 m_regs[NUM_REGS]; + u32 m_stack[STACK_SIZE]; + u8 m_stack_ptr; + optional_shared_ptr m_sharedprotram; required_memory_region m_rom; -}; + u32 read_reg(u16 offset); + void write_reg(u16 offset, u32 data); + + void push_stack(u32 data); + u32 pop_stack(); + std::string stack_as_string() const; + + void do_dma(u16 src, u16 dst, u16 size, u16 mode); + + void handle_command_6d(); + void handle_incomplete_command(u16 cmd, u16 res); +}; DECLARE_DEVICE_TYPE(IGS022, igs022_device) diff --git a/src/mame/machine/pgmprot_igs025_igs022.cpp b/src/mame/machine/pgmprot_igs025_igs022.cpp index 29bc98c34a4..0bba9402785 100644 --- a/src/mame/machine/pgmprot_igs025_igs022.cpp +++ b/src/mame/machine/pgmprot_igs025_igs022.cpp @@ -4,25 +4,22 @@ PGM 022 + 025 PGM protection emulation this file contains the game / pgm specifc hookups for the IGS022/IGS025 - protection chips, actual simulation is in igs025_igs022.c + protection chips, actual simulation is in igs022.cpp/igs025.cpp - sed by + Used by: The Killing Blade Dragon World 3 Dragon World 3 EX - ---- - - - - ***********************************************************************/ +************************************************************************/ #include "emu.h" #include "includes/pgm.h" #include "machine/pgmprot_igs025_igs022.h" -/* The IGS022 is an MCU which performs encrypted DMA used by +/* + The IGS022 is an MCU which performs encrypted DMA used by: - The Killing Blade - Dragon World 3 - Dragon World 3 Ex @@ -32,7 +29,7 @@ */ -/* NON-device stuff, game specific, keep here */ +// NON-device stuff, game specific, keep here void pgm_022_025_state::pgm_dw3_decrypt() { @@ -337,7 +334,7 @@ MACHINE_RESET_MEMBER(pgm_022_025_state, dw3) void pgm_022_025_state::igs025_to_igs022_callback( void ) { // printf("igs025_to_igs022_callback\n"); - m_igs022->IGS022_handle_command(); + m_igs022->handle_command(); } @@ -380,7 +377,6 @@ void pgm_022_025_state::pgm_022_025(machine_config &config) m_igs025->set_external_cb(FUNC(pgm_022_025_state::igs025_to_igs022_callback)); IGS022(config, m_igs022, 0); - } void pgm_022_025_state::pgm_022_025_dw3(machine_config &config) @@ -415,6 +411,7 @@ INPUT_PORTS_START( killbld ) PORT_DIPSETTING( 0x0021, DEF_STR( World ) ) INPUT_PORTS_END + INPUT_PORTS_START( dw3 ) PORT_INCLUDE ( pgm ) @@ -428,7 +425,6 @@ INPUT_PORTS_START( dw3 ) PORT_CONFSETTING( 0x0005, DEF_STR( China ) ) PORT_CONFSETTING( 0x0006, DEF_STR( World ) ) PORT_CONFSETTING( 0x0007, "Singapore" ) - INPUT_PORTS_END @@ -445,5 +441,4 @@ INPUT_PORTS_START( dw3j ) // for dw3100 set // PORT_CONFSETTING( 0x0005, DEF_STR( China ) ) // PORT_CONFSETTING( 0x0006, DEF_STR( World ) ) // PORT_CONFSETTING( 0x0007, "Singapore" ) - INPUT_PORTS_END diff --git a/src/mame/mame.lst b/src/mame/mame.lst index 66ad012bdc1..b9ee3a77868 100644 --- a/src/mame/mame.lst +++ b/src/mame/mame.lst @@ -17299,10 +17299,11 @@ wlcc // (c) 1996 xymg // (c) 1996 @source:igs017.cpp +cpoker2 // (c) 2000? genius6 // (c) 1998 genius6a // (c) 1997 genius6b // (c) 1997 -happyskl // (c) 2001? +happyskl // (c) 2000? iqblocka // (c) 1996 iqblockf // (c) 1996 lhzb2 // (c) 1998 @@ -17312,13 +17313,12 @@ mgdh // (c) 1997 mgdha // (c) 1997 sdmg2 // (c) 1997 slqz2 // (c) 1998 -spkrform // (c) ???? +spkrform // (c) 2000? starzan // (c) 2000? tarzan // (c) 1999 tarzana // (c) 1999 tarzanc // (c) 1999 tjsb // (c) 1997 -unkigs // (c) 2001? @source:igspc.cpp eztouch // (c) 200? diff --git a/src/mame/video/igs017_igs031.cpp b/src/mame/video/igs017_igs031.cpp index 2e07c242f63..67acf4e8c0b 100644 --- a/src/mame/video/igs017_igs031.cpp +++ b/src/mame/video/igs017_igs031.cpp @@ -6,7 +6,7 @@ IGS017 / IGS031 video device what's the difference between IGS017 and IGS031? encryption? -all the known IGS017 / IGS031 games use same memory map, is the IGS017 / IGS031 +all the known IGS017 / IGS031 games use the same memory map, is the IGS017 / IGS031 providing the interface to the 8255, or is it coincidence? */ @@ -17,7 +17,6 @@ providing the interface to the 8255, or is it coincidence? void igs017_igs031_device::map(address_map &map) { map(0x1000, 0x17ff).ram().share("spriteram"); -// map(0x1800, 0x1bff).ram() //.w("palette", FUNC(palette_device::write).share("palette"); map(0x1800, 0x1bff).ram().w(FUNC(igs017_igs031_device::palram_w)).share("palram"); map(0x1c00, 0x1fff).ram(); @@ -29,7 +28,6 @@ void igs017_igs031_device::map(address_map &map) map(0x4000, 0x5fff).ram().w(FUNC(igs017_igs031_device::fg_w)).share("fg_videoram"); map(0x6000, 0x7fff).ram().w(FUNC(igs017_igs031_device::bg_w)).share("bg_videoram"); - } u8 igs017_igs031_device::i8255_r(offs_t offset) @@ -260,7 +258,7 @@ void igs017_igs031_device::draw_sprite(bitmap_ind16 &bitmap, const rectangle &cl if (addr + dimx * dimy >= m_sprites_gfx_size) return; - /* Start drawing */ + // Start drawing const u16 pal = 0x100 + (color << 5); const u8 *source_base = &m_sprites_gfx[addr]; const u8 transparent_color = 0x1f; @@ -389,7 +387,7 @@ int igs017_igs031_device::debug_viewer(bitmap_ind16 &bitmap,const rectangle &cli popmessage("a: %08X w: %03X p: %02x-%02x-%02x",a,w,m_sprites_gfx[a/3*3+0],m_sprites_gfx[a/3*3+1],m_sprites_gfx[a/3*3+2]); m_debug_addr = a; m_debug_width = w; - osd_sleep(osd_ticks_per_second() / 1000 * 200); + osd_sleep(osd_ticks_per_second() / 1000 * 200 / 4); return 1; } #endif