From d3138d7dd41e85504d4f99788b5ddab0f2294039 Mon Sep 17 00:00:00 2001 From: arbee Date: Sun, 20 Sep 2020 22:41:42 -0400 Subject: apple2: preliminary support for the Sider SASI card and the Xebec OEM version [R. Belmont] --- scripts/src/bus.lua | 2 + src/devices/bus/a2bus/sider.cpp | 277 ++++++++++++++++++++++++++++++++++++++++ src/devices/bus/a2bus/sider.h | 77 +++++++++++ src/mame/drivers/apple2e.cpp | 3 + src/mame/drivers/apple2gs.cpp | 5 +- 5 files changed, 363 insertions(+), 1 deletion(-) create mode 100644 src/devices/bus/a2bus/sider.cpp create mode 100644 src/devices/bus/a2bus/sider.h diff --git a/scripts/src/bus.lua b/scripts/src/bus.lua index e2404cf1abf..9b0c50556e2 100644 --- a/scripts/src/bus.lua +++ b/scripts/src/bus.lua @@ -2378,6 +2378,8 @@ if (BUSES["A2BUS"]~=null) then MAME_DIR .. "src/devices/bus/a2bus/cmsscsi.h", MAME_DIR .. "src/devices/bus/a2bus/uthernet.cpp", MAME_DIR .. "src/devices/bus/a2bus/uthernet.h", + MAME_DIR .. "src/devices/bus/a2bus/sider.cpp", + MAME_DIR .. "src/devices/bus/a2bus/sider.h", } end diff --git a/src/devices/bus/a2bus/sider.cpp b/src/devices/bus/a2bus/sider.cpp new file mode 100644 index 00000000000..97826b9b3d5 --- /dev/null +++ b/src/devices/bus/a2bus/sider.cpp @@ -0,0 +1,277 @@ +// license:BSD-3-Clause +// copyright-holders:R. Belmont +/********************************************************************* + + sider.cpp + + Implementation of the First Class Peripherals / Advanced Tech Services / Xebec SASI Card + + The original card was by Xebec; the Sider's relationship with Xebec is not clear, but + the Sider version of the firmware is quite different (and much more compact). + + $C0(n+8)X space: + $0: read state / write latch + $1: read data / write control + + State: + b3: /Busy + b4: /Message + b5: I/O + b6: C/D + b7: REQ + + Control: + b4: drive contents of output latch onto the SASI bus (reverse logic; latch is driven when this bit is clear) + b5: reset bus + b6: /BSY + b7: /SEL + +*********************************************************************/ + +#include "emu.h" +#include "sider.h" +#include "bus/scsi/scsihd.h" +#include "bus/scsi/s1410.h" + +/*************************************************************************** + PARAMETERS +***************************************************************************/ + +//************************************************************************** +// GLOBAL VARIABLES +//************************************************************************** + +DEFINE_DEVICE_TYPE(A2BUS_SIDER, a2bus_sidercard_device, "a2sider", "First Class Peripherals Sider SASI Card") +DEFINE_DEVICE_TYPE(A2BUS_XEBEC, a2bus_xebeccard_device, "a2xebec", "Xebec SASI Card") + +#define SASI_ROM_REGION "sasi_rom" + +ROM_START( sider ) + ROM_REGION(0x800, SASI_ROM_REGION, 0) + ROM_LOAD( "atsv22_a02a9baad2262a8a49ecea843f602124.bin", 0x000000, 0x000800, CRC(97773a0b) SHA1(8d0a5d6ce3b9a236771126033c4aba6c0cc5e704) ) +ROM_END + +ROM_START( xebec ) + ROM_REGION(0x800, SASI_ROM_REGION, 0) + ROM_LOAD( "xebec-103684c-1986.bin", 0x000000, 0x000800, CRC(9e62e15f) SHA1(7f50b5e00cac4960204f50448a6e2d623b1a41e2) ) +ROM_END + +/*************************************************************************** + FUNCTION PROTOTYPES +***************************************************************************/ + +//------------------------------------------------- +// device_add_mconfig - add device configuration +//------------------------------------------------- + +void a2bus_sider_device::device_add_mconfig(machine_config &config) +{ + NSCSI_BUS(config, m_sasibus); + NSCSI_CONNECTOR(config, "sasibus:0", default_scsi_devices, "s1410", false); + NSCSI_CONNECTOR(config, "sasibus:1", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:2", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:3", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:4", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:5", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:6", default_scsi_devices, nullptr, false); + NSCSI_CONNECTOR(config, "sasibus:7", default_scsi_devices, "scsicb", true).option_add_internal("scsicb", NSCSI_CB); +} + +//------------------------------------------------- +// rom_region - device-specific ROM region +//------------------------------------------------- + +const tiny_rom_entry *a2bus_sidercard_device::device_rom_region() const +{ + return ROM_NAME( sider ); +} + +const tiny_rom_entry *a2bus_xebeccard_device::device_rom_region() const +{ + return ROM_NAME( xebec ); +} + +//************************************************************************** +// LIVE DEVICE +//************************************************************************** + +a2bus_sider_device::a2bus_sider_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock) : + device_t(mconfig, type, tag, owner, clock), + device_a2bus_card_interface(mconfig, *this), + m_sasibus(*this, "sasibus"), + m_sasi(*this, "sasibus:7:scsicb"), + m_rom(*this, SASI_ROM_REGION), + m_latch(0xff), + m_control(0) +{ +} + +a2bus_sidercard_device::a2bus_sidercard_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + a2bus_sider_device(mconfig, A2BUS_SIDER, tag, owner, clock) +{ +} + +a2bus_xebeccard_device::a2bus_xebeccard_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + a2bus_sider_device(mconfig, A2BUS_XEBEC, tag, owner, clock) +{ +} + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- + +void a2bus_sider_device::device_start() +{ + save_item(NAME(m_latch)); + save_item(NAME(m_control)); +} + +void a2bus_sider_device::device_reset() +{ + m_latch = 0xff; + m_control = 0; +} + +void a2bus_xebeccard_device::device_start() +{ + a2bus_sider_device::device_start(); + + m_rom[0x42] = 0x01; // correct boot block jump to $801 + m_rom[0x492] = 0x01; // correct ProDOS READ_BLOCK to read one block, not two + m_rom[0x497] = 0xea; // fix various weird stuff done to the READ_BLOCK parameters + m_rom[0x498] = 0xea; + m_rom[0x499] = 0xea; + m_rom[0x49a] = 0xea; + m_rom[0x49b] = 0xea; + m_rom[0x49c] = 0xea; + m_rom[0x4b4] = 0xea; + m_rom[0x4b5] = 0xea; + m_rom[0x4b9] = 0xea; + m_rom[0x4ba] = 0xea; + m_rom[0x4bf] = 0xea; + m_rom[0x4c0] = 0xea; + m_rom[0x4c7] = 0xea; + m_rom[0x4c8] = 0xea; + m_rom[0x4c9] = 0xea; + m_rom[0x4ca] = 0xea; + m_rom[0x4cb] = 0xea; + m_rom[0x4cc] = 0xea; +} + +/*------------------------------------------------- + read_c0nx - called for reads from this card's c0nx space +-------------------------------------------------*/ + +uint8_t a2bus_sider_device::read_c0nx(uint8_t offset) +{ + u8 rv = 0; + + switch (offset) + { + case 0: + // b3: /Busy + // b4: /Message + // b5: I/O + // b6: C/D + // b7: REQ + rv |= m_sasi->req_r() ? 0x80 : 0; + rv |= m_sasi->cd_r() ? 0x40 : 0; + rv |= m_sasi->io_r() ? 0x20 : 0; + rv |= m_sasi->msg_r() ? 0x10 : 0; + rv |= m_sasi->bsy_r() ? 0x08 : 0; + return rv; + + case 1: + rv = m_sasi->read(); + if ((m_sasi->req_r()) && (m_sasi->io_r())) + { + m_sasi->ack_w(1); + m_sasi->ack_w(0); + } + return rv; + + default: + printf("Read c0n%x (%s)\n", offset, machine().describe_context().c_str()); + break; + } + + return 0xff; +} + + +/*------------------------------------------------- + write_c0nx - called for writes to this card's c0nx space +-------------------------------------------------*/ + +void a2bus_sider_device::write_c0nx(uint8_t offset, uint8_t data) +{ + switch (offset) + { + case 0: + m_latch = data; + if (!(m_control & 0x10)) + { + m_sasi->write(m_latch); + + if (m_sasi->req_r()) + { + m_sasi->ack_w(1); + m_sasi->write(0); // stop driving the data lines + m_sasi->ack_w(0); + } + } + break; + + case 1: +// b4: drive contents of output latch onto the SASI bus +// b5: reset bus +// b6: /BSY +// b7: /SEL (error in note on A2DP's schematic; BSY and SEL are the same polarity from the 6502's POV) + m_control = data; + m_sasi->sel_w((data & 0x80) ? 1 : 0); + m_sasi->bsy_w((data & 0x40) ? 1 : 0); + if (data & 0x20) + { + m_sasibus->reset(); + } + else if (!(data & 0x10)) + { + m_sasi->write(m_latch); + } + break; + + default: + printf("Write %02x to c0n%x (%s)\n", data, offset, machine().describe_context().c_str()); + break; + } +} + +/*------------------------------------------------- + read_cnxx - called for reads from this card's cnxx space +-------------------------------------------------*/ + +uint8_t a2bus_sider_device::read_cnxx(uint8_t offset) +{ + // slot images at $700 + return m_rom[offset + 0x700]; +} + +void a2bus_sider_device::write_cnxx(uint8_t offset, uint8_t data) +{ +} + +/*------------------------------------------------- + read_c800 - called for reads from this card's c800 space +-------------------------------------------------*/ + +uint8_t a2bus_sider_device::read_c800(uint16_t offset) +{ + return m_rom[offset]; +} + +/*------------------------------------------------- + write_c800 - called for writes to this card's c800 space +-------------------------------------------------*/ +void a2bus_sider_device::write_c800(uint16_t offset, uint8_t data) +{ +} diff --git a/src/devices/bus/a2bus/sider.h b/src/devices/bus/a2bus/sider.h new file mode 100644 index 00000000000..36452c6d3e1 --- /dev/null +++ b/src/devices/bus/a2bus/sider.h @@ -0,0 +1,77 @@ +// license:BSD-3-Clause +// copyright-holders:R. Belmont +/********************************************************************* + + sider.h + + Implementation of the First Class Peripherals / Advanced Tech Services / Xebec Sider SASI Card + +*********************************************************************/ + +#ifndef MAME_BUS_A2BUS_SIDER_H +#define MAME_BUS_A2BUS_SIDER_H + +#pragma once + +#include "a2bus.h" +#include "bus/nscsi/devices.h" +#include "machine/nscsi_bus.h" +#include "machine/nscsi_cb.h" + +//************************************************************************** +// TYPE DEFINITIONS +//************************************************************************** + +class a2bus_sider_device: + public device_t, + public device_a2bus_card_interface +{ +protected: + a2bus_sider_device(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock); + + virtual void device_start() override; + virtual void device_reset() override; + virtual void device_add_mconfig(machine_config &config) override; + + // overrides of standard a2bus slot functions + virtual uint8_t read_c0nx(uint8_t offset) override; + virtual void write_c0nx(uint8_t offset, uint8_t data) override; + virtual uint8_t read_cnxx(uint8_t offset) override; + virtual void write_cnxx(uint8_t offset, uint8_t data) override; + virtual uint8_t read_c800(uint16_t offset) override; + virtual void write_c800(uint16_t offset, uint8_t data) override; + + required_device m_sasibus; + required_device m_sasi; + required_region_ptr m_rom; + +private: + u8 m_latch; + u8 m_control; +}; + +class a2bus_sidercard_device: public a2bus_sider_device +{ +public: + a2bus_sidercard_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + virtual const tiny_rom_entry *device_rom_region() const override; +}; + +class a2bus_xebeccard_device: public a2bus_sider_device +{ +public: + a2bus_xebeccard_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + virtual const tiny_rom_entry *device_rom_region() const override; + + // the Xebec version of the firmware doesn't work; it appears to have some bytes corrupted. + static constexpr feature_type unemulated_features() { return feature::DISK; } + +protected: + virtual void device_start() override; +}; + +// device type definition +DECLARE_DEVICE_TYPE(A2BUS_SIDER, a2bus_sidercard_device) +DECLARE_DEVICE_TYPE(A2BUS_XEBEC, a2bus_xebeccard_device) + +#endif // MAME_BUS_A2BUS_SIDER_H diff --git a/src/mame/drivers/apple2e.cpp b/src/mame/drivers/apple2e.cpp index 891e8dbe22c..68b3afa9dd6 100644 --- a/src/mame/drivers/apple2e.cpp +++ b/src/mame/drivers/apple2e.cpp @@ -176,6 +176,7 @@ MIG RAM page 2 $CE02 is the speaker/slot bitfield and $CE03 is the paddle/accele #include "bus/a2bus/byte8251.h" #include "bus/a2bus/a2iwm.h" #include "bus/a2bus/uthernet.h" +#include "bus/a2bus/sider.h" #include "bus/a2gameio/gameio.h" #include "bus/rs232/rs232.h" @@ -4502,6 +4503,8 @@ static void apple2_cards(device_slot_interface &device) device.option_add("byte8251", A2BUS_BYTE8251); /* BYTE Magazine 8251 serial card */ device.option_add("cmsscsi", A2BUS_CMSSCSI); /* CMS Apple II SCSI Card */ device.option_add("uthernet", A2BUS_UTHERNET); /* A2RetroSystems Uthernet card */ + device.option_add("sider", A2BUS_SIDER); /* First Class Peripherals / Advanced Tech Systems Sider SASI card */ + device.option_add("xebec", A2BUS_XEBEC); /* Xebec SASI card */ } static void apple2eaux_cards(device_slot_interface &device) diff --git a/src/mame/drivers/apple2gs.cpp b/src/mame/drivers/apple2gs.cpp index d2dea6f7b90..ba7dbbb67b5 100644 --- a/src/mame/drivers/apple2gs.cpp +++ b/src/mame/drivers/apple2gs.cpp @@ -109,6 +109,7 @@ //#include "bus/a2bus/hostram.h" //#include "bus/a2bus/ramfast.h" #include "bus/a2bus/uthernet.h" +#include "bus/a2bus/sider.h" #include "bus/a2gameio/gameio.h" @@ -4580,7 +4581,9 @@ static void apple2_cards(device_slot_interface &device) // device.option_add("hostram", A2BUS_HOSTRAM); /* Slot 7 RAM for GS Plus host protocol */ // device.option_add("ramfast", A2BUS_RAMFAST); /* C.V. Technologies RAMFast SCSI card */ device.option_add("cmsscsi", A2BUS_CMSSCSI); /* CMS Apple II SCSI Card */ - device.option_add("uthernet", A2BUS_UTHERNET); /* CMS Apple II SCSI Card */ + device.option_add("uthernet", A2BUS_UTHERNET); /* A2RetroSystems Uthernet card */ + device.option_add("sider", A2BUS_SIDER); /* Advanced Tech Systems / First Class Peripherals Sider SASI card */ + device.option_add("xebec", A2BUS_XEBEC); /* Xebec SASI card */ } void apple2gs_state::apple2gs(machine_config &config) -- cgit v1.2.3