sega/sg1000.cpp: Slotified controller ports.

* Replaced built-in controllers with Sega controller ports for SC-3000
  and SG-1000.
* Fixed inappropriate default assignment of SG-1000 pause button to P
  key, conflicting with the default emulator pause assignment.
* Got rid of half a player 2 D-pad that was somehow polluting the
  Othello Multivision FG-2000.
* Hooked up SF-7000 Centronics busy line to previously unused function.
This commit is contained in:
Vas Crabb 2022-12-18 01:19:30 +11:00
parent 0fba4f8018
commit 3a4bb633ac
3 changed files with 214 additions and 239 deletions

View File

@ -4,27 +4,24 @@
Sega 7-bit I/O port emulation
1 Up in
2 Down in
3 Left in
4 Right in
5 +5V
6 TL TxD in
7 TH in/out edge-sensitive
8 GND
9 TR RxD in/out
10 NC -
Pin 1 2 3 4 5 6 7 8 9 10
Up Down Left Right TL TH TR
TxD RXD
PC0 PC1 PC2 PC3 PC4 PC6 PC5
SC-3000 I I I I N/C I N/C GND I
SG-1000 I I I I N/C I GND GND I
SG-1000 Mark III I I I I +5V I GND GND I
Master System I I I I +5V I I/O GND I/O
Mega Drive I/O I/O I/O I/O +5V I/O I/O GND I/O
Game Gear I/O I/O I/O I/O +5V I/O I/O GND I/O N/C
DE-9 connector on most systems, or 10-pin tongue connector on
Game Gear (Hoshiden HDC-0492). Pin 10 is not connected if
present.
SG-1000 Mark III:
* Pin 7 (TH) tied to ground
* Pin 9 (TR) is input only
Mega Drive, Game Gear:
* All pins besides +5V and GND are in/out
* Male DE-9 connector on most systems.
* Female DE-9 connector for Mega Drive EXP port.
* 10-pin tongue connector on Game Gear (Hoshiden HDC-0492).
* TH/PC6 can latch the VDP's horizontal counter and/or raise
interrupts on some systems.
* Mega Drive and Game Gear can route TL/PC4 and TR/PC5 to a
UART for serial communication.
**********************************************************************/
#ifndef MAME_BUS_SMS_CTRL_SMSCTRL_H

View File

