astrocde.cpp: Driver and device modernization (nw)

- Rename sound device, document pinout and add input and output callbacks
- Add addressable and non-addressable output latch devices
- Add watchdog timers for most games
- Use memory maps instead of hacking in handlers in DRIVER_INIT
This commit is contained in:
AJR 2018-05-09 09:19:00 -04:00
parent e5f7ea6ffc
commit 65711d82fc
7 changed files with 497 additions and 408 deletions

View File

@ -39,6 +39,19 @@
Register 7:
D7..D0: Noise volume
************************************************************
The device has active high(!) SO strobes triggered by
read accesses, which transfer data from the the 8 SI
lines to the bus. Logically SO0-7 and SI0-7 ought to
be hooked up to the same input matrix, but this only
appears to be the case with the Astrocade home systems.
The arcade games instead channel the SI inputs through
a quartet of MC14539B (pin-compatible with 74153) CMOS
multiplexers and connect the SO strobes to unrelated
outputs which generally use the upper 8 address bits
as data.
***********************************************************/
#include "emu.h"
@ -46,7 +59,7 @@
// device type definition
DEFINE_DEVICE_TYPE(ASTROCADE, astrocade_device, "astrocade", "Astrocade")
DEFINE_DEVICE_TYPE(ASTROCADE_IO, astrocade_io_device, "astrocade_io", "Astrocade Custom I/O")
//**************************************************************************
@ -54,39 +67,54 @@ DEFINE_DEVICE_TYPE(ASTROCADE, astrocade_device, "astrocade", "Astrocade")
//**************************************************************************
//-------------------------------------------------
// astrocade_device - constructor
// astrocade_io_device - constructor
//-------------------------------------------------
astrocade_device::astrocade_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: device_t(mconfig, ASTROCADE, tag, owner, clock),
device_sound_interface(mconfig, *this),
m_stream(nullptr),
m_master_count(0),
m_vibrato_clock(0),
m_noise_clock(0),
m_noise_state(0),
m_a_count(0),
m_a_state(0),
m_b_count(0),
m_b_state(0),
m_c_count(0),
m_c_state(0)
astrocade_io_device::astrocade_io_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock)
: device_t(mconfig, ASTROCADE_IO, tag, owner, clock)
, device_sound_interface(mconfig, *this)
, m_stream(nullptr)
, m_master_count(0)
, m_vibrato_clock(0)
, m_noise_clock(0)
, m_noise_state(0)
, m_a_count(0)
, m_a_state(0)
, m_b_count(0)
, m_b_state(0)
, m_c_count(0)
, m_c_state(0)
, m_si_callback(*this)
, m_so_callback{{*this}, {*this}, {*this}, {*this}, {*this}, {*this}, {*this}, {*this}}
, m_pots(*this, {finder_base::DUMMY_TAG, finder_base::DUMMY_TAG, finder_base::DUMMY_TAG, finder_base::DUMMY_TAG})
{
memset(m_reg, 0, sizeof(uint8_t)*8);
memset(m_bitswap, 0, sizeof(uint8_t)*256);
}
//-------------------------------------------------
// device_resolve_objects - resolve objects that
// may be needed for other devices to set
// initial conditions at start time
//-------------------------------------------------
void astrocade_io_device::device_resolve_objects()
{
m_si_callback.resolve_safe(0);
for (auto &cb : m_so_callback)
cb.resolve_safe();
}
//-------------------------------------------------
// device_start - device-specific startup
//-------------------------------------------------
void astrocade_device::device_start()
void astrocade_io_device::device_start()
{
int i;
/* generate a bitswap table for the noise */
for (i = 0; i < 256; i++)
for (int i = 0; i < 256; i++)
m_bitswap[i] = bitswap<8>(i, 0,1,2,3,4,5,6,7);
/* allocate a stream for output */
@ -102,7 +130,7 @@ void astrocade_device::device_start()
// sound_stream_update - handle a stream update
//-------------------------------------------------
void astrocade_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
void astrocade_io_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
{
stream_sample_t *dest = outputs[0];
uint16_t noise_state;
@ -218,7 +246,7 @@ void astrocade_device::sound_stream_update(sound_stream &stream, stream_sample_t
// device_reset - device-specific reset
//-------------------------------------------------
void astrocade_device::device_reset()
void astrocade_io_device::device_reset()
{
memset(m_reg, 0, sizeof(m_reg));
@ -243,7 +271,7 @@ void astrocade_device::device_reset()
// Save state registration
//-------------------------------------------------
void astrocade_device::state_save_register()
void astrocade_io_device::state_save_register()
{
save_item(NAME(m_reg));
@ -270,7 +298,7 @@ void astrocade_device::state_save_register()
*
*************************************/
WRITE8_MEMBER( astrocade_device::astrocade_sound_w )
WRITE8_MEMBER(astrocade_io_device::write)
{
if ((offset & 8) != 0)
offset = (offset >> 8) & 7;
@ -283,3 +311,19 @@ WRITE8_MEMBER( astrocade_device::astrocade_sound_w )
/* stash the new register value */
m_reg[offset & 7] = data;
}
READ8_MEMBER(astrocade_io_device::read)
{
if ((offset & 0x0f) < 0x08)
{
if (!machine().side_effects_disabled())
m_so_callback[offset & 7](space, 0, offset >> 8);
return m_si_callback(space, offset & 7);
}
else if ((offset & 0x0f) >= 0x0c)
return m_pots[offset & 3].read_safe(0);
else
return 0xff;
}

View File

@ -1,5 +1,34 @@
// license:BSD-3-Clause
// copyright-holders:Aaron Giles,Frank Palazzolo
/***********************************************************
Astrocade custom 'IO' chip
************************************************************
_____ _____
Vss 1 |* \_/ | 40 MXD7
SI0 2 | | 39 MXD6
SI1 3 | | 38 MXD5
SI2 4 | | 37 MXD4
SI3 5 | | 36 MXD3
SI4 6 | | 35 MXD2
SI5 7 | | 34 MXD1
SI6 8 | | 33 MXD0
SI7 9 | | 32 SO0
POT0 10 | CUSTOM | 31 SO1
POT1 11 | I/O | 30 SO2
POT2 12 | | 29 SO3
POT3 13 | | 28 SO4
DISCHG 14 | | 27 SO5
MONOS 15 | | 26 SO6
ϕ 16 | | 25 SO7
/RESET 17 | | 24 AUDIO
TEST 18 | | 23 /RD
/IORQ 19 | | 22 Vgg
/ϕ 20 |_____________| 21 Vdd
***********************************************************/
#ifndef MAME_SOUND_ASTROCDE_H
#define MAME_SOUND_ASTROCDE_H
@ -10,11 +39,44 @@
// INTERFACE CONFIGURATION MACROS
//**************************************************************************
#define MCFG_ASTROCADE_ADD(tag, clock) \
MCFG_DEVICE_ADD((tag), ASTROCADE, (clock))
#define MCFG_ASTROCADE_IO_SI_READ_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_si_callback(DEVCB_##_devcb);
#define MCFG_ASTROCADE_REPLACE(tag, clock) \
MCFG_DEVICE_REPLACE((tag), ASTROCADE, (clock))
#define MCFG_ASTROCADE_IO_SO0_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<0>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO1_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<1>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO2_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<2>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO3_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<3>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO4_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<4>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO5_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<5>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO6_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<6>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_SO7_STROBE_CB(_devcb) \
devcb = &downcast<astrocade_io_device &>(*device).set_so_callback<7>(DEVCB_##_devcb);
#define MCFG_ASTROCADE_IO_POT0(_tag) \
downcast<astrocade_io_device &>(*device).set_pot_tag<0>(_tag);
#define MCFG_ASTROCADE_IO_POT1(_tag) \
downcast<astrocade_io_device &>(*device).set_pot_tag<1>(_tag);
#define MCFG_ASTROCADE_IO_POT2(_tag) \
downcast<astrocade_io_device &>(*device).set_pot_tag<2>(_tag);
#define MCFG_ASTROCADE_IO_POT3(_tag) \
downcast<astrocade_io_device &>(*device).set_pot_tag<3>(_tag);
@ -22,15 +84,21 @@
// TYPE DEFINITIONS
//**************************************************************************
// ======================> astrocade_device
// ======================> astrocade_io_device
class astrocade_device : public device_t, public device_sound_interface
class astrocade_io_device : public device_t, public device_sound_interface
{
public:
astrocade_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
astrocade_io_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
// configuration access
template<class Object> devcb_base &set_si_callback(Object &&cb) { return m_si_callback.set_callback(std::forward<Object>(cb)); }
template<int N, class Object> devcb_base &set_so_callback(Object &&cb) { return m_so_callback[N].set_callback(std::forward<Object>(cb)); }
template<int N> void set_pot_tag(const char *tag) { m_pots[N].set_tag(tag); }
protected:
// device-level overrides
virtual void device_resolve_objects() override;
virtual void device_start() override;
virtual void device_reset() override;
@ -38,7 +106,8 @@ protected:
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples) override;
public:
DECLARE_WRITE8_MEMBER( astrocade_sound_w );
DECLARE_WRITE8_MEMBER(write);
DECLARE_READ8_MEMBER(read);
private:
void state_save_register();
@ -63,8 +132,12 @@ private:
uint8_t m_c_state; /* current tone generator C state */
uint8_t m_bitswap[256]; /* bitswap table */
devcb_read8 m_si_callback;
devcb_write8 m_so_callback[8];
optional_ioport_array<4> m_pots;
};
DECLARE_DEVICE_TYPE(ASTROCADE, astrocade_device)
DECLARE_DEVICE_TYPE(ASTROCADE_IO, astrocade_io_device)
#endif // MAME_SOUND_ASTROCDE_H

View File

@ -120,6 +120,9 @@
#include "cpu/z80/z80daisy.h"
#include "machine/z80ctc.h"
#include "machine/nvram.h"
#include "machine/74259.h"
#include "machine/output_latch.h"
#include "machine/watchdog.h"
#include "sound/ay8910.h"
#include "sound/votrax.h"
@ -164,26 +167,6 @@ WRITE8_MEMBER(astrocde_state::protected_ram_w)
*
*************************************/
WRITE8_MEMBER(astrocde_state::seawolf2_lamps_w)
{
/* 0x42 = player 2 (left), 0x43 = player 1 (right) */
/* --x----- explosion */
/* ---x---- RELOAD (active low) */
/* ----x--- torpedo 1 available */
/* -----x-- torpedo 2 available */
/* ------x- torpedo 3 available */
/* -------x torpedo 4 available */
output().set_lamp_value((offset ^ 1) * 7 + 0, ( data >> 5) & 1); /* 0/7 = hit lamp */
output().set_lamp_value((offset ^ 1) * 7 + 1, (~data >> 4) & 1); /* 1/8 = reload lamp */
output().set_lamp_value((offset ^ 1) * 7 + 2, ( data >> 4) & 1); /* 2/9 = ready lamp */
output().set_lamp_value((offset ^ 1) * 7 + 3, ( data >> 3) & 1); /* 3/10 = torpedo 1 lamp */
output().set_lamp_value((offset ^ 1) * 7 + 4, ( data >> 2) & 1); /* 4/11 = torpedo 2 lamp */
output().set_lamp_value((offset ^ 1) * 7 + 5, ( data >> 1) & 1); /* 5/12 = torpedo 3 lamp */
output().set_lamp_value((offset ^ 1) * 7 + 6, ( data >> 0) & 1); /* 6/13 = torpedo 4 lamp */
}
WRITE8_MEMBER(astrocde_state::seawolf2_sound_1_w)// Port 40
{
uint8_t rising_bits = data & ~m_port_1_last;
@ -229,6 +212,33 @@ WRITE8_MEMBER(astrocde_state::seawolf2_sound_2_w)// Port 41
/*************************************
*
* Generic input/output
*
*************************************/
READ8_MEMBER(astrocde_state::input_mux_r)
{
return m_handle[offset & 3].read_safe(0xff);
}
template<int Coin>
WRITE_LINE_MEMBER(astrocde_state::coin_counter_w)
{
machine().bookkeeping().coin_counter_w(Coin, state);
}
template<int Bit>
WRITE_LINE_MEMBER(astrocde_state::sparkle_w)
{
m_sparkle[Bit] = state;
}
/*************************************
*
* Extra Bases specific input/output
@ -254,112 +264,47 @@ WRITE8_MEMBER(astrocde_state::ebases_coin_w)
/*************************************
*
* Space Zap specific input/output
*
*************************************/
READ8_MEMBER(astrocde_state::spacezap_io_r)
{
machine().bookkeeping().coin_counter_w(0, (offset >> 8) & 1);
machine().bookkeeping().coin_counter_w(1, (offset >> 9) & 1);
return m_p3handle.read_safe(0xff);
}
/*************************************
*
* Wizard of Wor specific input/output
*
*************************************/
READ8_MEMBER(astrocde_state::wow_io_r)
{
uint8_t data = (offset >> 8) & 1;
switch ((offset >> 9) & 7)
{
case 0: machine().bookkeeping().coin_counter_w(0, data); break;
case 1: machine().bookkeeping().coin_counter_w(1, data); break;
case 2: m_sparkle[0] = data; break;
case 3: m_sparkle[1] = data; break;
case 4: m_sparkle[2] = data; break;
case 5: m_sparkle[3] = data; break;
case 7: machine().bookkeeping().coin_counter_w(2, data); break;
}
return 0xff;
}
/*************************************
*
* Gorf specific input/output
*
*************************************/
READ8_MEMBER(astrocde_state::gorf_io_1_r)
WRITE_LINE_MEMBER(astrocde_state::gorf_sound_switch_w)
{
uint8_t data = (offset >> 8) & 1;
switch ((offset >> 9) & 7)
{
case 0: machine().bookkeeping().coin_counter_w(0, data); break;
case 1: machine().bookkeeping().coin_counter_w(1, data); break;
case 2: m_sparkle[0] = data; break;
case 3: m_sparkle[1] = data; break;
case 4: m_sparkle[2] = data; break;
case 5: m_sparkle[3] = data; break;
case 6:
m_astrocade_sound1->set_output_gain(0, data ? 0.0 : 1.0);
m_votrax->set_output_gain(0, data ? 1.0 : 0.0);
break;
case 7: osd_printf_debug("io_1:%d\n", data); break;
}
return 0xff;
}
READ8_MEMBER(astrocde_state::gorf_io_2_r)
{
uint8_t data = (offset >> 8) & 1;
switch ((offset >> 9) & 7)
{
case 0: output().set_lamp_value(0, data); break;
case 1: output().set_lamp_value(1, data); break;
case 2: output().set_lamp_value(2, data); break;
case 3: output().set_lamp_value(3, data); break;
case 4: output().set_lamp_value(4, data); break;
case 5: output().set_lamp_value(5, data); break;
case 6: /* n/c */ break;
case 7: output().set_lamp_value(7, data); break;
}
return 0xff;
m_astrocade_sound1->set_output_gain(0, state ? 0.0 : 1.0);
m_votrax->set_output_gain(0, state ? 1.0 : 0.0);
}
/*************************************
*
* Robby Roto specific input/output
* Demons & Dragons specific input/output
*
*************************************/
READ8_MEMBER(astrocde_state::robby_io_r)
WRITE8_MEMBER(astrocde_state::demndrgn_banksw_w)
{
uint8_t data = (offset >> 8) & 1;
int bank = (data >> 5) & 3;
m_bank4000->set_bank(bank);
m_bank8000->set_entry(bank);
}
switch ((offset >> 9) & 7)
{
case 0: machine().bookkeeping().coin_counter_w(0, data); break;
case 1: machine().bookkeeping().coin_counter_w(1, data); break;
case 2: machine().bookkeeping().coin_counter_w(2, data); break;
case 6: output().set_led_value(0, data); break;
case 7: output().set_led_value(1, data); break;
}
return 0xff;
WRITE_LINE_MEMBER(astrocde_state::demndrgn_input_select_w)
{
m_input_select = state;
}
CUSTOM_INPUT_MEMBER(astrocde_state::demndragn_joystick_r)
{
return m_joystick[m_input_select]->read();
}
WRITE8_MEMBER(astrocde_state::demndrgn_sound_w)
{
logerror("Trigger sound sample 0x%02x\n",data);
}
@ -370,35 +315,6 @@ READ8_MEMBER(astrocde_state::robby_io_r)
*
*************************************/
READ8_MEMBER(astrocde_state::profpac_io_1_r)
{
machine().bookkeeping().coin_counter_w(0, (offset >> 8) & 1);
machine().bookkeeping().coin_counter_w(1, (offset >> 9) & 1);
output().set_led_value(0, (offset >> 10) & 1);
output().set_led_value(1, (offset >> 11) & 1);
return 0xff;
}
READ8_MEMBER(astrocde_state::profpac_io_2_r)
{
output().set_lamp_value(0, (offset >> 8) & 1); /* left lamp A */
output().set_lamp_value(1, (offset >> 9) & 1); /* left lamp B */
output().set_lamp_value(2, (offset >> 10) & 1); /* left lamp C */
output().set_lamp_value(3, (offset >> 12) & 1); /* right lamp A */
output().set_lamp_value(4, (offset >> 13) & 1); /* right lamp B */
output().set_lamp_value(5, (offset >> 14) & 1); /* right lamp C */
return 0xff;
}
WRITE8_MEMBER(astrocde_state::demndrgn_banksw_w)
{
int bank = (data >> 5) & 3;
m_bank4000->set_bank(bank);
m_bank8000->set_entry(bank);
}
WRITE8_MEMBER(astrocde_state::profpac_banksw_w)
{
@ -418,36 +334,6 @@ WRITE8_MEMBER(astrocde_state::profpac_banksw_w)
}
/*************************************
*
* Demons & Dragons specific input/output
*
*************************************/
READ8_MEMBER(astrocde_state::demndrgn_io_r)
{
machine().bookkeeping().coin_counter_w(0, (offset >> 8) & 1);
machine().bookkeeping().coin_counter_w(1, (offset >> 9) & 1);
output().set_led_value(0, (offset >> 10) & 1);
output().set_led_value(1, (offset >> 11) & 1);
m_input_select = (offset >> 12) & 1;
return 0xff;
}
CUSTOM_INPUT_MEMBER(astrocde_state::demndragn_joystick_r)
{
return m_joystick[m_input_select]->read();
}
WRITE8_MEMBER(astrocde_state::demndrgn_sound_w)
{
logerror("Trigger sound sample 0x%02x\n",data);
}
/*************************************
*
@ -507,14 +393,12 @@ WRITE8_MEMBER(astrocde_state::tenpindx_lights_w)
*
*************************************/
READ8_MEMBER( astrocde_state::votrax_speech_r )
WRITE8_MEMBER(astrocde_state::votrax_speech_w)
{
uint8_t data = offset >> 8;
m_votrax->inflection_w(space, 0, data >> 6);
m_votrax->write(space, 0, data);
/* Note : We should really also use volume in this as well as frequency */
return data; /* Return nicely */
}
@ -633,13 +517,40 @@ void astrocde_state::tenpin_sub_map(address_map &map)
void astrocde_state::port_map(address_map &map)
{
map(0x0000, 0x0019).select(0xff00).rw(this, FUNC(astrocde_state::astrocade_data_chip_register_r), FUNC(astrocde_state::astrocade_data_chip_register_w));
map(0x0000, 0x000f).mirror(0xff00).rw(this, FUNC(astrocde_state::video_register_r), FUNC(astrocde_state::video_register_w));
map(0x0010, 0x001f).select(0xff00).r("astrocade1", FUNC(astrocade_io_device::read));
map(0x0010, 0x0018).select(0xff00).w("astrocade1", FUNC(astrocade_io_device::write));
map(0x0019, 0x0019).mirror(0xff00).w(this, FUNC(astrocde_state::expand_register_w));
}
void astrocde_state::port_map_discrete(address_map &map)
{
map.global_mask(0xff);
map(0x00, 0x0f).rw(this, FUNC(astrocde_state::video_register_r), FUNC(astrocde_state::video_register_w));
map(0x10, 0x10).portr("HANDLE0");
map(0x11, 0x11).portr("HANDLE1");
map(0x12, 0x12).portr("HANDLE2");
map(0x13, 0x13).portr("HANDLE3");
map(0x19, 0x19).w(this, FUNC(astrocde_state::expand_register_w));
map(0x40, 0x40).mirror(0x18).w(this, FUNC(astrocde_state::seawolf2_sound_1_w));
map(0x41, 0x41).mirror(0x18).w(this, FUNC(astrocde_state::seawolf2_sound_2_w));
map(0x42, 0x42).mirror(0x18).w("lamplatch2", FUNC(output_latch_device::write));
map(0x43, 0x43).mirror(0x18).w("lamplatch1", FUNC(output_latch_device::write));
}
void astrocde_state::port_map_ebases(address_map &map)
{
port_map(map);
map(0x0020, 0x0020).mirror(0xff07).w(this, FUNC(astrocde_state::ebases_coin_w));
map(0x0028, 0x0028).mirror(0xff07).w(this, FUNC(astrocde_state::ebases_trackball_select_w));
}
void astrocde_state::port_map_mono_pattern(address_map &map)
{
map(0x0000, 0x0019).select(0xff00).rw(this, FUNC(astrocde_state::astrocade_data_chip_register_r), FUNC(astrocde_state::astrocade_data_chip_register_w));
port_map(map);
map(0x0078, 0x007e).mirror(0xff00).w(this, FUNC(astrocde_state::astrocade_pattern_board_w));
map(0xa55b, 0xa55b).w(this, FUNC(astrocde_state::protected_ram_enable_w));
}
@ -647,29 +558,25 @@ void astrocde_state::port_map_mono_pattern(address_map &map)
void astrocde_state::port_map_stereo_pattern(address_map &map)
{
map(0x0000, 0x0019).select(0xff00).rw(this, FUNC(astrocde_state::astrocade_data_chip_register_r), FUNC(astrocde_state::astrocade_data_chip_register_w));
map(0x0050, 0x0058).select(0xff00).w("astrocade2", FUNC(astrocade_device::astrocade_sound_w));
map(0x0078, 0x007e).mirror(0xff00).w(this, FUNC(astrocde_state::astrocade_pattern_board_w));
map(0xa55b, 0xa55b).w(this, FUNC(astrocde_state::protected_ram_enable_w));
port_map_mono_pattern(map);
map(0x0050, 0x0058).select(0xff00).w("astrocade2", FUNC(astrocade_io_device::write));
}
void astrocde_state::port_map_16col_pattern(address_map &map)
{
map(0x0000, 0x0019).select(0xff00).rw(this, FUNC(astrocde_state::astrocade_data_chip_register_r), FUNC(astrocde_state::astrocade_data_chip_register_w));
map(0x0050, 0x0058).select(0xff00).w("astrocade2", FUNC(astrocade_device::astrocade_sound_w));
map(0x0078, 0x007e).mirror(0xff00).w(this, FUNC(astrocde_state::astrocade_pattern_board_w));
port_map_stereo_pattern(map);
map(0x00bf, 0x00bf).mirror(0xff00).w(this, FUNC(astrocde_state::profpac_page_select_w));
map(0x00c3, 0x00c3).mirror(0xff00).r(this, FUNC(astrocde_state::profpac_intercept_r));
map(0x00c0, 0x00c5).mirror(0xff00).w(this, FUNC(astrocde_state::profpac_screenram_ctrl_w));
map(0x00f3, 0x00f3).mirror(0xff00).w(this, FUNC(astrocde_state::profpac_banksw_w));
map(0xa55b, 0xa55b).w(this, FUNC(astrocde_state::protected_ram_enable_w));
}
void astrocde_state::port_map_16col_pattern_nosound(address_map &map)
{
map(0x0000, 0x0019).select(0xff00).rw(this, FUNC(astrocde_state::astrocade_data_chip_register_r), FUNC(astrocde_state::astrocade_data_chip_register_w));
map(0x0000, 0x000f).mirror(0xff00).rw(this, FUNC(astrocde_state::video_register_r), FUNC(astrocde_state::video_register_w));
map(0x0019, 0x0019).mirror(0xff00).w(this, FUNC(astrocde_state::expand_register_w));
map(0x0078, 0x007e).mirror(0xff00).w(this, FUNC(astrocde_state::astrocade_pattern_board_w));
map(0x00bf, 0x00bf).mirror(0xff00).w(this, FUNC(astrocde_state::profpac_page_select_w));
map(0x00c3, 0x00c3).mirror(0xff00).r(this, FUNC(astrocde_state::profpac_intercept_r));
@ -679,6 +586,14 @@ void astrocde_state::port_map_16col_pattern_nosound(address_map &map)
}
void astrocde_state::port_map_16col_pattern_demndrgn(address_map &map)
{
port_map_16col_pattern_nosound(map);
map(0x0010, 0x001f).select(0xff00).r("astrocade1", FUNC(astrocade_io_device::read));
map(0x0097, 0x0097).mirror(0xff00).w(this, FUNC(astrocde_state::demndrgn_sound_w));
}
void astrocde_state::port_map_16col_pattern_tenpindx(address_map &map)
{
port_map_16col_pattern_nosound(map);
@ -1311,7 +1226,8 @@ MACHINE_CONFIG_START(astrocde_state::astrocade_mono_sound)
/* sound hardware */
SPEAKER(config, "mono").front_center();
MCFG_ASTROCADE_ADD("astrocade1", ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade1", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_ASTROCADE_IO_SI_READ_CB(READ8(*this, astrocde_state, input_mux_r))
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0)
MACHINE_CONFIG_END
@ -1322,11 +1238,16 @@ MACHINE_CONFIG_START(astrocde_state::astrocade_stereo_sound)
SPEAKER(config, "lspeaker").front_left();
SPEAKER(config, "rspeaker").front_right();
MCFG_ASTROCADE_ADD("astrocade1", ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade1", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_ASTROCADE_IO_SI_READ_CB(READ8(*this, astrocde_state, input_mux_r))
MCFG_ASTROCADE_IO_SO0_STROBE_CB(WRITE8("watchdog", watchdog_timer_device, reset_w))
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "lspeaker", 1.0)
MCFG_ASTROCADE_ADD("astrocade2", ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade2", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "rspeaker", 1.0)
MCFG_WATCHDOG_ADD("watchdog") // MC14024B on CPU board at U18
MCFG_WATCHDOG_VBLANK_INIT("screen", 128) // CLK = VERTDR, Q7 used for RESET
MACHINE_CONFIG_END
@ -1343,7 +1264,25 @@ MACHINE_CONFIG_START(astrocde_state::seawolf2)
/* basic machine hardware */
MCFG_DEVICE_MODIFY("maincpu")
MCFG_DEVICE_PROGRAM_MAP(seawolf2_map)
MCFG_DEVICE_IO_MAP(port_map)
MCFG_DEVICE_IO_MAP(port_map_discrete)
MCFG_DEVICE_ADD("lamplatch1", OUTPUT_LATCH, 0) // 74174 on game board at N2
MCFG_OUTPUT_LATCH_BIT0_HANDLER(OUTPUT("lamp6")) // right player torpedo 4 available
MCFG_OUTPUT_LATCH_BIT1_HANDLER(OUTPUT("lamp5")) // right player torpedo 3 available
MCFG_OUTPUT_LATCH_BIT2_HANDLER(OUTPUT("lamp4")) // right player torpedo 2 available
MCFG_OUTPUT_LATCH_BIT3_HANDLER(OUTPUT("lamp3")) // right player torpedo 1 available
MCFG_OUTPUT_LATCH_BIT4_HANDLER(OUTPUT("lamp2")) // right player ready
MCFG_DEVCB_CHAIN_OUTPUT(OUTPUT("lamp1")) MCFG_DEVCB_INVERT // right player reload (active low)
MCFG_OUTPUT_LATCH_BIT5_HANDLER(OUTPUT("lamp0")) // right player explosion (hit)
MCFG_DEVICE_ADD("lamplatch2", OUTPUT_LATCH, 0) // 74174 on game board at P2
MCFG_OUTPUT_LATCH_BIT0_HANDLER(OUTPUT("lamp13")) // left player torpedo 4 available
MCFG_OUTPUT_LATCH_BIT1_HANDLER(OUTPUT("lamp12")) // left player torpedo 3 available
MCFG_OUTPUT_LATCH_BIT2_HANDLER(OUTPUT("lamp11")) // left player torpedo 2 available
MCFG_OUTPUT_LATCH_BIT3_HANDLER(OUTPUT("lamp10")) // left player torpedo 1 available
MCFG_OUTPUT_LATCH_BIT4_HANDLER(OUTPUT("lamp9")) // left player ready
MCFG_DEVCB_CHAIN_OUTPUT(OUTPUT("lamp8")) MCFG_DEVCB_INVERT // left player reload (active low)
MCFG_OUTPUT_LATCH_BIT5_HANDLER(OUTPUT("lamp7")) // left player explosion (hit)
/* sound hardware */
SPEAKER(config, "lspeaker").front_left();
@ -1372,7 +1311,13 @@ MACHINE_CONFIG_START(astrocde_state::ebases)
/* basic machine hardware */
MCFG_DEVICE_MODIFY("maincpu")
MCFG_DEVICE_PROGRAM_MAP(ebases_map)
MCFG_DEVICE_IO_MAP(port_map)
MCFG_DEVICE_IO_MAP(port_map_ebases)
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO1_STROBE_CB(WRITE8("watchdog", watchdog_timer_device, reset_w))
MCFG_WATCHDOG_ADD("watchdog") // MC14024 on CPU board at U18
MCFG_WATCHDOG_VBLANK_INIT("screen", 128) // CLK = VERTDR, Q7 used for RESET
MACHINE_CONFIG_END
@ -1384,6 +1329,17 @@ MACHINE_CONFIG_START(astrocde_state::spacezap)
MCFG_DEVICE_MODIFY("maincpu")
MCFG_DEVICE_PROGRAM_MAP(spacezap_map)
MCFG_DEVICE_IO_MAP(port_map_mono_pattern)
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO0_STROBE_CB(WRITE8("watchdog", watchdog_timer_device, reset_w))
MCFG_ASTROCADE_IO_SO3_STROBE_CB(WRITE8("outlatch", output_latch_device, write))
MCFG_DEVICE_ADD("outlatch", OUTPUT_LATCH, 0) // MC14174B on game board at U16
MCFG_OUTPUT_LATCH_BIT0_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_OUTPUT_LATCH_BIT1_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_WATCHDOG_ADD("watchdog") // MC14024 on CPU board at U18
MCFG_WATCHDOG_VBLANK_INIT("screen", 128) // CLK = VERTDR, Q7 used for RESET
MACHINE_CONFIG_END
MACHINE_CONFIG_START(astrocde_state::wow)
@ -1395,6 +1351,15 @@ MACHINE_CONFIG_START(astrocde_state::wow)
MCFG_DEVICE_PROGRAM_MAP(wow_map)
MCFG_DEVICE_IO_MAP(port_map_stereo_pattern)
MCFG_DEVICE_ADD("outlatch", CD4099, 0)
MCFG_ADDRESSABLE_LATCH_Q0_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_ADDRESSABLE_LATCH_Q1_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_ADDRESSABLE_LATCH_Q2_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<0>))
MCFG_ADDRESSABLE_LATCH_Q3_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<1>))
MCFG_ADDRESSABLE_LATCH_Q4_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<2>))
MCFG_ADDRESSABLE_LATCH_Q5_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<3>))
MCFG_ADDRESSABLE_LATCH_Q7_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<2>))
/* video hardware */
MCFG_SCREEN_MODIFY("screen")
MCFG_SCREEN_DEFAULT_POSITION(1.0, 0.0, 1.0, 0.0) /* adjusted to match screenshots */
@ -1403,6 +1368,10 @@ MACHINE_CONFIG_START(astrocde_state::wow)
/* sound hardware */
SPEAKER(config, "center").front_center();
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO5_STROBE_CB(WRITE8("outlatch", cd4099_device, write_nibble_d0))
MCFG_ASTROCADE_IO_SO7_STROBE_CB(WRITE8(*this, astrocde_state, votrax_speech_w))
MCFG_DEVICE_ADD("votrax", VOTRAX_SC01, 720000)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "center", 0.85)
MACHINE_CONFIG_END
@ -1416,6 +1385,29 @@ MACHINE_CONFIG_START(astrocde_state::gorf)
MCFG_DEVICE_PROGRAM_MAP(wow_map)
MCFG_DEVICE_IO_MAP(port_map_stereo_pattern)
MCFG_DEVICE_ADD("outlatch", CD4099, 0) // MC14099B on game board at U6
MCFG_ADDRESSABLE_LATCH_Q0_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_ADDRESSABLE_LATCH_Q1_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_ADDRESSABLE_LATCH_Q2_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<0>))
MCFG_ADDRESSABLE_LATCH_Q3_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<1>))
MCFG_ADDRESSABLE_LATCH_Q4_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<2>))
MCFG_ADDRESSABLE_LATCH_Q5_OUT_CB(WRITELINE(*this, astrocde_state, sparkle_w<3>))
MCFG_ADDRESSABLE_LATCH_Q6_OUT_CB(WRITELINE(*this, astrocde_state, gorf_sound_switch_w))
MCFG_ADDRESSABLE_LATCH_Q7_OUT_CB(OUTPUT("lamp6"))
MCFG_DEVICE_ADD("lamplatch", CD4099, 0) // MC14099B on game board at U7
MCFG_ADDRESSABLE_LATCH_Q0_OUT_CB(OUTPUT("lamp0"))
MCFG_ADDRESSABLE_LATCH_Q1_OUT_CB(OUTPUT("lamp1"))
MCFG_ADDRESSABLE_LATCH_Q2_OUT_CB(OUTPUT("lamp2"))
MCFG_ADDRESSABLE_LATCH_Q3_OUT_CB(OUTPUT("lamp3"))
MCFG_ADDRESSABLE_LATCH_Q4_OUT_CB(OUTPUT("lamp4"))
MCFG_ADDRESSABLE_LATCH_Q5_OUT_CB(OUTPUT("lamp5"))
MCFG_ADDRESSABLE_LATCH_Q6_OUT_CB(NOOP) // n/c
MCFG_ADDRESSABLE_LATCH_Q7_OUT_CB(OUTPUT("lamp7"))
MCFG_WATCHDOG_ADD("watchdog") // MC14024 on CPU board at U18
MCFG_WATCHDOG_VBLANK_INIT("screen", 128) // CLK = VERTDR, Q7 used for RESET
/* video hardware */
MCFG_SCREEN_MODIFY("screen")
MCFG_SCREEN_DEFAULT_POSITION(1.0, 0.0, 1.0, 0.0) /* adjusted to match flyer */
@ -1424,10 +1416,15 @@ MACHINE_CONFIG_START(astrocde_state::gorf)
SPEAKER(config, "upper", 0.0, 0.0, 1.0);
SPEAKER(config, "lower", 0.0, -0.5, 1.0);
MCFG_ASTROCADE_ADD("astrocade1", ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade1", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_ASTROCADE_IO_SI_READ_CB(READ8(*this, astrocde_state, input_mux_r))
MCFG_ASTROCADE_IO_SO0_STROBE_CB(WRITE8("watchdog", watchdog_timer_device, reset_w))
MCFG_ASTROCADE_IO_SO5_STROBE_CB(WRITE8("outlatch", cd4099_device, write_nibble_d0))
MCFG_ASTROCADE_IO_SO6_STROBE_CB(WRITE8("lamplatch", cd4099_device, write_nibble_d0))
MCFG_ASTROCADE_IO_SO7_STROBE_CB(WRITE8(*this, astrocde_state, votrax_speech_w))
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "upper", 1.0)
MCFG_ASTROCADE_ADD("astrocade2", ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade2", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "lower", 1.0)
MCFG_DEVICE_ADD("votrax", VOTRAX_SC01, 720000)
@ -1444,7 +1441,17 @@ MACHINE_CONFIG_START(astrocde_state::robby)
MCFG_DEVICE_PROGRAM_MAP(robby_map)
MCFG_DEVICE_IO_MAP(port_map_stereo_pattern)
MCFG_NVRAM_ADD_0FILL("nvram")
MCFG_NVRAM_ADD_0FILL("nvram") // HM6116LP-4 + battery
MCFG_DEVICE_ADD("outlatch", CD4099, 0) // on game board at U1
MCFG_ADDRESSABLE_LATCH_Q0_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_ADDRESSABLE_LATCH_Q1_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_ADDRESSABLE_LATCH_Q2_OUT_CB(WRITELINE(*this, astrocde_state, coin_counter_w<2>))
MCFG_ADDRESSABLE_LATCH_Q6_OUT_CB(OUTPUT("led0"))
MCFG_ADDRESSABLE_LATCH_Q7_OUT_CB(OUTPUT("led1"))
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO5_STROBE_CB(WRITE8("outlatch", cd4099_device, write_nibble_d0))
MACHINE_CONFIG_END
@ -1460,16 +1467,47 @@ MACHINE_CONFIG_START(astrocde_state::profpac)
MCFG_DEVICE_MODIFY("bank4000")
MCFG_DEVICE_PROGRAM_MAP(profpac_bank4000_map)
MCFG_ADDRESS_MAP_BANK_ADDR_WIDTH(20)
MCFG_DEVICE_ADD("outlatch", OUTPUT_LATCH, 0) // 74LS174 on game board at U6
MCFG_OUTPUT_LATCH_BIT0_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_OUTPUT_LATCH_BIT1_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_OUTPUT_LATCH_BIT2_HANDLER(OUTPUT("led0"))
MCFG_OUTPUT_LATCH_BIT3_HANDLER(OUTPUT("led1"))
MCFG_DEVICE_ADD("lamplatch", OUTPUT_LATCH, 0) // 74LS174 on game board at U7
MCFG_OUTPUT_LATCH_BIT0_HANDLER(OUTPUT("lamp0")) // left lamp A
MCFG_OUTPUT_LATCH_BIT1_HANDLER(OUTPUT("lamp1")) // left lamp B
MCFG_OUTPUT_LATCH_BIT2_HANDLER(OUTPUT("lamp2")) // left lamp C
MCFG_OUTPUT_LATCH_BIT4_HANDLER(OUTPUT("lamp3")) // right lamp A
MCFG_OUTPUT_LATCH_BIT5_HANDLER(OUTPUT("lamp4")) // right lamp B
MCFG_OUTPUT_LATCH_BIT6_HANDLER(OUTPUT("lamp5")) // right lamp C
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO4_STROBE_CB(WRITE8("outlatch", output_latch_device, write))
MCFG_ASTROCADE_IO_SO5_STROBE_CB(WRITE8("lamplatch", output_latch_device, write))
MACHINE_CONFIG_END
MACHINE_CONFIG_START(astrocde_state::demndrgn)
astrocade_16color_base(config);
astrocade_mono_sound(config); // used only for I/O
/* basic machine hardware */
MCFG_DEVICE_MODIFY("maincpu")
MCFG_DEVICE_PROGRAM_MAP(demndrgn_map)
MCFG_DEVICE_IO_MAP(port_map_16col_pattern_nosound)
MCFG_DEVICE_IO_MAP(port_map_16col_pattern_demndrgn)
MCFG_DEVICE_ADD("outlatch", OUTPUT_LATCH, 0)
MCFG_OUTPUT_LATCH_BIT0_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<0>))
MCFG_OUTPUT_LATCH_BIT1_HANDLER(WRITELINE(*this, astrocde_state, coin_counter_w<1>))
MCFG_OUTPUT_LATCH_BIT2_HANDLER(OUTPUT("led0"))
MCFG_OUTPUT_LATCH_BIT3_HANDLER(OUTPUT("led1"))
MCFG_OUTPUT_LATCH_BIT4_HANDLER(WRITELINE(*this, astrocde_state, demndrgn_input_select_w))
MCFG_DEVICE_MODIFY("astrocade1")
MCFG_ASTROCADE_IO_SO4_STROBE_CB(WRITE8("outlatch", output_latch_device, write))
MCFG_ASTROCADE_IO_POT0("FIREX")
MCFG_ASTROCADE_IO_POT1("FIREY")
MACHINE_CONFIG_END
@ -1727,58 +1765,42 @@ ROM_END
DRIVER_INIT_MEMBER(astrocde_state,seawolf2)
{
m_video_config = 0x00;
m_maincpu->space(AS_IO).install_write_handler(0x40, 0x40, 0, 0xff18, 0, write8_delegate(FUNC(astrocde_state::seawolf2_sound_1_w), this));
m_maincpu->space(AS_IO).install_write_handler(0x41, 0x41, 0, 0xff18, 0, write8_delegate(FUNC(astrocde_state::seawolf2_sound_2_w), this));
m_maincpu->space(AS_IO).install_write_handler(0x42, 0x43, 0, 0xff18, 0, write8_delegate(FUNC(astrocde_state::seawolf2_lamps_w), this));
}
DRIVER_INIT_MEMBER(astrocde_state,ebases)
{
m_video_config = AC_SOUND_PRESENT | AC_MONITOR_BW;
m_maincpu->space(AS_IO).install_write_handler(0x20, 0x20, 0, 0xff07, 0, write8_delegate(FUNC(astrocde_state::ebases_coin_w), this));
m_maincpu->space(AS_IO).install_write_handler(0x28, 0x28, 0, 0xff07, 0, write8_delegate(FUNC(astrocde_state::ebases_trackball_select_w), this));
}
DRIVER_INIT_MEMBER(astrocde_state,spacezap)
{
m_video_config = AC_SOUND_PRESENT | AC_MONITOR_BW;
m_maincpu->space(AS_IO).install_read_handler(0x13, 0x13, 0, 0xfc00, 0x0300, read8_delegate(FUNC(astrocde_state::spacezap_io_r), this));
}
DRIVER_INIT_MEMBER(astrocde_state,wow)
{
m_video_config = AC_SOUND_PRESENT | AC_LIGHTPEN_INTS | AC_STARS;
m_maincpu->space(AS_IO).install_read_handler(0x15, 0x15, 0, 0xf000, 0x0f00, read8_delegate(FUNC(astrocde_state::wow_io_r), this));
m_maincpu->space(AS_IO).install_read_handler(0x17, 0x17, 0, 0x0000, 0xff00, read8_delegate(FUNC(astrocde_state::votrax_speech_r), this));
}
DRIVER_INIT_MEMBER(astrocde_state,gorf)
{
m_video_config = AC_SOUND_PRESENT | AC_LIGHTPEN_INTS | AC_STARS;
m_maincpu->space(AS_IO).install_read_handler(0x15, 0x15, 0, 0xf000, 0x0f00, read8_delegate(FUNC(astrocde_state::gorf_io_1_r), this));
m_maincpu->space(AS_IO).install_read_handler(0x16, 0x16, 0, 0xf000, 0x0f00, read8_delegate(FUNC(astrocde_state::gorf_io_2_r), this));
m_maincpu->space(AS_IO).install_read_handler(0x17, 0x17, 0, 0x0000, 0xff00, read8_delegate(FUNC(astrocde_state::votrax_speech_r), this));
}
DRIVER_INIT_MEMBER(astrocde_state,robby)
{
m_video_config = AC_SOUND_PRESENT;
m_maincpu->space(AS_IO).install_read_handler(0x15, 0x15, 0, 0xf000, 0x0f00, read8_delegate(FUNC(astrocde_state::robby_io_r), this));
}
DRIVER_INIT_MEMBER(astrocde_state,profpac)
{
address_space &iospace = m_maincpu->space(AS_IO);
m_video_config = AC_SOUND_PRESENT;
iospace.install_read_handler(0x14, 0x14, 0, 0xf000, 0x0f00, read8_delegate(FUNC(astrocde_state::profpac_io_1_r), this));
iospace.install_read_handler(0x15, 0x15, 0, 0x8800, 0x7700, read8_delegate(FUNC(astrocde_state::profpac_io_2_r), this));
/* configure banking */
m_bank8000->configure_entries(0, 4, memregion("banks")->base() + 0x4000, 0x8000);
@ -1788,13 +1810,7 @@ DRIVER_INIT_MEMBER(astrocde_state,profpac)
DRIVER_INIT_MEMBER(astrocde_state,demndrgn)
{
address_space &iospace = m_maincpu->space(AS_IO);
m_video_config = 0x00;
iospace.install_read_handler(0x14, 0x14, 0, 0xe000, 0x1f00, read8_delegate(FUNC(astrocde_state::demndrgn_io_r), this));
iospace.install_read_port(0x1c, 0x1c, 0xff00, "FIREX");
iospace.install_read_port(0x1d, 0x1d, 0xff00, "FIREY");
iospace.install_write_handler(0x97, 0x97, 0, 0xff00, 0x0000, write8_delegate(FUNC(astrocde_state::demndrgn_sound_w), this));
/* configure banking */
m_bank8000->configure_entries(0, 4, memregion("banks")->base() + 0x4000, 0x8000);

View File

@ -29,14 +29,20 @@ public:
: astrocde_state(mconfig, type, tag)
, m_cart(*this, "cartslot")
, m_exp(*this, "exp")
, m_keypad(*this, "KEYPAD%u", 0U)
{ }
void astrocde(machine_config &config);
private:
DECLARE_READ8_MEMBER(inputs_r);
DECLARE_MACHINE_START(astrocde);
void astrocade_io(address_map &map);
void astrocade_mem(address_map &map);
required_device<astrocade_cart_slot_device> m_cart;
required_device<astrocade_exp_device> m_exp;
DECLARE_MACHINE_START(astrocde);
void astrocde(machine_config &config);
void astrocade_io(address_map &map);
void astrocade_mem(address_map &map);
required_ioport_array<4> m_keypad;
};
/*********************************************************************************
@ -64,7 +70,10 @@ void astrocde_mess_state::astrocade_mem(address_map &map)
void astrocde_mess_state::astrocade_io(address_map &map)
{
map(0x00, 0x1f).select(0xff00).rw(this, FUNC(astrocde_mess_state::astrocade_data_chip_register_r), FUNC(astrocde_mess_state::astrocade_data_chip_register_w));
map(0x00, 0x0f).mirror(0xff00).rw(this, FUNC(astrocde_state::video_register_r), FUNC(astrocde_state::video_register_w));
map(0x10, 0x1f).select(0xff00).r("astrocade1", FUNC(astrocade_io_device::read));
map(0x10, 0x18).select(0xff00).w("astrocade1", FUNC(astrocade_io_device::write));
map(0x19, 0x19).mirror(0xff00).w(this, FUNC(astrocde_state::expand_register_w));
}
/*************************************
@ -90,6 +99,14 @@ void astrocde_mess_state::astrocade_io(address_map &map)
*
*************************************/
READ8_MEMBER(astrocde_mess_state::inputs_r)
{
if (BIT(offset, 2))
return m_keypad[offset & 3]->read();
else
return m_handle[offset & 3]->read();
}
static INPUT_PORTS_START( astrocde )
PORT_START("P1HANDLE")
PORT_BIT(0x01, IP_ACTIVE_HIGH, IPT_JOYSTICK_UP) PORT_PLAYER(1) PORT_8WAY
@ -216,7 +233,12 @@ MACHINE_CONFIG_START(astrocde_mess_state::astrocde)
/* sound hardware */
SPEAKER(config, "mono").front_center();
MCFG_DEVICE_ADD("astrocade1", ASTROCADE, ASTROCADE_CLOCK/4)
MCFG_DEVICE_ADD("astrocade1", ASTROCADE_IO, ASTROCADE_CLOCK/4)
MCFG_ASTROCADE_IO_SI_READ_CB(READ8(*this, astrocde_mess_state, inputs_r))
MCFG_ASTROCADE_IO_POT0("P1_KNOB")
MCFG_ASTROCADE_IO_POT1("P2_KNOB")
MCFG_ASTROCADE_IO_POT2("P3_KNOB")
MCFG_ASTROCADE_IO_POT3("P4_KNOB")
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.00)
/* expansion port */

