From c9f4c658f7db048a5b2b00fc9b80dcf88304e725 Mon Sep 17 00:00:00 2001 From: angelosa Date: Sun, 9 Jun 2024 21:11:34 +0200 Subject: skeleton/swunktarot.cpp: rename to sunwise/anoworld.cpp misc/jankenmn.cpp: move to sunwise folder --- src/mame/mame.lst | 12 +- src/mame/misc/jankenmn.cpp | 444 ------------------------------------ src/mame/skeleton/swunktarot.cpp | 475 --------------------------------------- src/mame/sunwise/anoworld.cpp | 475 +++++++++++++++++++++++++++++++++++++++ src/mame/sunwise/jankenmn.cpp | 444 ++++++++++++++++++++++++++++++++++++ 5 files changed, 925 insertions(+), 925 deletions(-) delete mode 100644 src/mame/misc/jankenmn.cpp delete mode 100644 src/mame/skeleton/swunktarot.cpp create mode 100644 src/mame/sunwise/anoworld.cpp create mode 100644 src/mame/sunwise/jankenmn.cpp diff --git a/src/mame/mame.lst b/src/mame/mame.lst index 12a9df60c3f..f213f4131bb 100644 --- a/src/mame/mame.lst +++ b/src/mame/mame.lst @@ -30617,9 +30617,6 @@ jackpota @source:misc/jaminator.cpp jaminator // 1990 Noise Toys Inc. -@source:misc/jankenmn.cpp -jankenmn // (c) 1985 Sunwise - @source:misc/jokrwild.cpp jokrwild // (c) 1988 Sigma @@ -42264,9 +42261,6 @@ squale // @source:skeleton/sterz80.cpp tongzi -@source:skeleton/swunktarot.cpp -unktarot - @source:skeleton/swyft.cpp swyft // @@ -43013,6 +43007,12 @@ shanghaij // (c) 1988 Sunsoft (Sun Electronics) @source:sunelectronics/tonton.cpp tonton // (c) 199? Success / Taiyo Jidoki. +@source:sunwise/anoworld.cpp +anoworld + +@source:sunwise/jankenmn.cpp +jankenmn // (c) 1985 Sunwise + @source:svi/svi318.cpp svi318 // SVI-318 (PAL) svi318n // SVI-318 (NTSC) diff --git a/src/mame/misc/jankenmn.cpp b/src/mame/misc/jankenmn.cpp deleted file mode 100644 index af95b344fe0..00000000000 --- a/src/mame/misc/jankenmn.cpp +++ /dev/null @@ -1,444 +0,0 @@ -// license:BSD-3-Clause -// copyright-holders:Roberto Fresca, hap -/*************************************************************************** - - JANKENMAN UNIT - - Driver by Roberto Fresca. - With further improvements by MAME Team. - - - Coin-operated Z80-CTC + DAC system. No screen, just artwork with lamps + LEDs. - Janken man is coming from Jankenpon, the rock-paper-scissors game. - There are several versions of this game, the most notable difference being in - the artwork and bonus lamps. The kid's voice and hand are the same among all. - - Control panel is composed of buttons: - Guu (rock), Choki (scissors), Paa (paper). - Some cabs have a Start button and/or Payout button too. - - Info: - http://dgm.hmc6.net/museum/jyankenman.html - http://dgm.hmc6.net/museum/jyankenman_kattaraageru.html - (and many videos on Youtube) - - - Janken Man series (working on this hardware): - - * Janken Man (Pretty Carnival) (3 station prize game), (c) 1985, Sunwise. - * New Janken Man, (c) 1986, Sunwise. - * Janken Man Fever, (c) 1988, Sunwise. - * Janken Man Fever JP, (c) 1991, Sunwise. - * Janken Man JP, (c) 1991, Sunwise. - * Janken Man Kattara Ageru, (c) 1991, Sunwise. - * Janken Man Bubbles, (c) 1992, Sunwise. - * Janken Man Big, (c) 19??, Sunwise. - * Janken Man Lucky!, (c) 199?, Sunwise. - - -**************************************************************************** - - General Notes... - - For better experience, use the hi-res external artwork I made. - - Preview: http://www.robertofresca.com/imagenes/jankenmn_full.png - Artwork: http://mrdo.mameworld.info/artwork/jankenmn.zip - (mirror) http://www.progettoemma.net/mw/jankenmn.zip - -**************************************************************************** - - Hardware Notes... - - 1x LH0080A ; Sharp, Z80A CPU. - 1x LH0082A ; Sharp, Z80 CTC Counter Timer Circuit. - 2x M5L8255AP-5 ; Mitsubishi, PPI 8255 (I/O). - 1x HM6116P-3 ; Hitachi, SRAM. - - 1x 27C128 ; Program, labeled 'PCG1'. - 1x 27C020 ; Waveform (8bit mono unsigned 8192Hz), labeled 'PCG2'. - - 1x AD7523JN ; InterSil, D/A Converter, 8-Bit, Multiplying, 6.7MHz. - 1x LA8358 ; Sanyo, ???. (near volume knob) - 1x 386D NJR ; New Japan Radio, LM386D IC (500mW, 1-Channel Mono Audio AMP). - 3x M54562P ; 8-Unit 500mA source type Darlington Transistor Array with clamp diode. - - 1x 2.500 MHz Xtal. - 1x 8 DIP Switches bank. - - -**************************************************************************** - - Other specs... - - Name of game: Janken Man. - Manufacturer: Sanwaizu Co., Ltd. (Bankruptcy on March 6, 1998) - Year: May 1985 (1985) - Body dimensions: Depth: 355mm, Width: 340mm, Height: 855mm (body only) - Weight: 30kg. - Power: AC 100V 50/60Hz. - Power consumption: 32W - Capacity: 400 game tokens, 200 commemorative tokens - Safe capacity: 6000 coins 10 yen, 500 coins 100 yen. - Coin acceptor: 10 and 100 yens, Manufactured by Asahi Seiko 730-A/BW. - Coin selector: KWM/740 made by Asahi Seiko. - Hopper: MP04975 made by MAX. - Solenoid: AES-112 manufactured by Asahi Seiko. - - -**************************************************************************** - - The waveform is 8bit mono unsigned at 8192Hz. - Sampleset has sounds, music and voice at approximate rom offsets: - - $00c58-$038a4: "jan ken pon!" --> Is the call for rock paper and scissors. - $04d2e-$05a4b: "zuko" --> Is just used for sound effect when player loses. - $05b2d-$08207: "ai ko desho" --> Is the call for rematch when you've drawn. - $08410-$0a9ec: "ooatari" --> "you got it! / perfect!". - $0a9ec-$0c008: "yappii" --> Is just an exclamation of happiness. - $0c008-$0dac0: "attarii" --> "you got it". - - unused PCM data: - - $15db7-$18628: "kakariin o oyobi kudasai" --> "please call the attendant". - $18628-$1a4f3: "keihin ga deru yo" --> "your prize is incoming". - $3c26d-$3f677: "keihin o sentaku shite kudasai" --> "please select your prize". - - -**************************************************************************** - - About lamps... - - The internal layout has lamps mapped the following way: - - digits: - - 0 = Left - 1 = Right - - lamps: - - 00 = Multiplier 1 "attarii" (pays x1) - 01 = Multiplier 2 "ooatari" (pays x2) - - 02 = Rock button LED - 03 = Scissors button LED - 04 = Paper button LED - - 05 = Lose - 06 = Draw - 07 = Win - - 08 = Base Hand - 09 = Paper components - 10 = Paper/Scissors common components - 11 = Rock components - 12 = Scissors components - 13 = Rock/Scissors common components - - 14 = Payout error LED - - Not implemented in the internal layout/artwork: - - 15 = Rotating blue lamp - - -***************************************************************************/ - -#include "emu.h" -#include "cpu/z80/z80.h" -#include "machine/z80daisy.h" -#include "machine/z80ctc.h" -#include "machine/i8255.h" -#include "sound/dac.h" -#include "speaker.h" - -#include "jankenmn.lh" - - -namespace { - -#define MASTER_CLOCK XTAL(2'500'000) - - -class jankenmn_state : public driver_device -{ -public: - jankenmn_state(const machine_config &mconfig, device_type type, const char *tag) - : driver_device(mconfig, type, tag) - , m_maincpu(*this, "maincpu") - , m_digits(*this, "digit%u", 0U) - , m_lamps(*this, "lamp%u", 0U) - { } - - int hopper_status_r(); - - void jankenmn(machine_config &config); - -private: - void lamps1_w(uint8_t data); - void lamps2_w(uint8_t data); - void lamps3_w(uint8_t data); - - virtual void machine_start() override; - - void jankenmn_map(address_map &map); - void jankenmn_port_map(address_map &map); - - required_device m_maincpu; - output_finder<2> m_digits; - output_finder<16> m_lamps; -}; - - -/********************************************* -* Read/Write Handlers * -*********************************************/ - -static constexpr uint8_t led_map[16] = // 7748 IC? - { 0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7c, 0x07, 0x7f, 0x67, 0x58, 0x4c, 0x62, 0x69, 0x78, 0x00 }; - -void jankenmn_state::lamps1_w(uint8_t data) -{ - // hand state: d0: rock, d1: scissors, d2: paper - m_lamps[8] = (data & 7) != 0; - m_lamps[11] = BIT(data, 0); - m_lamps[12] = BIT(data, 1); - m_lamps[9] = BIT(data, 2); - m_lamps[10] = (data & 6) != 0; - m_lamps[13] = (data & 3) != 0; - - // d4-d7: led7seg (remaining credits) right digit - m_digits[1] = led_map[(data >> 4) & 0x0f]; - - // d3: ? (only set if game is over) -} - -void jankenmn_state::lamps2_w(uint8_t data) -{ - // button LEDs: d1: paper, d2: scissors, d3: rock - m_lamps[2] = BIT(data, 3); - m_lamps[3] = BIT(data, 2); - m_lamps[4] = BIT(data, 1); - - // lamps: d5: draw, d6: lose, d7: win - m_lamps[5] = BIT(data, 6); - m_lamps[6] = BIT(data, 5); - m_lamps[7] = BIT(data, 7); - - // d4: payout error LED - m_lamps[14] = BIT(data, 4); - - // d0: led7seg (remaining credits) left digit - m_digits[0] = led_map[data & 1]; -} - -void jankenmn_state::lamps3_w(uint8_t data) -{ - // d1: blue rotating lamp on top of cab - m_lamps[15] = BIT(data, 1); - - // d2: payout (waits for hopper status) - machine().bookkeeping().coin_counter_w(2, data & 0x04); - - // d3: right multiplier lamp(2), d4: left multiplier lamp(1) - m_lamps[0] = BIT(data, 4); - m_lamps[1] = BIT(data, 3); - - // d5: assume coin lockout - machine().bookkeeping().coin_lockout_global_w(~data & 0x20); - - // d0, d6, d7: N/C? - if (data & 0x04) - logerror("payout: %02X\n", (data & 0x04)); -} - -int jankenmn_state::hopper_status_r() -{ - // temp workaround, needs hopper - return machine().rand(); -} - -void jankenmn_state::machine_start() -{ - m_digits.resolve(); - m_lamps.resolve(); -} - - -/********************************************* -* Memory Map Definition * -*********************************************/ - -void jankenmn_state::jankenmn_map(address_map &map) -{ - map(0x0000, 0xbfff).rom(); - map(0xc000, 0xc7ff).ram(); - map(0xe000, 0xffff).rom(); -} - -void jankenmn_state::jankenmn_port_map(address_map &map) -{ - map.global_mask(0xff); - map(0x00, 0x03).rw("ctc", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); - map(0x10, 0x13).rw("ppi8255_0", FUNC(i8255_device::read), FUNC(i8255_device::write)); - map(0x20, 0x23).rw("ppi8255_1", FUNC(i8255_device::read), FUNC(i8255_device::write)); - map(0x30, 0x30).nopw(); // ??? -} - -/* - Writes to port 30h.... - - They are coming from different code chunks, but seems that at least - they have different functions. Writes from 00B6h are unknown, whilst - others coming from 00D6h are counters. Sometimes whilst one increase, - the other one decrease. Writes coming from 0103h seems to clear (00) - or just end whatever the command sent. - - Other behaviours could point to be different counters. - - Also when you win, and the multipliers start to run, a lot of data - is written to the port. Maybe is a leftover, or just a connector to - hook the multiplier's 'roulette style' matrix lamps for other Janken - Man games... - - ':maincpu' (00B6): unmapped io memory write to 0030 = 01 & FF - ':maincpu' (00D6): unmapped io memory write to 0030 = 2F & FF - ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF - - ':maincpu' (00B6): unmapped io memory write to 0030 = F4 & FF - ':maincpu' (00D6): unmapped io memory write to 0030 = 30 & FF - ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF - - ':maincpu' (00B6): unmapped io memory write to 0030 = E7 & FF - ':maincpu' (00D6): unmapped io memory write to 0030 = 31 & FF - ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF - - ':maincpu' (00B6): unmapped io memory write to 0030 = DA & FF - ':maincpu' (00D6): unmapped io memory write to 0030 = 32 & FF - ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF - - ':maincpu' (00B6): unmapped io memory write to 0030 = CD & FF - ':maincpu' (00D6): unmapped io memory write to 0030 = 33 & FF - ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF - - - Need more analysis... - -*/ - -/********************************************* -* Input Ports Definitions * -*********************************************/ - -static INPUT_PORTS_START( jankenmn ) - PORT_START("IN0") - PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_NAME("Guu (Rock)") - PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_NAME("Choki (Scissors)") - PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_NAME("Paa (Paper)") - PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_UNKNOWN ) - PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_COIN3 ) // 100 yen coin - PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_MEMBER(jankenmn_state, hopper_status_r) - PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_COIN2 ) // 10 yen coin - PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_COIN1 ) // 10 yen coin - - PORT_START("DSW") - PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("DSW:7,8") - PORT_DIPSETTING( 0x00, "Lamp Test" ) - PORT_DIPSETTING( 0x02, DEF_STR( 3C_1C ) ) // or 4 credits on 100 yen - PORT_DIPSETTING( 0x01, DEF_STR( 2C_1C ) ) // or 6 credits on 100 yen - PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) // or 11 credits on 100 yen - PORT_DIPNAME( 0x04, 0x04, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:6") - PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x08, 0x08, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:5") - PORT_DIPSETTING( 0x08, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x10, 0x10, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:4") - PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x20, 0x20, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:3") - PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x40, 0x40, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:2") - PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:1") - PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x00, DEF_STR( On ) ) - -INPUT_PORTS_END - - -/********************************************* -* Daisy Chain Interrupts Interface * -*********************************************/ - -static const z80_daisy_config daisy_chain[] = -{ - { "ctc" }, - { nullptr } -}; - - -/********************************************* -* Machine Config * -*********************************************/ - -void jankenmn_state::jankenmn(machine_config &config) -{ - /* basic machine hardware */ - Z80(config, m_maincpu, MASTER_CLOCK); /* 2.5 MHz */ - m_maincpu->set_daisy_config(daisy_chain); - m_maincpu->set_addrmap(AS_PROGRAM, &jankenmn_state::jankenmn_map); - m_maincpu->set_addrmap(AS_IO, &jankenmn_state::jankenmn_port_map); - - i8255_device &ppi0(I8255(config, "ppi8255_0")); - /* (10-13) Mode 0 - Ports A & B set as input, high C & low C as output. */ - ppi0.in_pa_callback().set_ioport("DSW"); - ppi0.in_pb_callback().set_ioport("IN0"); - ppi0.out_pc_callback().set(FUNC(jankenmn_state::lamps3_w)); - - i8255_device &ppi1(I8255(config, "ppi8255_1")); - /* (20-23) Mode 0 - Ports A, B, high C & low C set as output. */ - ppi1.out_pa_callback().set("dac", FUNC(dac_byte_interface::data_w)); - ppi1.out_pb_callback().set(FUNC(jankenmn_state::lamps1_w)); - ppi1.out_pc_callback().set(FUNC(jankenmn_state::lamps2_w)); - - z80ctc_device& ctc(Z80CTC(config, "ctc", MASTER_CLOCK)); - ctc.intr_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0); - - /* NO VIDEO */ - - /* sound hardware */ - SPEAKER(config, "speaker").front_center(); - - AD7523(config, "dac", 0).add_route(ALL_OUTPUTS, "speaker", 0.5); -} - - -/********************************************* -* Rom Load * -*********************************************/ - -ROM_START( jankenmn ) - ROM_REGION( 0x40000, "maincpu", 0 ) - ROM_LOAD( "pcg2.bin", 0x0000, 0xc000, CRC(48a8f769) SHA1(656346ca0a83fd8ff5c8683152e4c5e1a1c797fa) ) - ROM_CONTINUE( 0xe000, 0x2000 ) - ROM_IGNORE( 0x32000 ) // lots of unused PCM data - - // Z80 code/data in $0000-$2b4f, rest is empty. CTC probably at 58-5b. - // Can't find any sign of 8255 PPI. Is this an unused leftover or testrom? - ROM_REGION( 0x4000, "temp", 0 ) - ROM_LOAD( "pcg1.bin", 0x0000, 0x4000, CRC(a9c5aa2e) SHA1(c3b81eeefa5c442231cd26615aaf6c682063b26f) ) -ROM_END - -} // anonymous namespace - - -/********************************************* -* Game Drivers * -*********************************************/ - -// YEAR NAME PARENT MACHINE INPUT CLASS INIT ROT COMPANY FULLNAME FLAGS LAYOUT -GAMEL( 1991, jankenmn, 0, jankenmn, jankenmn, jankenmn_state, empty_init, ROT0, "Sunwise", "Janken Man Kattara Ageru", MACHINE_SUPPORTS_SAVE, layout_jankenmn ) diff --git a/src/mame/skeleton/swunktarot.cpp b/src/mame/skeleton/swunktarot.cpp deleted file mode 100644 index 10504df20e7..00000000000 --- a/src/mame/skeleton/swunktarot.cpp +++ /dev/null @@ -1,475 +0,0 @@ -// license: BSD-3-Clause -// copyright-holders: Angelo Salese, AJR -/*************************************************************************************************** - -Another World (c) 1989 Sunwise - -TODO: -- Identify irq sources ($24 timer, $26 VBLANK?, $20 or $22 quadrature encoder); -- Z80DMA never sends a ready signal, workaround by forcing is_ready fn to 1; -- Verify data ROM bank; -- Sound; - -==================================================================================================== - -TOP BOARD (S-8808A) -========= -ROMs 1-12 -main: -Z80 CTC-D -LH0083A Z80A-DMA -Z0840004PSC Z80 CPU -D8255AC-2 -6116 RAM -Oki M6242 -32.768 kHz osc - -sound: -Z80 CTC-D -D8255AC-2 -Z0840004PSC Z80 CPU -YM3812 -5816 RAM -4 MHz osc - -LOWER BOARD (S-8809A) -========== -ROMs A-E -3x 6148 RAM -video output -5x 5816 RAM -18 MHz osc - -***************************************************************************************************/ - -#include "emu.h" - -#include "cpu/z80/z80.h" -#include "machine/i8255.h" -#include "machine/msm6242.h" -#include "machine/z80ctc.h" -#include "machine/z80dma.h" -#include "sound/ymopl.h" - -#include "emupal.h" -#include "screen.h" -#include "speaker.h" -#include "tilemap.h" - - -// configurable logging -#define LOG_PORTS (1U << 1) -#define LOG_DMA (1U << 2) - -//#define VERBOSE (LOG_GENERAL | LOG_PORTS | LOG_DMA) -#define VERBOSE (LOG_GENERAL | LOG_PORTS) - -#include "logmacro.h" - -#define LOGPORTS(...) LOGMASKED(LOG_PORTS, __VA_ARGS__) -#define LOGDMA(...) LOGMASKED(LOG_DMA, __VA_ARGS__) - - -namespace { - -class anoworld_state : public driver_device -{ -public: - anoworld_state(const machine_config &mconfig, device_type type, const char *tag) - : driver_device(mconfig, type, tag) - , m_maincpu(*this, "maincpu") - , m_audiocpu(*this, "audiocpu") - , m_dma(*this, "dma") - , m_palette(*this, "palette") - , m_gfxdecode(*this, "gfxdecode") - , m_video_view(*this, "video_view") - , m_databank(*this, "databank") - , m_audiobank(*this, "audiobank") - { - } - - void unktarot(machine_config &config) ATTR_COLD; - -protected: - virtual void machine_start() override ATTR_COLD; - virtual void machine_reset() override ATTR_COLD; - -private: - required_device m_maincpu; - required_device m_audiocpu; - required_device m_dma; - required_device m_palette; - required_device m_gfxdecode; - - memory_view m_video_view; - required_memory_bank m_databank; - required_memory_bank m_audiobank; - std::unique_ptr m_paletteram; - - void main_program_map(address_map &map) ATTR_COLD; - void audio_program_map(address_map &map) ATTR_COLD; - void main_io_map(address_map &map) ATTR_COLD; - void audio_io_map(address_map &map) ATTR_COLD; - - void data_bank_w(offs_t offset, u8 data); - void video_bank_w(offs_t offset, u8 data); - - void dma_busreq_w(int state); - u8 dma_memory_r(offs_t offset); - void dma_memory_w(offs_t offset, u8 data); - u8 dma_io_r(offs_t offset); - void dma_io_w(offs_t offset, u8 data); - - uint32_t screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); -}; - - -uint32_t anoworld_state::screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect) -{ - bitmap.fill(rgb_t::black(), cliprect); - - return 0; -} - -void anoworld_state::data_bank_w(offs_t offset, u8 data) -{ - // guess, also bit 6 actively used - m_databank->set_entry(data & 0x3f); - LOG("PPI port A data_bank_w: %02x\n", data); -} - -void anoworld_state::video_bank_w(offs_t offset, u8 data) -{ - m_video_view.select(BIT(data, 4)); - LOG("PPI port C video_bank_w: %02x\n", data); -} - -void anoworld_state::dma_busreq_w(int state) -{ - // HACK: grant bus request immediately - LOGDMA("dma_busreq_w %d\n", state); - m_maincpu->set_input_line(INPUT_LINE_HALT, state); - m_dma->bai_w(state); -} - -u8 anoworld_state::dma_memory_r(offs_t offset) -{ - LOGDMA("dma_memory_r %04X\n", offset); - return m_maincpu->space(AS_PROGRAM).read_byte(offset); -} - -void anoworld_state::dma_memory_w(offs_t offset, u8 data) -{ - LOGDMA("dma_memory_w %04X <- %02X\n", offset, data); - m_maincpu->space(AS_PROGRAM).write_byte(offset, data); -} - -u8 anoworld_state::dma_io_r(offs_t offset) -{ - LOGDMA("dma_io_r %04X\n", offset); - return m_maincpu->space(AS_IO).read_byte(offset); -} - -void anoworld_state::dma_io_w(offs_t offset, u8 data) -{ - LOGDMA("dma_io_w %04X <- %02X\n", offset, data); - m_maincpu->space(AS_IO).write_byte(offset, data); -} - -void anoworld_state::main_program_map(address_map &map) -{ - map(0x0000, 0x7fff).rom(); - map(0x8000, 0x9fff).ram(); - map(0xa000, 0xafff).ram(); - map(0xb000, 0xbfff).view(m_video_view); - m_video_view[0](0xb000, 0xbfff).lrw8( - NAME([this] (offs_t offset) { - return m_paletteram[bitswap<12>(offset ^ 2, 1, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 0)]; - }), - NAME([this] (offs_t offset, u8 data) { - const u16 pal_offset = bitswap<12>(offset ^ 2, 1, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 0); - m_paletteram[pal_offset] = data; - const u16 datax = m_paletteram[pal_offset & ~1] | (m_paletteram[pal_offset | 1] << 8); - const u8 r = (datax >> 0) & 0xf; - const u8 g = (datax >> 4) & 0xf; - const u8 b = (datax >> 8) & 0xf; - - m_palette->set_pen_color(pal_offset >> 1, pal4bit(r), pal4bit(g), pal4bit(b)); - }) - ); - m_video_view[1](0xb000, 0xbfff).ram(); - - map(0xc000, 0xffff).bankr(m_databank); -} - -void anoworld_state::main_io_map(address_map &map) -{ - map.global_mask(0xff); - map.unmap_value_high(); - - map(0x00, 0x00).rw(m_dma, FUNC(z80dma_device::read), FUNC(z80dma_device::write)); - map(0x10, 0x13).rw("ctc0", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); - map(0x20, 0x2f).rw("rtc", FUNC(msm6242_device::read), FUNC(msm6242_device::write)); - map(0x30, 0x33).rw("ppi0", FUNC(i8255_device::read), FUNC(i8255_device::write)); - map(0x40, 0x43).rw("ppi1", FUNC(i8255_device::read), FUNC(i8255_device::write)); - map(0x50, 0x50).portr("IN0"); // ? (bits 4 and 5 checked in service routines $20 and $22) - map(0x60, 0x60).portr("IN1"); // ? -} - -static const z80_daisy_config main_daisy_chain[] = -{ - { "dma" }, - { "ctc0" }, - { nullptr } -}; - -void anoworld_state::audio_program_map(address_map &map) -{ - map(0x0000, 0x1fff).rom(); - map(0x4000, 0x47ff).ram(); - map(0xc000, 0xffff).bankr(m_audiobank); -} - -void anoworld_state::audio_io_map(address_map &map) -{ - map.global_mask(0xff); - - //map(0x00, 0x03).rw("ctc1", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); //TODO: maybe - //map(0x04, 0x07).rw("ppi1", FUNC(i8255_device::read), FUNC(i8255_device::write)); //TODO: maybe. 0x05 seems to set the audio bank - //map(0x08, 0x09).w // YM? - //map(0x0c, 0x0c).r? // latch? irq ack? -} - - -static INPUT_PORTS_START( unktarot ) - PORT_START("IN0") - PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - - PORT_START("IN1") - PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - - PORT_START("DSW") - PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) - PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) - PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) - PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) -INPUT_PORTS_END - - -const gfx_layout gfx_8x8x1 = -{ - 8,8, - RGN_FRAC(1,1), - 1, - { RGN_FRAC(0,1) }, - { STEP8(7,-1) }, - { STEP8(0,8) }, - 8*8 -}; - -const gfx_layout gfx_8x8x4 = -{ - 8,8, - RGN_FRAC(1,4), - 4, - { RGN_FRAC(3,4), RGN_FRAC(2,4), RGN_FRAC(1,4), RGN_FRAC(0,4) }, - { STEP8(7,-1) }, - { STEP8(0,8) }, - 8*8 -}; - -static GFXDECODE_START( gfx_unktarot ) - GFXDECODE_ENTRY( "chars", 0, gfx_8x8x1, 0, 16 ) // TODO: identify how it gathers palette - GFXDECODE_ENTRY( "tiles", 0, gfx_8x8x4, 0, 16 * 8 ) -GFXDECODE_END - -void anoworld_state::machine_start() -{ - m_paletteram = make_unique_clear(0x1000); - - m_databank->configure_entries(0, 0x40, memregion("data")->base(), 0x4000); - m_databank->set_entry(0); - m_audiobank->configure_entries(0, 32, memregion("audiocpu")->base(), 0x4000); - m_audiobank->set_entry(1); -} - -void anoworld_state::machine_reset() -{ - m_video_view.select(0); -} - -/* - * Irq table: - * $+10 (DMA) writes to $9e61 - * $+20 (CTC ch0, counter mode) increments or decrements $9e88 - * $+22 (CTC ch1, counter mode) increments or decrements $9e8a - * $+24 (CTC ch2, timer mode) writes to $86a9 - * $+26 (CTC ch3, counter mode) writes to $9e65 - */ - - -void anoworld_state::unktarot(machine_config &config) -{ - Z80(config, m_maincpu, 4_MHz_XTAL); - m_maincpu->set_addrmap(AS_PROGRAM, &anoworld_state::main_program_map); - m_maincpu->set_addrmap(AS_IO, &anoworld_state::main_io_map); - m_maincpu->set_daisy_config(main_daisy_chain); - - Z80(config, m_audiocpu, 4_MHz_XTAL).set_disable(); - m_audiocpu->set_addrmap(AS_PROGRAM, &anoworld_state::audio_program_map); - m_audiocpu->set_addrmap(AS_IO, &anoworld_state::audio_io_map); - - z80ctc_device &ctc0(Z80CTC(config, "ctc0", 4_MHz_XTAL)); - ctc0.intr_callback().set_inputline("maincpu", 0); - - Z80DMA(config, m_dma, 4_MHz_XTAL); - m_dma->out_busreq_callback().set(FUNC(anoworld_state::dma_busreq_w)); - m_dma->out_int_callback().set_inputline("maincpu", 0); - m_dma->in_mreq_callback().set(FUNC(anoworld_state::dma_memory_r)); - m_dma->out_mreq_callback().set(FUNC(anoworld_state::dma_memory_w)); - m_dma->in_iorq_callback().set(FUNC(anoworld_state::dma_io_r)); - m_dma->out_iorq_callback().set(FUNC(anoworld_state::dma_io_w)); - - z80ctc_device &ctc1(Z80CTC(config, "ctc1", 4_MHz_XTAL)); - ctc1.intr_callback().set([this] (int state) { LOGPORTS("%s: CTC1 INTR handler %d\n", machine().describe_context(), state); }); - ctc1.zc_callback<0>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC0 handler %d\n", machine().describe_context(), state); }); - ctc1.zc_callback<1>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC1 handler %d\n", machine().describe_context(), state); }); - ctc1.zc_callback<2>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC2 handler %d\n", machine().describe_context(), state); }); - - i8255_device &ppi0(I8255A(config, "ppi0")); // NEC D8255AC-2 - ppi0.in_pa_callback().set([this] () { LOGPORTS("%s: PPI0 port A in\n", machine().describe_context()); return uint8_t(0); }); - ppi0.in_pb_callback().set([this] () { LOGPORTS("%s: PPI0 port B in\n", machine().describe_context()); return uint8_t(0); }); - ppi0.in_pc_callback().set([this] () { LOGPORTS("%s: PPI0 port C in\n", machine().describe_context()); return uint8_t(0); }); - ppi0.out_pa_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port A out %02x\n", machine().describe_context(), data); }); - ppi0.out_pb_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port B out %02x\n", machine().describe_context(), data); }); - ppi0.out_pc_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port C out %02x\n", machine().describe_context(), data); }); - - i8255_device &ppi1(I8255A(config, "ppi1")); // NEC D8255AC-2 - ppi1.out_pa_callback().set(FUNC(anoworld_state::data_bank_w)); - ppi1.out_pb_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI1 port B out %02x\n", machine().describe_context(), data); }); - ppi1.out_pc_callback().set(FUNC(anoworld_state::video_bank_w)); - - msm6242_device &rtc(MSM6242(config, "rtc", 32.768_kHz_XTAL)); - rtc.out_int_handler().set("ctc0", FUNC(z80ctc_device::trg3)); // source guessed - - screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_RASTER)); // TODO: everything - screen.set_refresh_hz(60); - screen.set_vblank_time(ATTOSECONDS_IN_USEC(0)); - screen.set_size(64*8, 32*8); - screen.set_visarea(0*8, 64*8-1, 2*8, 30*8-1); - screen.set_screen_update(FUNC(anoworld_state::screen_update)); - - GFXDECODE(config, m_gfxdecode, m_palette, gfx_unktarot); - - PALETTE(config, m_palette).set_entries(0x800); //.set_format(palette_device::xRGB_444, 0x800); - - SPEAKER(config, "mono").front_center(); - - ym3812_device &ym(YM3812(config, "ym", 4_MHz_XTAL)); - ym.irq_handler().set([this] (int state) { LOGPORTS("%s: YM IRQ handler %d\n", machine().describe_context(), state); }); - ym.add_route(ALL_OUTPUTS, "mono", 0.80); -} - - -ROM_START( unktarot ) - ROM_REGION( 0x08000, "maincpu", 0 ) - ROM_LOAD( "1.u5", 0x00000, 0x08000, CRC(eaf339d1) SHA1(8325046d2059ad890204e0373bcfbe1221e12bdf) ) - - // these ROMs are located under the main CPU one - ROM_REGION( 0x100000, "data", 0 ) - ROM_LOAD( "2.u6", 0x00000, 0x20000, CRC(42564c5b) SHA1(c991a09c29283a50e6e1638cc80eb9dd490fda3f) ) - ROM_LOAD( "3.u7", 0x20000, 0x20000, CRC(5692e175) SHA1(a0a3d01a7d7ff5400cef8e497897786c653155f3) ) - ROM_LOAD( "4.u8", 0x40000, 0x20000, CRC(e368af7c) SHA1(9cbd32b4398bfa5b8c5a8f0e81705dcfd8919553) ) - ROM_LOAD( "5.u9", 0x60000, 0x20000, CRC(179989dd) SHA1(d07b8b980b67327ed3bbfa1da737c0261bef9e17) ) - ROM_LOAD( "6.u14", 0x80000, 0x20000, CRC(91d821d1) SHA1(ce9829fd24f45ed18ea6180104426562eee118d2) ) - ROM_LOAD( "7.u15", 0xa0000, 0x20000, CRC(d94904db) SHA1(2cb7a13f56aefed5e70f50f3c3439a2d5049b581) ) - ROM_LOAD( "8.u16", 0xc0000, 0x20000, CRC(a4d8e251) SHA1(ed0df6b525d833e5c2e9c0aeaa2e34b210f958aa) ) - ROM_LOAD( "9.u17", 0xe0000, 0x20000, CRC(5c00d059) SHA1(17fae821c17eebe675feab1c97099c6a2241b0d1) ) - - ROM_REGION( 0x80000, "audiocpu", ROMREGION_ERASE00 ) - ROM_LOAD( "10.u28", 0x00000, 0x20000, CRC(4bedeb7a) SHA1(d9ce1bc9efc26f8c90b98736ee41a3cb45fc3b68) ) - // empty u29 - ROM_LOAD( "11.u41", 0x20000, 0x20000, CRC(b0ffb442) SHA1(9524de6120adc8ec77b94e9a89992271ce12704b) ) - ROM_LOAD( "12.u42", 0x40000, 0x20000, CRC(83ae6756) SHA1(289d2ed72dbf5c1a941da67cb1f7fe9a0e3aaab2) ) - - ROM_REGION( 0x8000, "chars", 0 ) - ROM_LOAD( "e.u60", 0x0000, 0x8000, CRC(f80ba6fe) SHA1(573d49cf52b47f112f2cfd0e259b8dc5852a3102) ) - - ROM_REGION( 0x80000, "tiles", 0 ) - ROM_LOAD( "a.u56", 0x00000, 0x20000, CRC(698250cf) SHA1(aa2acb4a643d6fcff6fa406a6fe9c1ff3457ad51) ) - ROM_LOAD( "b.u57", 0x20000, 0x20000, CRC(ebcfa6fc) SHA1(00f2603c38e0e4ee86e14954afe282fafe8c1a8b) ) - ROM_LOAD( "c.u58", 0x40000, 0x20000, CRC(c6b572e8) SHA1(2fad7841a981bc98f2187237116dd61e272128d5) ) - ROM_LOAD( "d.u59", 0x60000, 0x20000, CRC(cbe4da16) SHA1(e673b3b7e95cda27f1a77e8ef44e13a58ba3d3dc) ) - // empty u66 to u69 -ROM_END - -} // anonymous namespace - - -GAME( 1989, unktarot, 0, unktarot, unktarot, anoworld_state, empty_init, ROT0, "Sunwise", "Another World (Japan)", MACHINE_IS_SKELETON ) // title screen GFXs in region 1 at 0x3051 onward diff --git a/src/mame/sunwise/anoworld.cpp b/src/mame/sunwise/anoworld.cpp new file mode 100644 index 00000000000..2fa487f0cd9 --- /dev/null +++ b/src/mame/sunwise/anoworld.cpp @@ -0,0 +1,475 @@ +// license: BSD-3-Clause +// copyright-holders: Angelo Salese, AJR +/*************************************************************************************************** + +Another World (c) 1989 Sunwise + +TODO: +- Identify irq sources ($24 timer, $26 VBLANK?, $20 or $22 quadrature encoder); +- Z80DMA never sends a ready signal, workaround by forcing is_ready fn to 1; +- Verify data ROM bank; +- Sound; + +==================================================================================================== + +TOP BOARD (S-8808A) +========= +ROMs 1-12 +main: +Z80 CTC-D +LH0083A Z80A-DMA +Z0840004PSC Z80 CPU +D8255AC-2 +6116 RAM +Oki M6242 +32.768 kHz osc + +sound: +Z80 CTC-D +D8255AC-2 +Z0840004PSC Z80 CPU +YM3812 +5816 RAM +4 MHz osc + +LOWER BOARD (S-8809A) +========== +ROMs A-E +3x 6148 RAM +video output +5x 5816 RAM +18 MHz osc + +***************************************************************************************************/ + +#include "emu.h" + +#include "cpu/z80/z80.h" +#include "machine/i8255.h" +#include "machine/msm6242.h" +#include "machine/z80ctc.h" +#include "machine/z80dma.h" +#include "sound/ymopl.h" + +#include "emupal.h" +#include "screen.h" +#include "speaker.h" +#include "tilemap.h" + + +// configurable logging +#define LOG_PORTS (1U << 1) +#define LOG_DMA (1U << 2) + +//#define VERBOSE (LOG_GENERAL | LOG_PORTS | LOG_DMA) +#define VERBOSE (LOG_GENERAL | LOG_PORTS) + +#include "logmacro.h" + +#define LOGPORTS(...) LOGMASKED(LOG_PORTS, __VA_ARGS__) +#define LOGDMA(...) LOGMASKED(LOG_DMA, __VA_ARGS__) + + +namespace { + +class anoworld_state : public driver_device +{ +public: + anoworld_state(const machine_config &mconfig, device_type type, const char *tag) + : driver_device(mconfig, type, tag) + , m_maincpu(*this, "maincpu") + , m_audiocpu(*this, "audiocpu") + , m_dma(*this, "dma") + , m_palette(*this, "palette") + , m_gfxdecode(*this, "gfxdecode") + , m_video_view(*this, "video_view") + , m_databank(*this, "databank") + , m_audiobank(*this, "audiobank") + { + } + + void anoworld(machine_config &config) ATTR_COLD; + +protected: + virtual void machine_start() override ATTR_COLD; + virtual void machine_reset() override ATTR_COLD; + +private: + required_device m_maincpu; + required_device m_audiocpu; + required_device m_dma; + required_device m_palette; + required_device m_gfxdecode; + + memory_view m_video_view; + required_memory_bank m_databank; + required_memory_bank m_audiobank; + std::unique_ptr m_paletteram; + + void main_program_map(address_map &map) ATTR_COLD; + void audio_program_map(address_map &map) ATTR_COLD; + void main_io_map(address_map &map) ATTR_COLD; + void audio_io_map(address_map &map) ATTR_COLD; + + void data_bank_w(offs_t offset, u8 data); + void video_bank_w(offs_t offset, u8 data); + + void dma_busreq_w(int state); + u8 dma_memory_r(offs_t offset); + void dma_memory_w(offs_t offset, u8 data); + u8 dma_io_r(offs_t offset); + void dma_io_w(offs_t offset, u8 data); + + uint32_t screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect); +}; + + +uint32_t anoworld_state::screen_update(screen_device &screen, bitmap_rgb32 &bitmap, const rectangle &cliprect) +{ + bitmap.fill(rgb_t::black(), cliprect); + + return 0; +} + +void anoworld_state::data_bank_w(offs_t offset, u8 data) +{ + // guess, also bit 6 actively used + m_databank->set_entry(data & 0x3f); + LOG("PPI port A data_bank_w: %02x\n", data); +} + +void anoworld_state::video_bank_w(offs_t offset, u8 data) +{ + m_video_view.select(BIT(data, 4)); + LOG("PPI port C video_bank_w: %02x\n", data); +} + +void anoworld_state::dma_busreq_w(int state) +{ + // HACK: grant bus request immediately + LOGDMA("dma_busreq_w %d\n", state); + m_maincpu->set_input_line(INPUT_LINE_HALT, state); + m_dma->bai_w(state); +} + +u8 anoworld_state::dma_memory_r(offs_t offset) +{ + LOGDMA("dma_memory_r %04X\n", offset); + return m_maincpu->space(AS_PROGRAM).read_byte(offset); +} + +void anoworld_state::dma_memory_w(offs_t offset, u8 data) +{ + LOGDMA("dma_memory_w %04X <- %02X\n", offset, data); + m_maincpu->space(AS_PROGRAM).write_byte(offset, data); +} + +u8 anoworld_state::dma_io_r(offs_t offset) +{ + LOGDMA("dma_io_r %04X\n", offset); + return m_maincpu->space(AS_IO).read_byte(offset); +} + +void anoworld_state::dma_io_w(offs_t offset, u8 data) +{ + LOGDMA("dma_io_w %04X <- %02X\n", offset, data); + m_maincpu->space(AS_IO).write_byte(offset, data); +} + +void anoworld_state::main_program_map(address_map &map) +{ + map(0x0000, 0x7fff).rom(); + map(0x8000, 0x9fff).ram(); + map(0xa000, 0xafff).ram(); + map(0xb000, 0xbfff).view(m_video_view); + m_video_view[0](0xb000, 0xbfff).lrw8( + NAME([this] (offs_t offset) { + return m_paletteram[bitswap<12>(offset ^ 2, 1, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 0)]; + }), + NAME([this] (offs_t offset, u8 data) { + const u16 pal_offset = bitswap<12>(offset ^ 2, 1, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 0); + m_paletteram[pal_offset] = data; + const u16 datax = m_paletteram[pal_offset & ~1] | (m_paletteram[pal_offset | 1] << 8); + const u8 r = (datax >> 0) & 0xf; + const u8 g = (datax >> 4) & 0xf; + const u8 b = (datax >> 8) & 0xf; + + m_palette->set_pen_color(pal_offset >> 1, pal4bit(r), pal4bit(g), pal4bit(b)); + }) + ); + m_video_view[1](0xb000, 0xbfff).ram(); + + map(0xc000, 0xffff).bankr(m_databank); +} + +void anoworld_state::main_io_map(address_map &map) +{ + map.global_mask(0xff); + map.unmap_value_high(); + + map(0x00, 0x00).rw(m_dma, FUNC(z80dma_device::read), FUNC(z80dma_device::write)); + map(0x10, 0x13).rw("ctc0", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); + map(0x20, 0x2f).rw("rtc", FUNC(msm6242_device::read), FUNC(msm6242_device::write)); + map(0x30, 0x33).rw("ppi0", FUNC(i8255_device::read), FUNC(i8255_device::write)); + map(0x40, 0x43).rw("ppi1", FUNC(i8255_device::read), FUNC(i8255_device::write)); + map(0x50, 0x50).portr("IN0"); // ? (bits 4 and 5 checked in service routines $20 and $22) + map(0x60, 0x60).portr("IN1"); // ? +} + +static const z80_daisy_config main_daisy_chain[] = +{ + { "dma" }, + { "ctc0" }, + { nullptr } +}; + +void anoworld_state::audio_program_map(address_map &map) +{ + map(0x0000, 0x1fff).rom(); + map(0x4000, 0x47ff).ram(); + map(0xc000, 0xffff).bankr(m_audiobank); +} + +void anoworld_state::audio_io_map(address_map &map) +{ + map.global_mask(0xff); + + //map(0x00, 0x03).rw("ctc1", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); //TODO: maybe + //map(0x04, 0x07).rw("ppi1", FUNC(i8255_device::read), FUNC(i8255_device::write)); //TODO: maybe. 0x05 seems to set the audio bank + //map(0x08, 0x09).w // YM? + //map(0x0c, 0x0c).r? // latch? irq ack? +} + + +static INPUT_PORTS_START( anoworld ) + PORT_START("IN0") + PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + + PORT_START("IN1") + PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + + PORT_START("DSW") + PORT_DIPNAME( 0x0001, 0x0001, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0001, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0002, 0x0002, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0002, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0004, 0x0004, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0004, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0008, 0x0008, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0008, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0010, 0x0010, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0010, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0020, 0x0020, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0020, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0040, 0x0040, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0040, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) + PORT_DIPNAME( 0x0080, 0x0080, DEF_STR( Unknown ) ) + PORT_DIPSETTING( 0x0080, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x0000, DEF_STR( On ) ) +INPUT_PORTS_END + + +const gfx_layout gfx_8x8x1 = +{ + 8,8, + RGN_FRAC(1,1), + 1, + { RGN_FRAC(0,1) }, + { STEP8(7,-1) }, + { STEP8(0,8) }, + 8*8 +}; + +const gfx_layout gfx_8x8x4 = +{ + 8,8, + RGN_FRAC(1,4), + 4, + { RGN_FRAC(3,4), RGN_FRAC(2,4), RGN_FRAC(1,4), RGN_FRAC(0,4) }, + { STEP8(7,-1) }, + { STEP8(0,8) }, + 8*8 +}; + +static GFXDECODE_START( gfx_anoworld ) + GFXDECODE_ENTRY( "chars", 0, gfx_8x8x1, 0, 16 ) // TODO: identify how it gathers palette + GFXDECODE_ENTRY( "tiles", 0, gfx_8x8x4, 0, 16 * 8 ) +GFXDECODE_END + +void anoworld_state::machine_start() +{ + m_paletteram = make_unique_clear(0x1000); + + m_databank->configure_entries(0, 0x40, memregion("data")->base(), 0x4000); + m_databank->set_entry(0); + m_audiobank->configure_entries(0, 32, memregion("audiocpu")->base(), 0x4000); + m_audiobank->set_entry(1); +} + +void anoworld_state::machine_reset() +{ + m_video_view.select(0); +} + +/* + * Irq table: + * $+10 (DMA) writes to $9e61 + * $+20 (CTC ch0, counter mode) increments or decrements $9e88 + * $+22 (CTC ch1, counter mode) increments or decrements $9e8a + * $+24 (CTC ch2, timer mode) writes to $86a9 + * $+26 (CTC ch3, counter mode) writes to $9e65 + */ + + +void anoworld_state::anoworld(machine_config &config) +{ + Z80(config, m_maincpu, 4_MHz_XTAL); + m_maincpu->set_addrmap(AS_PROGRAM, &anoworld_state::main_program_map); + m_maincpu->set_addrmap(AS_IO, &anoworld_state::main_io_map); + m_maincpu->set_daisy_config(main_daisy_chain); + + Z80(config, m_audiocpu, 4_MHz_XTAL).set_disable(); + m_audiocpu->set_addrmap(AS_PROGRAM, &anoworld_state::audio_program_map); + m_audiocpu->set_addrmap(AS_IO, &anoworld_state::audio_io_map); + + z80ctc_device &ctc0(Z80CTC(config, "ctc0", 4_MHz_XTAL)); + ctc0.intr_callback().set_inputline("maincpu", 0); + + Z80DMA(config, m_dma, 4_MHz_XTAL); + m_dma->out_busreq_callback().set(FUNC(anoworld_state::dma_busreq_w)); + m_dma->out_int_callback().set_inputline("maincpu", 0); + m_dma->in_mreq_callback().set(FUNC(anoworld_state::dma_memory_r)); + m_dma->out_mreq_callback().set(FUNC(anoworld_state::dma_memory_w)); + m_dma->in_iorq_callback().set(FUNC(anoworld_state::dma_io_r)); + m_dma->out_iorq_callback().set(FUNC(anoworld_state::dma_io_w)); + + z80ctc_device &ctc1(Z80CTC(config, "ctc1", 4_MHz_XTAL)); + ctc1.intr_callback().set([this] (int state) { LOGPORTS("%s: CTC1 INTR handler %d\n", machine().describe_context(), state); }); + ctc1.zc_callback<0>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC0 handler %d\n", machine().describe_context(), state); }); + ctc1.zc_callback<1>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC1 handler %d\n", machine().describe_context(), state); }); + ctc1.zc_callback<2>().set([this] (int state) { LOGPORTS("%s: CTC1 ZC2 handler %d\n", machine().describe_context(), state); }); + + i8255_device &ppi0(I8255A(config, "ppi0")); // NEC D8255AC-2 + ppi0.in_pa_callback().set([this] () { LOGPORTS("%s: PPI0 port A in\n", machine().describe_context()); return uint8_t(0); }); + ppi0.in_pb_callback().set([this] () { LOGPORTS("%s: PPI0 port B in\n", machine().describe_context()); return uint8_t(0); }); + ppi0.in_pc_callback().set([this] () { LOGPORTS("%s: PPI0 port C in\n", machine().describe_context()); return uint8_t(0); }); + ppi0.out_pa_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port A out %02x\n", machine().describe_context(), data); }); + ppi0.out_pb_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port B out %02x\n", machine().describe_context(), data); }); + ppi0.out_pc_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI0 port C out %02x\n", machine().describe_context(), data); }); + + i8255_device &ppi1(I8255A(config, "ppi1")); // NEC D8255AC-2 + ppi1.out_pa_callback().set(FUNC(anoworld_state::data_bank_w)); + ppi1.out_pb_callback().set([this] (uint8_t data) { LOGPORTS("%s: PPI1 port B out %02x\n", machine().describe_context(), data); }); + ppi1.out_pc_callback().set(FUNC(anoworld_state::video_bank_w)); + + msm6242_device &rtc(MSM6242(config, "rtc", 32.768_kHz_XTAL)); + rtc.out_int_handler().set("ctc0", FUNC(z80ctc_device::trg3)); // source guessed + + screen_device &screen(SCREEN(config, "screen", SCREEN_TYPE_RASTER)); // TODO: everything + screen.set_refresh_hz(60); + screen.set_vblank_time(ATTOSECONDS_IN_USEC(0)); + screen.set_size(64*8, 32*8); + screen.set_visarea(0*8, 64*8-1, 2*8, 30*8-1); + screen.set_screen_update(FUNC(anoworld_state::screen_update)); + + GFXDECODE(config, m_gfxdecode, m_palette, gfx_anoworld); + + PALETTE(config, m_palette).set_entries(0x800); //.set_format(palette_device::xRGB_444, 0x800); + + SPEAKER(config, "mono").front_center(); + + ym3812_device &ym(YM3812(config, "ym", 4_MHz_XTAL)); + ym.irq_handler().set([this] (int state) { LOGPORTS("%s: YM IRQ handler %d\n", machine().describe_context(), state); }); + ym.add_route(ALL_OUTPUTS, "mono", 0.80); +} + + +ROM_START( anoworld ) + ROM_REGION( 0x08000, "maincpu", 0 ) + ROM_LOAD( "1.u5", 0x00000, 0x08000, CRC(eaf339d1) SHA1(8325046d2059ad890204e0373bcfbe1221e12bdf) ) + + // these ROMs are located under the main CPU one + ROM_REGION( 0x100000, "data", 0 ) + ROM_LOAD( "2.u6", 0x00000, 0x20000, CRC(42564c5b) SHA1(c991a09c29283a50e6e1638cc80eb9dd490fda3f) ) + ROM_LOAD( "3.u7", 0x20000, 0x20000, CRC(5692e175) SHA1(a0a3d01a7d7ff5400cef8e497897786c653155f3) ) + ROM_LOAD( "4.u8", 0x40000, 0x20000, CRC(e368af7c) SHA1(9cbd32b4398bfa5b8c5a8f0e81705dcfd8919553) ) + ROM_LOAD( "5.u9", 0x60000, 0x20000, CRC(179989dd) SHA1(d07b8b980b67327ed3bbfa1da737c0261bef9e17) ) + ROM_LOAD( "6.u14", 0x80000, 0x20000, CRC(91d821d1) SHA1(ce9829fd24f45ed18ea6180104426562eee118d2) ) + ROM_LOAD( "7.u15", 0xa0000, 0x20000, CRC(d94904db) SHA1(2cb7a13f56aefed5e70f50f3c3439a2d5049b581) ) + ROM_LOAD( "8.u16", 0xc0000, 0x20000, CRC(a4d8e251) SHA1(ed0df6b525d833e5c2e9c0aeaa2e34b210f958aa) ) + ROM_LOAD( "9.u17", 0xe0000, 0x20000, CRC(5c00d059) SHA1(17fae821c17eebe675feab1c97099c6a2241b0d1) ) + + ROM_REGION( 0x80000, "audiocpu", ROMREGION_ERASE00 ) + ROM_LOAD( "10.u28", 0x00000, 0x20000, CRC(4bedeb7a) SHA1(d9ce1bc9efc26f8c90b98736ee41a3cb45fc3b68) ) + // empty u29 + ROM_LOAD( "11.u41", 0x20000, 0x20000, CRC(b0ffb442) SHA1(9524de6120adc8ec77b94e9a89992271ce12704b) ) + ROM_LOAD( "12.u42", 0x40000, 0x20000, CRC(83ae6756) SHA1(289d2ed72dbf5c1a941da67cb1f7fe9a0e3aaab2) ) + + ROM_REGION( 0x8000, "chars", 0 ) + ROM_LOAD( "e.u60", 0x0000, 0x8000, CRC(f80ba6fe) SHA1(573d49cf52b47f112f2cfd0e259b8dc5852a3102) ) + + ROM_REGION( 0x80000, "tiles", 0 ) + ROM_LOAD( "a.u56", 0x00000, 0x20000, CRC(698250cf) SHA1(aa2acb4a643d6fcff6fa406a6fe9c1ff3457ad51) ) + ROM_LOAD( "b.u57", 0x20000, 0x20000, CRC(ebcfa6fc) SHA1(00f2603c38e0e4ee86e14954afe282fafe8c1a8b) ) + ROM_LOAD( "c.u58", 0x40000, 0x20000, CRC(c6b572e8) SHA1(2fad7841a981bc98f2187237116dd61e272128d5) ) + ROM_LOAD( "d.u59", 0x60000, 0x20000, CRC(cbe4da16) SHA1(e673b3b7e95cda27f1a77e8ef44e13a58ba3d3dc) ) + // empty u66 to u69 +ROM_END + +} // anonymous namespace + + +GAME( 1989, anoworld, 0, anoworld, anoworld, anoworld_state, empty_init, ROT0, "Sunwise", "Another World (Japan)", MACHINE_IS_SKELETON ) // title screen GFXs in region 1 at 0x3051 onward diff --git a/src/mame/sunwise/jankenmn.cpp b/src/mame/sunwise/jankenmn.cpp new file mode 100644 index 00000000000..af95b344fe0 --- /dev/null +++ b/src/mame/sunwise/jankenmn.cpp @@ -0,0 +1,444 @@ +// license:BSD-3-Clause +// copyright-holders:Roberto Fresca, hap +/*************************************************************************** + + JANKENMAN UNIT + + Driver by Roberto Fresca. + With further improvements by MAME Team. + + + Coin-operated Z80-CTC + DAC system. No screen, just artwork with lamps + LEDs. + Janken man is coming from Jankenpon, the rock-paper-scissors game. + There are several versions of this game, the most notable difference being in + the artwork and bonus lamps. The kid's voice and hand are the same among all. + + Control panel is composed of buttons: + Guu (rock), Choki (scissors), Paa (paper). + Some cabs have a Start button and/or Payout button too. + + Info: + http://dgm.hmc6.net/museum/jyankenman.html + http://dgm.hmc6.net/museum/jyankenman_kattaraageru.html + (and many videos on Youtube) + + + Janken Man series (working on this hardware): + + * Janken Man (Pretty Carnival) (3 station prize game), (c) 1985, Sunwise. + * New Janken Man, (c) 1986, Sunwise. + * Janken Man Fever, (c) 1988, Sunwise. + * Janken Man Fever JP, (c) 1991, Sunwise. + * Janken Man JP, (c) 1991, Sunwise. + * Janken Man Kattara Ageru, (c) 1991, Sunwise. + * Janken Man Bubbles, (c) 1992, Sunwise. + * Janken Man Big, (c) 19??, Sunwise. + * Janken Man Lucky!, (c) 199?, Sunwise. + + +**************************************************************************** + + General Notes... + + For better experience, use the hi-res external artwork I made. + + Preview: http://www.robertofresca.com/imagenes/jankenmn_full.png + Artwork: http://mrdo.mameworld.info/artwork/jankenmn.zip + (mirror) http://www.progettoemma.net/mw/jankenmn.zip + +**************************************************************************** + + Hardware Notes... + + 1x LH0080A ; Sharp, Z80A CPU. + 1x LH0082A ; Sharp, Z80 CTC Counter Timer Circuit. + 2x M5L8255AP-5 ; Mitsubishi, PPI 8255 (I/O). + 1x HM6116P-3 ; Hitachi, SRAM. + + 1x 27C128 ; Program, labeled 'PCG1'. + 1x 27C020 ; Waveform (8bit mono unsigned 8192Hz), labeled 'PCG2'. + + 1x AD7523JN ; InterSil, D/A Converter, 8-Bit, Multiplying, 6.7MHz. + 1x LA8358 ; Sanyo, ???. (near volume knob) + 1x 386D NJR ; New Japan Radio, LM386D IC (500mW, 1-Channel Mono Audio AMP). + 3x M54562P ; 8-Unit 500mA source type Darlington Transistor Array with clamp diode. + + 1x 2.500 MHz Xtal. + 1x 8 DIP Switches bank. + + +**************************************************************************** + + Other specs... + + Name of game: Janken Man. + Manufacturer: Sanwaizu Co., Ltd. (Bankruptcy on March 6, 1998) + Year: May 1985 (1985) + Body dimensions: Depth: 355mm, Width: 340mm, Height: 855mm (body only) + Weight: 30kg. + Power: AC 100V 50/60Hz. + Power consumption: 32W + Capacity: 400 game tokens, 200 commemorative tokens + Safe capacity: 6000 coins 10 yen, 500 coins 100 yen. + Coin acceptor: 10 and 100 yens, Manufactured by Asahi Seiko 730-A/BW. + Coin selector: KWM/740 made by Asahi Seiko. + Hopper: MP04975 made by MAX. + Solenoid: AES-112 manufactured by Asahi Seiko. + + +**************************************************************************** + + The waveform is 8bit mono unsigned at 8192Hz. + Sampleset has sounds, music and voice at approximate rom offsets: + + $00c58-$038a4: "jan ken pon!" --> Is the call for rock paper and scissors. + $04d2e-$05a4b: "zuko" --> Is just used for sound effect when player loses. + $05b2d-$08207: "ai ko desho" --> Is the call for rematch when you've drawn. + $08410-$0a9ec: "ooatari" --> "you got it! / perfect!". + $0a9ec-$0c008: "yappii" --> Is just an exclamation of happiness. + $0c008-$0dac0: "attarii" --> "you got it". + + unused PCM data: + + $15db7-$18628: "kakariin o oyobi kudasai" --> "please call the attendant". + $18628-$1a4f3: "keihin ga deru yo" --> "your prize is incoming". + $3c26d-$3f677: "keihin o sentaku shite kudasai" --> "please select your prize". + + +**************************************************************************** + + About lamps... + + The internal layout has lamps mapped the following way: + + digits: + + 0 = Left + 1 = Right + + lamps: + + 00 = Multiplier 1 "attarii" (pays x1) + 01 = Multiplier 2 "ooatari" (pays x2) + + 02 = Rock button LED + 03 = Scissors button LED + 04 = Paper button LED + + 05 = Lose + 06 = Draw + 07 = Win + + 08 = Base Hand + 09 = Paper components + 10 = Paper/Scissors common components + 11 = Rock components + 12 = Scissors components + 13 = Rock/Scissors common components + + 14 = Payout error LED + + Not implemented in the internal layout/artwork: + + 15 = Rotating blue lamp + + +***************************************************************************/ + +#include "emu.h" +#include "cpu/z80/z80.h" +#include "machine/z80daisy.h" +#include "machine/z80ctc.h" +#include "machine/i8255.h" +#include "sound/dac.h" +#include "speaker.h" + +#include "jankenmn.lh" + + +namespace { + +#define MASTER_CLOCK XTAL(2'500'000) + + +class jankenmn_state : public driver_device +{ +public: + jankenmn_state(const machine_config &mconfig, device_type type, const char *tag) + : driver_device(mconfig, type, tag) + , m_maincpu(*this, "maincpu") + , m_digits(*this, "digit%u", 0U) + , m_lamps(*this, "lamp%u", 0U) + { } + + int hopper_status_r(); + + void jankenmn(machine_config &config); + +private: + void lamps1_w(uint8_t data); + void lamps2_w(uint8_t data); + void lamps3_w(uint8_t data); + + virtual void machine_start() override; + + void jankenmn_map(address_map &map); + void jankenmn_port_map(address_map &map); + + required_device m_maincpu; + output_finder<2> m_digits; + output_finder<16> m_lamps; +}; + + +/********************************************* +* Read/Write Handlers * +*********************************************/ + +static constexpr uint8_t led_map[16] = // 7748 IC? + { 0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7c, 0x07, 0x7f, 0x67, 0x58, 0x4c, 0x62, 0x69, 0x78, 0x00 }; + +void jankenmn_state::lamps1_w(uint8_t data) +{ + // hand state: d0: rock, d1: scissors, d2: paper + m_lamps[8] = (data & 7) != 0; + m_lamps[11] = BIT(data, 0); + m_lamps[12] = BIT(data, 1); + m_lamps[9] = BIT(data, 2); + m_lamps[10] = (data & 6) != 0; + m_lamps[13] = (data & 3) != 0; + + // d4-d7: led7seg (remaining credits) right digit + m_digits[1] = led_map[(data >> 4) & 0x0f]; + + // d3: ? (only set if game is over) +} + +void jankenmn_state::lamps2_w(uint8_t data) +{ + // button LEDs: d1: paper, d2: scissors, d3: rock + m_lamps[2] = BIT(data, 3); + m_lamps[3] = BIT(data, 2); + m_lamps[4] = BIT(data, 1); + + // lamps: d5: draw, d6: lose, d7: win + m_lamps[5] = BIT(data, 6); + m_lamps[6] = BIT(data, 5); + m_lamps[7] = BIT(data, 7); + + // d4: payout error LED + m_lamps[14] = BIT(data, 4); + + // d0: led7seg (remaining credits) left digit + m_digits[0] = led_map[data & 1]; +} + +void jankenmn_state::lamps3_w(uint8_t data) +{ + // d1: blue rotating lamp on top of cab + m_lamps[15] = BIT(data, 1); + + // d2: payout (waits for hopper status) + machine().bookkeeping().coin_counter_w(2, data & 0x04); + + // d3: right multiplier lamp(2), d4: left multiplier lamp(1) + m_lamps[0] = BIT(data, 4); + m_lamps[1] = BIT(data, 3); + + // d5: assume coin lockout + machine().bookkeeping().coin_lockout_global_w(~data & 0x20); + + // d0, d6, d7: N/C? + if (data & 0x04) + logerror("payout: %02X\n", (data & 0x04)); +} + +int jankenmn_state::hopper_status_r() +{ + // temp workaround, needs hopper + return machine().rand(); +} + +void jankenmn_state::machine_start() +{ + m_digits.resolve(); + m_lamps.resolve(); +} + + +/********************************************* +* Memory Map Definition * +*********************************************/ + +void jankenmn_state::jankenmn_map(address_map &map) +{ + map(0x0000, 0xbfff).rom(); + map(0xc000, 0xc7ff).ram(); + map(0xe000, 0xffff).rom(); +} + +void jankenmn_state::jankenmn_port_map(address_map &map) +{ + map.global_mask(0xff); + map(0x00, 0x03).rw("ctc", FUNC(z80ctc_device::read), FUNC(z80ctc_device::write)); + map(0x10, 0x13).rw("ppi8255_0", FUNC(i8255_device::read), FUNC(i8255_device::write)); + map(0x20, 0x23).rw("ppi8255_1", FUNC(i8255_device::read), FUNC(i8255_device::write)); + map(0x30, 0x30).nopw(); // ??? +} + +/* + Writes to port 30h.... + + They are coming from different code chunks, but seems that at least + they have different functions. Writes from 00B6h are unknown, whilst + others coming from 00D6h are counters. Sometimes whilst one increase, + the other one decrease. Writes coming from 0103h seems to clear (00) + or just end whatever the command sent. + + Other behaviours could point to be different counters. + + Also when you win, and the multipliers start to run, a lot of data + is written to the port. Maybe is a leftover, or just a connector to + hook the multiplier's 'roulette style' matrix lamps for other Janken + Man games... + + ':maincpu' (00B6): unmapped io memory write to 0030 = 01 & FF + ':maincpu' (00D6): unmapped io memory write to 0030 = 2F & FF + ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF + + ':maincpu' (00B6): unmapped io memory write to 0030 = F4 & FF + ':maincpu' (00D6): unmapped io memory write to 0030 = 30 & FF + ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF + + ':maincpu' (00B6): unmapped io memory write to 0030 = E7 & FF + ':maincpu' (00D6): unmapped io memory write to 0030 = 31 & FF + ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF + + ':maincpu' (00B6): unmapped io memory write to 0030 = DA & FF + ':maincpu' (00D6): unmapped io memory write to 0030 = 32 & FF + ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF + + ':maincpu' (00B6): unmapped io memory write to 0030 = CD & FF + ':maincpu' (00D6): unmapped io memory write to 0030 = 33 & FF + ':maincpu' (0103): unmapped io memory write to 0030 = 00 & FF + + + Need more analysis... + +*/ + +/********************************************* +* Input Ports Definitions * +*********************************************/ + +static INPUT_PORTS_START( jankenmn ) + PORT_START("IN0") + PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_BUTTON1 ) PORT_NAME("Guu (Rock)") + PORT_BIT( 0x02, IP_ACTIVE_HIGH, IPT_BUTTON2 ) PORT_NAME("Choki (Scissors)") + PORT_BIT( 0x04, IP_ACTIVE_HIGH, IPT_BUTTON3 ) PORT_NAME("Paa (Paper)") + PORT_BIT( 0x08, IP_ACTIVE_HIGH, IPT_UNKNOWN ) + PORT_BIT( 0x10, IP_ACTIVE_HIGH, IPT_COIN3 ) // 100 yen coin + PORT_BIT( 0x20, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_READ_LINE_MEMBER(jankenmn_state, hopper_status_r) + PORT_BIT( 0x40, IP_ACTIVE_HIGH, IPT_COIN2 ) // 10 yen coin + PORT_BIT( 0x80, IP_ACTIVE_HIGH, IPT_COIN1 ) // 10 yen coin + + PORT_START("DSW") + PORT_DIPNAME( 0x03, 0x03, DEF_STR( Coinage ) ) PORT_DIPLOCATION("DSW:7,8") + PORT_DIPSETTING( 0x00, "Lamp Test" ) + PORT_DIPSETTING( 0x02, DEF_STR( 3C_1C ) ) // or 4 credits on 100 yen + PORT_DIPSETTING( 0x01, DEF_STR( 2C_1C ) ) // or 6 credits on 100 yen + PORT_DIPSETTING( 0x03, DEF_STR( 1C_1C ) ) // or 11 credits on 100 yen + PORT_DIPNAME( 0x04, 0x04, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:6") + PORT_DIPSETTING( 0x04, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x08, 0x08, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:5") + PORT_DIPSETTING( 0x08, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x10, 0x10, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:4") + PORT_DIPSETTING( 0x10, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x20, 0x20, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:3") + PORT_DIPSETTING( 0x20, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x40, 0x40, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:2") + PORT_DIPSETTING( 0x40, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + PORT_DIPNAME( 0x80, 0x80, DEF_STR( Unknown ) ) PORT_DIPLOCATION("DSW:1") + PORT_DIPSETTING( 0x80, DEF_STR( Off ) ) + PORT_DIPSETTING( 0x00, DEF_STR( On ) ) + +INPUT_PORTS_END + + +/********************************************* +* Daisy Chain Interrupts Interface * +*********************************************/ + +static const z80_daisy_config daisy_chain[] = +{ + { "ctc" }, + { nullptr } +}; + + +/********************************************* +* Machine Config * +*********************************************/ + +void jankenmn_state::jankenmn(machine_config &config) +{ + /* basic machine hardware */ + Z80(config, m_maincpu, MASTER_CLOCK); /* 2.5 MHz */ + m_maincpu->set_daisy_config(daisy_chain); + m_maincpu->set_addrmap(AS_PROGRAM, &jankenmn_state::jankenmn_map); + m_maincpu->set_addrmap(AS_IO, &jankenmn_state::jankenmn_port_map); + + i8255_device &ppi0(I8255(config, "ppi8255_0")); + /* (10-13) Mode 0 - Ports A & B set as input, high C & low C as output. */ + ppi0.in_pa_callback().set_ioport("DSW"); + ppi0.in_pb_callback().set_ioport("IN0"); + ppi0.out_pc_callback().set(FUNC(jankenmn_state::lamps3_w)); + + i8255_device &ppi1(I8255(config, "ppi8255_1")); + /* (20-23) Mode 0 - Ports A, B, high C & low C set as output. */ + ppi1.out_pa_callback().set("dac", FUNC(dac_byte_interface::data_w)); + ppi1.out_pb_callback().set(FUNC(jankenmn_state::lamps1_w)); + ppi1.out_pc_callback().set(FUNC(jankenmn_state::lamps2_w)); + + z80ctc_device& ctc(Z80CTC(config, "ctc", MASTER_CLOCK)); + ctc.intr_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0); + + /* NO VIDEO */ + + /* sound hardware */ + SPEAKER(config, "speaker").front_center(); + + AD7523(config, "dac", 0).add_route(ALL_OUTPUTS, "speaker", 0.5); +} + + +/********************************************* +* Rom Load * +*********************************************/ + +ROM_START( jankenmn ) + ROM_REGION( 0x40000, "maincpu", 0 ) + ROM_LOAD( "pcg2.bin", 0x0000, 0xc000, CRC(48a8f769) SHA1(656346ca0a83fd8ff5c8683152e4c5e1a1c797fa) ) + ROM_CONTINUE( 0xe000, 0x2000 ) + ROM_IGNORE( 0x32000 ) // lots of unused PCM data + + // Z80 code/data in $0000-$2b4f, rest is empty. CTC probably at 58-5b. + // Can't find any sign of 8255 PPI. Is this an unused leftover or testrom? + ROM_REGION( 0x4000, "temp", 0 ) + ROM_LOAD( "pcg1.bin", 0x0000, 0x4000, CRC(a9c5aa2e) SHA1(c3b81eeefa5c442231cd26615aaf6c682063b26f) ) +ROM_END + +} // anonymous namespace + + +/********************************************* +* Game Drivers * +*********************************************/ + +// YEAR NAME PARENT MACHINE INPUT CLASS INIT ROT COMPANY FULLNAME FLAGS LAYOUT +GAMEL( 1991, jankenmn, 0, jankenmn, jankenmn, jankenmn_state, empty_init, ROT0, "Sunwise", "Janken Man Kattara Ageru", MACHINE_SUPPORTS_SAVE, layout_jankenmn ) -- cgit v1.2.3