@ -65,11 +65,130 @@ Notes:
#include "emu.h"
#include "sg1000.h"
#include "bus/centronics/ctronics.h"
#include "bus/rs232/rs232.h"
#include "bus/sega8/sega8_slot.h"
#include "bus/sg1000_exp/sg1000exp.h"
#include "bus/sms_ctrl/controllers.h"
#include "bus/sms_ctrl/smsctrl.h"
#include "cpu/z80/z80.h"
#include "imagedev/floppy.h"
#include "machine/i8251.h"
#include "machine/i8255.h"
#include "machine/ram.h"
#include "machine/upd765.h"
#include "sound/sn76496.h"
#include "video/tms9928a.h"
#include "crsshair.h"
#include "softlist_dev.h"
#include "speaker.h"
#include "formats/sf7000_dsk.h"
namespace {
#define Z80_TAG "z80"
#define SN76489AN_TAG "sn76489an"
#define UPD765_TAG "upd765"
#define UPD8251_TAG "upd8251"
#define UPD9255_TAG "upd9255"
#define UPD9255_1_TAG "upd9255_1" // "upd9255_0" is being used by sk1100 device
#define TMS9918A_TAG "tms9918a"
#define RS232_TAG "rs232"
class sg1000_state : public driver_device
{
public:
sg1000_state(const machine_config &mconfig, device_type type, const char *tag) :
driver_device(mconfig, type, tag),
m_maincpu(*this, Z80_TAG),
m_ram(*this, RAM_TAG),
m_rom(*this, Z80_TAG),
m_cart(*this, "slot"),
m_sgexpslot(*this, "sgexp"),
m_ctrlports(*this, "ctrl%u", 1U)
{ }
void sg1000(machine_config &config);
void omv(machine_config &config);
DECLARE_INPUT_CHANGED_MEMBER( trigger_nmi );
protected:
required_device<cpu_device> m_maincpu;
required_device<ram_device> m_ram;
required_memory_region m_rom;
optional_device<sega8_cart_slot_device> m_cart;
optional_device<sg1000_expansion_slot_device> m_sgexpslot;
optional_device_array<sms_control_port_device, 2> m_ctrlports;
virtual void machine_start() override;
uint8_t peripheral_r(offs_t offset);
void peripheral_w(offs_t offset, uint8_t data);
uint8_t omv_r(offs_t offset);
void omv_w(offs_t offset, uint8_t data);
void sg1000_base(machine_config &config);
void omv_io_map(address_map &map);
void omv_map(address_map &map);
void sc3000_io_map(address_map &map);
void sc3000_map(address_map &map);
void sg1000_io_map(address_map &map);
void sg1000_map(address_map &map);
};
class sc3000_state : public sg1000_state
{
public:
sc3000_state(const machine_config &mconfig, device_type type, const char *tag) :
sg1000_state(mconfig, type, tag)
{ }
void sc3000(machine_config &config);
protected:
virtual void machine_start() override;
void sc3000_base(machine_config &config);
};
class sf7000_state : public sc3000_state
{
public:
sf7000_state(const machine_config &mconfig, device_type type, const char *tag) :
sc3000_state(mconfig, type, tag),
m_fdc(*this, UPD765_TAG),
m_centronics(*this, "centronics"),
m_floppy0(*this, UPD765_TAG ":0:3ssdd")
{ }
void sf7000(machine_config &config);
private:
required_device<upd765a_device> m_fdc;
required_device<centronics_device> m_centronics;
required_device<floppy_image_device> m_floppy0;
int m_centronics_busy = 0;
virtual void machine_start() override;
virtual void machine_reset() override;
DECLARE_WRITE_LINE_MEMBER( write_centronics_busy );
uint8_t ppi_pa_r();
void ppi_pc_w(uint8_t data);
void sf7000_io_map(address_map &map);
void sf7000_map(address_map &map);
static void floppy_formats(format_registration &fr);
};
/***************************************************************************
READ/WRITE HANDLERS
@ -97,16 +216,11 @@ uint8_t sg1000_state::peripheral_r(offs_t offset)
bool joy_ports_disabled = m_sgexpslot->is_readable(offset);
if (joy_ports_disabled)
{
return m_sgexpslot->read(offset);
}
else if (offset & 0x01)
return BIT(m_ctrlports[1]->in_r(), 2, 4) | 0xf0;
else
{
if (offset & 0x01)
return m_pb7->read();
else
return m_pa7->read();
}
return BIT(m_ctrlports[0]->in_r(), 0, 6) | (BIT(m_ctrlports[1]->in_r(), 0, 2) << 6);
}
void sg1000_state::peripheral_w(offs_t offset, uint8_t data)
@ -174,7 +288,7 @@ void sg1000_state::omv_io_map(address_map &map)
void sg1000_state::sc3000_map(address_map &map)
{
map(0x0000, 0xbfff).rw(CARTSLOT_TAG, FUNC(sega8_cart_slot_device::read_cart), FUNC(sega8_cart_slot_device::write_cart));
map(0x0000, 0xbfff).rw(m_cart, FUNC(sega8_cart_slot_device::read_cart), FUNC(sega8_cart_slot_device::write_cart));
map(0xc000, 0xc7ff).mirror(0x3800).ram();
}
@ -185,7 +299,7 @@ void sg1000_state::sc3000_map(address_map &map)
void sg1000_state::sc3000_io_map(address_map &map)
{
map.global_mask(0xff);
map(0x00, 0xff).rw(CARTSLOT_TAG, FUNC(sega8_cart_slot_device::read_io), FUNC(sega8_cart_slot_device::write_io));
map(0x00, 0xff).rw(m_cart, FUNC(sega8_cart_slot_device::read_io), FUNC(sega8_cart_slot_device::write_io));
map(0x7f, 0x7f).w(SN76489AN_TAG, FUNC(sn76489a_device::write));
map(0xbe, 0xbf).rw(TMS9918A_TAG, FUNC(tms9918a_device::read), FUNC(tms9918a_device::write));
map(0xdc, 0xdf).rw(FUNC(sg1000_state::peripheral_r), FUNC(sg1000_state::peripheral_w));
@ -244,30 +358,9 @@ INPUT_CHANGED_MEMBER( sg1000_state::trigger_nmi )
INPUT_PORTS( sg1000 )
-------------------------------------------------*/
static INPUT_PORTS_START( sg1000_joy )
PORT_START("PA7")
PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_UP )
PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN )
PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT )
PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT )
PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON1 )
PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON2 )
PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2)
PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2)
PORT_START("PB7")
PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2)
PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2)
PORT_BIT( 0x04, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_PLAYER(2)
PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_PLAYER(2)
PORT_BIT( 0xf0, IP_ACTIVE_LOW, IPT_UNUSED )
INPUT_PORTS_END
static INPUT_PORTS_START( sg1000 )
PORT_INCLUDE( sg1000_joy )
PORT_START("NMI")
PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_START ) PORT_NAME("PAUSE") PORT_CODE(KEYCODE_P) PORT_CHANGED_MEMBER(DEVICE_SELF, sg1000_state, trigger_nmi, 0)
PORT_BIT( 0x01, IP_ACTIVE_HIGH, IPT_OTHER ) PORT_NAME(DEF_STR(Pause)) PORT_CODE(KEYCODE_1) PORT_CHANGED_MEMBER(DEVICE_SELF, sg1000_state, trigger_nmi, 0)
INPUT_PORTS_END
/*-------------------------------------------------
@ -312,18 +405,21 @@ static INPUT_PORTS_START( omv1000 )
PORT_BIT( 0x08, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT )
PORT_BIT( 0x10, IP_ACTIVE_LOW, IPT_BUTTON1 ) PORT_NAME("S-1")
PORT_BIT( 0x20, IP_ACTIVE_LOW, IPT_BUTTON2 ) PORT_NAME("S-2")
PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2)
PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2)
PORT_BIT( 0xc0, IP_ACTIVE_LOW, IPT_UNUSED )
// The OMV FG-1000 has no 2nd joystick
// http://www.famitsu.com/image/29819/pEllnbNQfCJ58skZ25uB511N6eSFfAu6.jpg
PORT_START("C5")
PORT_BIT( 0xff, IP_ACTIVE_LOW, IPT_UNUSED )
INPUT_PORTS_END
static INPUT_PORTS_START( omv2000 )
// FIXME: second controller attaches to a 9-pin port and should be a slot
PORT_INCLUDE( omv1000 )
PORT_MODIFY("C4")
PORT_BIT( 0x40, IP_ACTIVE_LOW, IPT_JOYSTICK_UP ) PORT_PLAYER(2)
PORT_BIT( 0x80, IP_ACTIVE_LOW, IPT_JOYSTICK_DOWN ) PORT_PLAYER(2)
PORT_MODIFY("C5")
PORT_BIT( 0x01, IP_ACTIVE_LOW, IPT_JOYSTICK_LEFT ) PORT_PLAYER(2)
PORT_BIT( 0x02, IP_ACTIVE_LOW, IPT_JOYSTICK_RIGHT ) PORT_PLAYER(2)
@ -337,8 +433,6 @@ INPUT_PORTS_END
-------------------------------------------------*/
static INPUT_PORTS_START( sc3000 )
PORT_INCLUDE( sg1000_joy )
// keyboard keys are added by the embedded sk1100 device
PORT_START("NMI")
@ -471,6 +565,9 @@ void sg1000_state::machine_start()
if (m_cart)
m_cart->save_ram();
m_ctrlports[0]->out_w(0x3f, 0x40);
m_ctrlports[1]->out_w(0x3f, 0x40);
}
/*-------------------------------------------------
@ -489,6 +586,9 @@ void sc3000_state::machine_start()
if (m_cart)
m_cart->save_ram();
m_ctrlports[0]->out_w(0x7f, 0x00);
m_ctrlports[1]->out_w(0x7f, 0x00);
}
@ -518,37 +618,62 @@ void sf7000_state::machine_reset()
MACHINE DRIVERS
***************************************************************************/
/*-------------------------------------------------
machine_config( sg1000 )
-------------------------------------------------*/
void sg1000_state::sg1000(machine_config &config)
void sg1000_state::sg1000_base(machine_config &config)
{
/* basic machine hardware */
Z80(config, m_maincpu, XTAL(10'738'635)/3);
m_maincpu->set_addrmap(AS_PROGRAM, &sg1000_state::sg1000_map);
m_maincpu->set_addrmap(AS_IO, &sg1000_state::sg1000_io_map);
Z80(config, m_maincpu, XTAL(10'738'635) / 3); // LH0080A
/* video hardware */
tms9918a_device &vdp(TMS9918A(config, TMS9918A_TAG, XTAL(10'738'635)));
vdp.set_screen("screen");
vdp.set_vram_size(0x4000);
vdp.int_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0);
SCREEN(config, "screen", SCREEN_TYPE_RASTER);
/* sound hardware */
SPEAKER(config, "mono").front_center();
SN76489A(config, SN76489AN_TAG, XTAL(10'738'635)/3).add_route(ALL_OUTPUTS, "mono", 1.00);
SN76489A(config, SN76489AN_TAG, XTAL(10'738'635) / 3).add_route(ALL_OUTPUTS, "mono", 1.00);
/* software lists */
SOFTWARE_LIST(config, "cart_list").set_original("sg1000");
}
void sc3000_state::sc3000_base(machine_config &config)
{
sg1000_base(config);
/* controller ports */
SMS_CONTROL_PORT(config, m_ctrlports[0], sms_control_port_passive_devices, SMS_CTRL_OPTION_JOYPAD);
SMS_CONTROL_PORT(config, m_ctrlports[1], sms_control_port_passive_devices, SMS_CTRL_OPTION_JOYPAD);
/* sc3000 has all sk1100 features built-in, so add it as a fixed slot */
SG1000_EXPANSION_SLOT(config, m_sgexpslot, sg1000_expansion_devices, "sk1100", true);
/* the sk1100 device will add sc3000 cart and cass lists */
}
/*-------------------------------------------------
machine_config( sg1000 )
-------------------------------------------------*/
void sg1000_state::sg1000(machine_config &config)
{
sg1000_base(config);
m_maincpu->set_addrmap(AS_PROGRAM, &sg1000_state::sg1000_map);
m_maincpu->set_addrmap(AS_IO, &sg1000_state::sg1000_io_map);
/* controller ports */
SMS_CONTROL_PORT(config, m_ctrlports[0], sms_control_port_passive_devices, SMS_CTRL_OPTION_JOYPAD);
SMS_CONTROL_PORT(config, m_ctrlports[1], sms_control_port_passive_devices, SMS_CTRL_OPTION_JOYPAD);
/* expansion slot */
SG1000_EXPANSION_SLOT(config, m_sgexpslot, sg1000_expansion_devices, nullptr, false);
/* cartridge */
SG1000_CART_SLOT(config, CARTSLOT_TAG, sg1000_cart, nullptr).set_must_be_loaded(true);
/* software lists */
SOFTWARE_LIST(config, "cart_list").set_original("sg1000");
SG1000_CART_SLOT(config, m_cart, sg1000_cart, nullptr).set_must_be_loaded(true);
/* internal ram */
RAM(config, m_ram).set_default_size("1K");
@ -560,14 +685,19 @@ void sg1000_state::sg1000(machine_config &config)
void sg1000_state::omv(machine_config &config)
{
sg1000(config);
sg1000_base(config);
m_maincpu->set_addrmap(AS_PROGRAM, &sg1000_state::omv_map);
m_maincpu->set_addrmap(AS_IO, &sg1000_state::omv_io_map);
OMV_CART_SLOT(config.replace(), CARTSLOT_TAG, sg1000_cart, nullptr);
/* expansion slot */
SG1000_EXPANSION_SLOT(config, m_sgexpslot, sg1000_expansion_devices, nullptr, false);
m_ram->set_default_size("2K");
/* cartridge */
OMV_CART_SLOT(config, m_cart, sg1000_cart, nullptr);
/* internal ram */
RAM(config, m_ram).set_default_size("2K");
}
/*-------------------------------------------------
@ -576,32 +706,13 @@ void sg1000_state::omv(machine_config &config)
void sc3000_state::sc3000(machine_config &config)
{
/* basic machine hardware */
Z80(config, m_maincpu, XTAL(10'738'635)/3); // LH0080A
sc3000_base(config);
m_maincpu->set_addrmap(AS_PROGRAM, &sc3000_state::sc3000_map);
m_maincpu->set_addrmap(AS_IO, &sc3000_state::sc3000_io_map);
/* video hardware */
tms9918a_device &vdp(TMS9918A(config, TMS9918A_TAG, XTAL(10'738'635)));
vdp.set_screen("screen");
vdp.set_vram_size(0x4000);
vdp.int_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0);
SCREEN(config, "screen", SCREEN_TYPE_RASTER);
/* sound hardware */
SPEAKER(config, "mono").front_center();
SN76489A(config, SN76489AN_TAG, XTAL(10'738'635)/3).add_route(ALL_OUTPUTS, "mono", 1.00);
/* sc3000 has all sk1100 features built-in, so add it as a fixed slot */
SG1000_EXPANSION_SLOT(config, m_sgexpslot, sg1000_expansion_devices, "sk1100", true);
/* cartridge */
SC3000_CART_SLOT(config, CARTSLOT_TAG, sg1000_cart, nullptr).set_must_be_loaded(true);
/* software lists */
SOFTWARE_LIST(config, "cart_list").set_original("sg1000");
/* the sk1100 device will add sc3000 cart and cass lists */
SC3000_CART_SLOT(config, m_cart, sg1000_cart, nullptr).set_must_be_loaded(true);
/* internal ram */
RAM(config, m_ram).set_default_size("2K");
@ -613,23 +724,13 @@ void sc3000_state::sc3000(machine_config &config)
void sf7000_state::sf7000(machine_config &config)
{
/* basic machine hardware */
Z80(config, m_maincpu, XTAL(10'738'635)/3);
// FIXME: this thing is actually a cartridge slot peripheral for the SC-3000 and shouldn't be a separate machine
sc3000_base(config);
m_maincpu->set_addrmap(AS_PROGRAM, &sf7000_state::sf7000_map);
m_maincpu->set_addrmap(AS_IO, &sf7000_state::sf7000_io_map);
/* video hardware */
tms9918a_device &vdp(TMS9918A(config, TMS9918A_TAG, XTAL(10'738'635)));
vdp.set_screen("screen");
vdp.set_vram_size(0x4000);
vdp.int_callback().set_inputline(m_maincpu, INPUT_LINE_IRQ0);
SCREEN(config, "screen", SCREEN_TYPE_RASTER);
/* sound hardware */
SPEAKER(config, "mono").front_center();
SN76489A(config, SN76489AN_TAG, XTAL(10'738'635)/3).add_route(ALL_OUTPUTS, "mono", 1.00);
/* devices */
i8255_device &ppi(I8255(config, UPD9255_1_TAG));
ppi.in_pa_callback().set(FUNC(sf7000_state::ppi_pa_r));
@ -649,13 +750,11 @@ void sf7000_state::sf7000(machine_config &config)
FLOPPY_CONNECTOR(config, UPD765_TAG ":0", sf7000_floppies, "3ssdd", sf7000_state::floppy_formats);
CENTRONICS(config, m_centronics, centronics_devices, "printer");
m_centronics->busy_handler().set(FUNC(sf7000_state::write_centronics_busy));
output_latch_device &cent_data_out(OUTPUT_LATCH(config, "cent_data_out"));
m_centronics->set_output_latch(cent_data_out);
/* sf7000 (sc3000) has all sk1100 features built-in, so add it as a fixed slot */
SG1000_EXPANSION_SLOT(config, m_sgexpslot, sg1000_expansion_devices, "sk1100", true);
/* software lists */
SOFTWARE_LIST(config, "flop_list").set_original("sf7000");
@ -692,11 +791,14 @@ ROM_START( omv2000 )
ROM_LOAD( "omvbios.bin", 0x0000, 0x4000, CRC(c5a67b95) SHA1(6d7c64dd60dee4a33061d3d3a7c2ed190d895cdb) )
ROM_END
} // anonymous namespace
/***************************************************************************
SYSTEM DRIVERS
***************************************************************************/
/* YEAR NAME PARENT COMPAT MACHINE INPUT CLASS INIT COMPANY FULLNAME FLAGS */
// YEAR NAME PARENT COMPAT MACHINE INPUT CLASS INIT COMPANY FULLNAME FLAGS
CONS( 1983, sg1000, 0, 0, sg1000, sg1000, sg1000_state, empty_init, "Sega", "SG-1000", MACHINE_SUPPORTS_SAVE )
CONS( 1984, sg1000m2, sg1000, 0, sc3000, sc3000, sc3000_state, empty_init, "Sega", "SG-1000 II", MACHINE_SUPPORTS_SAVE )
COMP( 1983, sc3000, 0, sg1000, sc3000, sc3000, sc3000_state, empty_init, "Sega", "SC-3000", MACHINE_SUPPORTS_SAVE )