View File

@ -96,7 +96,7 @@ void g627_state::io_map(address_map &map)
map.global_mask(0xff);
map(0x00, 0x02).w(this, FUNC(g627_state::disp_w));
map(0x03, 0x07).w(this, FUNC(g627_state::lamp_w));
map(0x10, 0x17).w("astrocade", FUNC(astrocade_device::astrocade_sound_w));
map(0x10, 0x17).w("astrocade", FUNC(astrocade_io_device::write));
map(0x20, 0x27).rw("i8156", FUNC(i8155_device::io_r), FUNC(i8155_device::io_w));
}
@ -311,7 +311,7 @@ MACHINE_CONFIG_START(g627_state::g627)
/* Sound */
genpin_audio(config);
SPEAKER(config, "mono").front_center();
MCFG_DEVICE_ADD("astrocade", ASTROCADE, 14138000/8) // 0066-117XX audio chip
MCFG_DEVICE_ADD("astrocade", ASTROCADE_IO, 14138000/8) // 0066-117XX audio chip
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0)
/* Video */

View File

@ -43,18 +43,7 @@ public:
m_soundlatch(*this, "soundlatch"),
m_bank4000(*this, "bank4000"),
m_bank8000(*this, "bank8000"),
m_p1handle(*this, "P1HANDLE"),
m_p2handle(*this, "P2HANDLE"),
m_p3handle(*this, "P3HANDLE"),
m_p4handle(*this, "P4HANDLE"),
m_keypad0(*this, "KEYPAD0"),
m_keypad1(*this, "KEYPAD1"),
m_keypad2(*this, "KEYPAD2"),
m_keypad3(*this, "KEYPAD3"),
m_p1_knob(*this, "P1_KNOB"),
m_p2_knob(*this, "P2_KNOB"),
m_p3_knob(*this, "P3_KNOB"),
m_p4_knob(*this, "P4_KNOB"),
m_handle(*this, "P%uHANDLE", 1U),
m_trackball(*this, { { "TRACKX2", "TRACKY2", "TRACKX1", "TRACKY1" } }),
m_joystick(*this, { { "MOVEX", "MOVEY" } }),
m_interrupt_scanline(0xff)
@ -64,25 +53,14 @@ public:
optional_device<cpu_device> m_subcpu;
optional_device<samples_device> m_samples;
optional_device<votrax_sc01_device> m_votrax;
optional_device<astrocade_device> m_astrocade_sound1;
optional_device<astrocade_io_device> m_astrocade_sound1;
optional_shared_ptr<uint8_t> m_videoram;
optional_shared_ptr<uint8_t> m_protected_ram;
required_device<screen_device> m_screen;
optional_device<generic_latch_8_device> m_soundlatch;
optional_device<address_map_bank_device> m_bank4000;
optional_memory_bank m_bank8000;
optional_ioport m_p1handle;
optional_ioport m_p2handle;
optional_ioport m_p3handle;
optional_ioport m_p4handle;
optional_ioport m_keypad0;
optional_ioport m_keypad1;
optional_ioport m_keypad2;
optional_ioport m_keypad3;
optional_ioport m_p1_knob;
optional_ioport m_p2_knob;
optional_ioport m_p3_knob;
optional_ioport m_p4_knob;
optional_ioport_array<4> m_handle;
optional_ioport_array<4> m_trackball;
optional_ioport_array<2> m_joystick;
@ -136,28 +114,25 @@ public:
DECLARE_WRITE8_MEMBER(protected_ram_enable_w);
DECLARE_READ8_MEMBER(protected_ram_r);
DECLARE_WRITE8_MEMBER(protected_ram_w);
DECLARE_WRITE8_MEMBER(seawolf2_lamps_w);
DECLARE_WRITE8_MEMBER(seawolf2_sound_1_w);
DECLARE_WRITE8_MEMBER(seawolf2_sound_2_w);
DECLARE_WRITE8_MEMBER(ebases_trackball_select_w);
DECLARE_WRITE8_MEMBER(ebases_coin_w);
DECLARE_READ8_MEMBER(spacezap_io_r);
DECLARE_READ8_MEMBER(wow_io_r);
DECLARE_READ8_MEMBER(gorf_io_1_r);
DECLARE_READ8_MEMBER(gorf_io_2_r);
DECLARE_READ8_MEMBER(robby_io_r);
DECLARE_READ8_MEMBER(profpac_io_1_r);
DECLARE_READ8_MEMBER(profpac_io_2_r);
DECLARE_READ8_MEMBER(input_mux_r);
template<int Coin> DECLARE_WRITE_LINE_MEMBER(coin_counter_w);
template<int Bit> DECLARE_WRITE_LINE_MEMBER(sparkle_w);
DECLARE_WRITE_LINE_MEMBER(gorf_sound_switch_w);
DECLARE_WRITE8_MEMBER(profpac_banksw_w);
DECLARE_WRITE8_MEMBER(demndrgn_banksw_w);
DECLARE_READ8_MEMBER(demndrgn_io_r);
DECLARE_WRITE_LINE_MEMBER(demndrgn_input_select_w);
DECLARE_WRITE8_MEMBER(demndrgn_sound_w);
DECLARE_WRITE8_MEMBER(tenpindx_lamp_w);
DECLARE_WRITE8_MEMBER(tenpindx_counter_w);
DECLARE_WRITE8_MEMBER(tenpindx_lights_w);
DECLARE_READ8_MEMBER(astrocade_data_chip_register_r);
DECLARE_WRITE8_MEMBER(astrocade_data_chip_register_w);
DECLARE_READ8_MEMBER(video_register_r);
DECLARE_WRITE8_MEMBER(video_register_w);
DECLARE_WRITE8_MEMBER(astrocade_funcgen_w);
DECLARE_WRITE8_MEMBER(expand_register_w);
DECLARE_WRITE8_MEMBER(astrocade_pattern_board_w);
DECLARE_WRITE8_MEMBER(profpac_page_select_w);
DECLARE_READ8_MEMBER(profpac_intercept_r);
@ -193,7 +168,7 @@ public:
void init_sparklestar();
virtual void machine_start() override;
DECLARE_READ8_MEMBER( votrax_speech_r );
DECLARE_WRITE8_MEMBER(votrax_speech_w);
CUSTOM_INPUT_MEMBER( votrax_speech_status_r );
void astrocade_base(machine_config &config);
@ -213,8 +188,11 @@ public:
void demndrgn_map(address_map &map);
void ebases_map(address_map &map);
void port_map(address_map &map);
void port_map_discrete(address_map &map);
void port_map_ebases(address_map &map);
void port_map_16col_pattern(address_map &map);
void port_map_16col_pattern_nosound(address_map &map);
void port_map_16col_pattern_demndrgn(address_map &map);
void port_map_16col_pattern_tenpindx(address_map &map);
void port_map_mono_pattern(address_map &map);
void port_map_stereo_pattern(address_map &map);

View File

@ -469,151 +469,100 @@ TIMER_CALLBACK_MEMBER(astrocde_state::scanline_callback)
*
*************************************/
READ8_MEMBER(astrocde_state::astrocade_data_chip_register_r)
READ8_MEMBER(astrocde_state::video_register_r)
{
uint8_t result = 0xff;
/* these are the core registers */
switch (offset & 0xff)
{
case 0x08: /* intercept feedback */
result = m_funcgen_intercept;
m_funcgen_intercept = 0;
break;
case 0x08: /* intercept feedback */
result = m_funcgen_intercept;
m_funcgen_intercept = 0;
break;
case 0x0e: /* vertical feedback (from lightpen interrupt) */
result = m_vertical_feedback;
break;
case 0x0e: /* vertical feedback (from lightpen interrupt) */
result = m_vertical_feedback;
break;
case 0x0f: /* horizontal feedback (from lightpen interrupt) */
result = m_horizontal_feedback;
break;
case 0x10: /* player 1 handle */
result = m_p1handle.read_safe(0xff);
break;
case 0x11: /* player 2 handle */
result = m_p2handle.read_safe(0xff);
break;
case 0x12: /* player 3 handle */
result = m_p3handle.read_safe(0xff);
break;
case 0x13: /* player 4 handle */
result = m_p4handle.read_safe(0xff);
break;
case 0x14: /* keypad column 0 */
result = m_keypad0.read_safe(0xff);
break;
case 0x15: /* keypad column 1 */
result = m_keypad1.read_safe(0xff);
break;
case 0x16: /* keypad column 2 */
result = m_keypad2.read_safe(0xff);
break;
case 0x17: /* keypad column 3 */
result = m_keypad3.read_safe(0xff);
break;
case 0x1c: /* player 1 knob */
result = m_p1_knob.read_safe(0xff);
break;
case 0x1d: /* player 2 knob */
result = m_p2_knob.read_safe(0xff);
break;
case 0x1e: /* player 3 knob */
result = m_p3_knob.read_safe(0xff);
break;
case 0x1f: /* player 4 knob */
result = m_p4_knob.read_safe(0xff);
break;
case 0x0f: /* horizontal feedback (from lightpen interrupt) */
result = m_horizontal_feedback;
break;
}
return result;
}
WRITE8_MEMBER(astrocde_state::astrocade_data_chip_register_w)
WRITE8_MEMBER(astrocde_state::video_register_w)
{
/* these are the core registers */
switch (offset & 0xff)
{
case 0x00: /* color table is in registers 0-7 */
case 0x01:
case 0x02:
case 0x03:
case 0x04:
case 0x05:
case 0x06:
case 0x07:
m_colors[offset & 7] = data;
break;
case 0x00: /* color table is in registers 0-7 */
case 0x01:
case 0x02:
case 0x03:
case 0x04:
case 0x05:
case 0x06:
case 0x07:
m_colors[offset & 7] = data;
break;
case 0x08: /* mode register */
m_video_mode = data & 1;
break;
case 0x08: /* mode register */
m_video_mode = data & 1;
break;
case 0x09: /* color split pixel */
m_colorsplit = 2 * (data & 0x3f);
m_bgdata = ((data & 0xc0) >> 6) * 0x55;
break;
case 0x09: /* color split pixel */
m_colorsplit = 2 * (data & 0x3f);
m_bgdata = ((data & 0xc0) >> 6) * 0x55;
break;
case 0x0a: /* vertical blank register */
m_vblank = data;
break;
case 0x0a: /* vertical blank register */
m_vblank = data;
break;
case 0x0b: /* color block transfer */
m_colors[(offset >> 8) & 7] = data;
break;
case 0x0b: /* color block transfer */
m_colors[(offset >> 8) & 7] = data;
break;
case 0x0c: /* function generator */
m_funcgen_control = data;
m_funcgen_expand_count = 0; /* reset flip-flop for expand mode on write to this register */
m_funcgen_rotate_count = 0; /* reset counter for rotate mode on write to this register */
m_funcgen_shift_prev_data = 0; /* reset shift buffer on write to this register */
break;
case 0x0c: /* function generator */
m_funcgen_control = data;
m_funcgen_expand_count = 0; /* reset flip-flop for expand mode on write to this register */
m_funcgen_rotate_count = 0; /* reset counter for rotate mode on write to this register */
m_funcgen_shift_prev_data = 0; /* reset shift buffer on write to this register */
break;
case 0x0d: /* interrupt feedback */
m_interrupt_vector = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x0d: /* interrupt feedback */
m_interrupt_vector = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x0e: /* interrupt enable and mode */
m_interrupt_enabl = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x0e: /* interrupt enable and mode */
m_interrupt_enabl = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x0f: /* interrupt line */
m_interrupt_scanline = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x0f: /* interrupt line */
m_interrupt_scanline = data;
m_maincpu->set_input_line(0, CLEAR_LINE);
break;
case 0x10: /* master oscillator register */
case 0x11: /* tone A frequency register */
case 0x12: /* tone B frequency register */
case 0x13: /* tone C frequency register */
case 0x14: /* vibrato register */
case 0x15: /* tone C volume, noise modulation and MUX register */
case 0x16: /* tone A volume and tone B volume register */
case 0x17: /* noise volume register */
case 0x18: /* sound block transfer */
if (m_video_config & AC_SOUND_PRESENT)
m_astrocade_sound1->astrocade_sound_w(space, offset, data);
break;
case 0x19: /* expand register */
m_funcgen_expand_color[0] = data & 0x03;
m_funcgen_expand_color[1] = (data >> 2) & 0x03;
break;
#ifdef UNUSED_OLD_CODE
case 0x10: /* master oscillator register */
case 0x11: /* tone A frequency register */
case 0x12: /* tone B frequency register */
case 0x13: /* tone C frequency register */
case 0x14: /* vibrato register */
case 0x15: /* tone C volume, noise modulation and MUX register */
case 0x16: /* tone A volume and tone B volume register */
case 0x17: /* noise volume register */
case 0x18: /* sound block transfer */
if (m_video_config & AC_SOUND_PRESENT)
m_astrocade_sound1->write(space, offset, data);
break;
#endif
}
}
@ -713,6 +662,13 @@ WRITE8_MEMBER(astrocde_state::astrocade_funcgen_w)
}
WRITE8_MEMBER(astrocde_state::expand_register_w)
{
m_funcgen_expand_color[0] = data & 0x03;
m_funcgen_expand_color[1] = (data >> 2) & 0x03;
}
/*************************************
*