View File

@ -1,124 +0,0 @@
// license:BSD-3-Clause
// copyright-holders:Curt Coder
#ifndef MAME_INCLUDES_SG1000_H
#define MAME_INCLUDES_SG1000_H
#include "cpu/z80/z80.h"
#include "formats/sf7000_dsk.h"
#include "imagedev/floppy.h"
#include "imagedev/printer.h"
#include "bus/centronics/ctronics.h"
#include "machine/i8255.h"
#include "machine/i8251.h"
#include "machine/ram.h"
#include "bus/sega8/sega8_slot.h"
#include "bus/sg1000_exp/sg1000exp.h"
#include "machine/upd765.h"
#include "sound/sn76496.h"
#include "video/tms9928a.h"
#include "crsshair.h"
#define SCREEN_TAG "screen"
#define Z80_TAG "z80"
#define SN76489AN_TAG "sn76489an"
#define UPD765_TAG "upd765"
#define UPD8251_TAG "upd8251"
#define UPD9255_TAG "upd9255"
#define UPD9255_1_TAG "upd9255_1" // "upd9255_0" is being used by sk1100 device
#define CENTRONICS_TAG "centronics"
#define TMS9918A_TAG "tms9918a"
#define RS232_TAG "rs232"
#define CARTSLOT_TAG "slot"
#define EXPSLOT_TAG "sgexp"
class sg1000_state : public driver_device
{
public:
sg1000_state(const machine_config &mconfig, device_type type, const char *tag)
: driver_device(mconfig, type, tag),
m_maincpu(*this, Z80_TAG),
m_ram(*this, RAM_TAG),
m_rom(*this, Z80_TAG),
m_cart(*this, CARTSLOT_TAG),
m_sgexpslot(*this, EXPSLOT_TAG),
m_pa7(*this, "PA7"),
m_pb7(*this, "PB7")
{ }
void sg1000(machine_config &config);
void omv(machine_config &config);
DECLARE_INPUT_CHANGED_MEMBER( trigger_nmi );
protected:
required_device<cpu_device> m_maincpu;
required_device<ram_device> m_ram;
required_memory_region m_rom;
optional_device<sega8_cart_slot_device> m_cart;
optional_device<sg1000_expansion_slot_device> m_sgexpslot;
optional_ioport m_pa7;
optional_ioport m_pb7;
virtual void machine_start() override;
uint8_t peripheral_r(offs_t offset);
void peripheral_w(offs_t offset, uint8_t data);
uint8_t omv_r(offs_t offset);
void omv_w(offs_t offset, uint8_t data);
void omv_io_map(address_map &map);
void omv_map(address_map &map);
void sc3000_io_map(address_map &map);
void sc3000_map(address_map &map);
void sg1000_io_map(address_map &map);
void sg1000_map(address_map &map);
};
class sc3000_state : public sg1000_state
{
public:
sc3000_state(const machine_config &mconfig, device_type type, const char *tag)
: sg1000_state(mconfig, type, tag)
{ }
void sc3000(machine_config &config);
protected:
virtual void machine_start() override;
};
class sf7000_state : public sc3000_state
{
public:
sf7000_state(const machine_config &mconfig, device_type type, const char *tag)
: sc3000_state(mconfig, type, tag),
m_fdc(*this, UPD765_TAG),
m_centronics(*this, CENTRONICS_TAG),
m_floppy0(*this, UPD765_TAG ":0:3ssdd")
{ }
void sf7000(machine_config &config);
private:
required_device<upd765a_device> m_fdc;
required_device<centronics_device> m_centronics;
required_device<floppy_image_device> m_floppy0;
virtual void machine_start() override;
virtual void machine_reset() override;
int m_centronics_busy = 0;
DECLARE_WRITE_LINE_MEMBER( write_centronics_busy );
uint8_t ppi_pa_r();
void ppi_pc_w(uint8_t data);
static void floppy_formats(format_registration &fr);
void sf7000_io_map(address_map &map);
void sf7000_map(address_map &map);
};
#endif