diff --git a/scripts/src/bus.lua b/scripts/src/bus.lua index b86f1073c08..8667c54788e 100644 --- a/scripts/src/bus.lua +++ b/scripts/src/bus.lua @@ -3733,6 +3733,17 @@ if (BUSES["EPSON_SIO"]~=null) then } end +--------------------------------------------------- +-- +--@src/devices/bus/epson_qx/option.h,BUSES["EPSON_QX"] = true +--------------------------------------------------- +if (BUSES["EPSON_QX"]~=null) then + files { + MAME_DIR .. "src/devices/bus/epson_qx/option.cpp", + MAME_DIR .. "src/devices/bus/epson_qx/option.h", + } +end + --------------------------------------------------- -- --@src/devices/bus/pce/pce_slot.h,BUSES["PCE"] = true diff --git a/scripts/target/mame/mess.lua b/scripts/target/mame/mess.lua index 70815cf1b96..3e4fa07b2c9 100644 --- a/scripts/target/mame/mess.lua +++ b/scripts/target/mame/mess.lua @@ -895,6 +895,7 @@ BUSES["ELECTRON_CART"] = true BUSES["ELECTRON"] = true BUSES["EP64"] = true BUSES["EPSON_SIO"] = true +BUSES["EPSON_QX"] = true BUSES["FMT_SCSI"] = true BUSES["GAMATE"] = true BUSES["GAMEBOY"] = true diff --git a/src/devices/bus/epson_qx/option.cpp b/src/devices/bus/epson_qx/option.cpp new file mode 100644 index 00000000000..0a6553d2f54 --- /dev/null +++ b/src/devices/bus/epson_qx/option.cpp @@ -0,0 +1,210 @@ +// license:BSD-3-Clause +// copyright-holders:Brian Johnson +/******************************************************************* + * + * Epson QX-10 Expansion emulation + * + *******************************************************************/ +#include "emu.h" +#include "option.h" + +DEFINE_DEVICE_TYPE(EPSON_QX_OPTION_BUS_SLOT, bus::epson_qx::option_slot_device, "epson_qx_option_slot", "QX-10 Option slot") +DEFINE_DEVICE_TYPE(EPSON_QX_OPTION_BUS, bus::epson_qx::option_bus_device, "epson_qx_option_bus", "QX-10 Option Bus") + +namespace bus::epson_qx { +//************************************************************************** +// EPSON SLOT DEVICE +//************************************************************************** + +//------------------------------------------------- +// option_bus_slot_device - constructor +//------------------------------------------------- +option_slot_device::option_slot_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + device_t(mconfig, EPSON_QX_OPTION_BUS_SLOT, tag, owner, clock), + device_single_card_slot_interface(mconfig, *this), + m_bus(*this, finder_base::DUMMY_TAG), + m_dmas_w_cb(*this), + m_dmas_r_cb(*this), + m_dmaf_w_cb(*this), + m_dmaf_r_cb(*this), + m_eopf_cb(*this), + m_eops_cb(*this), + m_slot(-1) +{ +} + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- +void option_slot_device::device_start() +{ + m_dmas_w_cb.resolve_safe(); + m_dmas_r_cb.resolve_safe(0xff); + m_dmaf_w_cb.resolve(); + m_dmaf_r_cb.resolve(); + + m_eopf_cb.resolve_safe(); + m_eops_cb.resolve_safe(); + + device_option_expansion_interface *const intf(get_card_device()); + if (intf) { + intf->set_option_bus(*m_bus, m_slot); + } + + m_bus->add_slot(*this); +} + +WRITE_LINE_MEMBER(option_slot_device::eopf) { m_eopf_cb(state); } +WRITE_LINE_MEMBER(option_slot_device::eops) { m_eops_cb(state); } + +WRITE_LINE_MEMBER(option_slot_device::inth1_w) { (*m_bus).set_inth1_line(state, m_slot); } +WRITE_LINE_MEMBER(option_slot_device::inth2_w) { (*m_bus).set_inth2_line(state, m_slot); } +WRITE_LINE_MEMBER(option_slot_device::intl_w) { (*m_bus).set_intl_line(state, m_slot); } + +WRITE_LINE_MEMBER(option_slot_device::drqf_w) { (*m_bus).set_drqf_line(state, m_slot); } +WRITE_LINE_MEMBER(option_slot_device::drqs_w) { (*m_bus).set_drqs_line(state, m_slot); } + +WRITE_LINE_MEMBER(option_slot_device::rdyf_w) { (*m_bus).set_rdyf_line(state, m_slot); } +WRITE_LINE_MEMBER(option_slot_device::rdys_w) { (*m_bus).set_rdys_line(state, m_slot); } + +//************************************************************************** +// EPSON OPTION BUS DEVICE +//************************************************************************** + +//------------------------------------------------- +// option_bus_device - constructor +//------------------------------------------------- +option_bus_device::option_bus_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + device_t(mconfig, EPSON_QX_OPTION_BUS, tag, owner, clock), + m_iospace(*this, finder_base::DUMMY_TAG, -1), + m_inth1_cb(*this), + m_inth2_cb(*this), + m_intl_cb(*this), + m_drqf_cb(*this), + m_drqs_cb(*this), + m_rdyf_cb(*this), + m_rdys_cb(*this), + m_inth1(0), + m_inth2(0), + m_drqf(0), + m_rdyf(0), + m_rdys(0) +{ +} + +void option_bus_device::add_slot(option_slot_device &slot) +{ + m_slot_list.push_back(&slot); +} + +//------------------------------------------------- +// device_start - device-specific startup +//------------------------------------------------- +void option_bus_device::device_start() +{ + m_inth1_cb.resolve_safe(); + m_inth2_cb.resolve_safe(); + m_intl_cb.resolve_all_safe(); + m_drqf_cb.resolve_safe(); + m_drqs_cb.resolve_all_safe(); + m_rdyf_cb.resolve_safe(); + m_rdys_cb.resolve_safe(); +} + +//------------------------------------------------- +// device_reset - device-specific startup +//------------------------------------------------- +void option_bus_device::device_reset() +{ + m_inth1 = 0; + m_inth2 = 0; + m_drqf = 0; + m_rdyf = 0; + m_rdys = 0; +} + +void option_bus_device::dackf_w(uint8_t data) +{ + for (int i = 0; i < m_slot_list.size(); ++i) { + if (!m_slot_list[i]->m_dmaf_w_cb.isnull()) { + m_slot_list[i]->m_dmaf_w_cb(data); + } + } +} + +uint8_t option_bus_device::dackf_r() +{ + uint8_t value = 0; + bool found = false; + for (int i = 0; i < m_slot_list.size(); ++i) { + if (!m_slot_list[i]->m_dmaf_r_cb.isnull()) { + found = true; + value |= m_slot_list[i]->m_dmaf_r_cb(); + } + } + return (found ? value : 0xff); +} + +void option_bus_device::set_inth1_line(uint8_t state, uint8_t slot) +{ + m_inth1 = state ? (m_inth1 | (1 << (slot & 0x07))) : (m_inth1 & ~(1 << (slot & 0x07))); + m_inth1_cb(m_inth1 != 0); +} + +void option_bus_device::set_inth2_line(uint8_t state, uint8_t slot) +{ + m_inth2 = state ? (m_inth2 | (1 << (slot & 0x07))) : (m_inth2 & ~(1 << (slot & 0x07))); + m_inth2_cb(m_inth2 != 0); +} + +void option_bus_device::set_drqf_line(uint8_t state, uint8_t slot) +{ + m_drqf = !state ? (m_drqf | (1 << (slot & 0x07))) : (m_drqf & ~(1 << (slot & 0x07))); + m_drqf_cb(m_drqf == 0); +} + +void option_bus_device::set_rdyf_line(uint8_t state, uint8_t slot) +{ + m_rdyf = !state ? (m_rdyf | (1 << (slot & 0x07))) : (m_rdyf & ~(1 << (slot & 0x07))); + m_rdyf_cb(m_rdyf == 0); +} + +void option_bus_device::set_rdys_line(uint8_t state, uint8_t slot) +{ + m_rdys = !state ? (m_rdys | (1 << (slot & 0x07))) : (m_rdys & ~(1 << (slot & 0x07))); + m_rdys_cb(m_rdys == 0); +} + + +//************************************************************************** +// EPSON OPTION CARD INTERFACE +//************************************************************************** + +//------------------------------------------------- +// option_device_expansion_interface - constructor +//------------------------------------------------- +device_option_expansion_interface::device_option_expansion_interface(const machine_config &mconfig, device_t &device) : + device_interface(device, "qx_option_bus"), + m_bus(nullptr), + m_slot(-1) +{ +} + +//--------------------------------------------------- +// interface_pre_start - device-specific pre startup +//--------------------------------------------------- +void device_option_expansion_interface::interface_pre_start() +{ + if (!m_bus || m_slot == -1) + throw device_missing_dependencies(); +} + +//------------------------------------------------- +// SLOT_INTERFACE( option_bus_devices ) +//------------------------------------------------- + +void option_bus_devices(device_slot_interface &device) +{ +} + +} // namespace bus::epson_qx diff --git a/src/devices/bus/epson_qx/option.h b/src/devices/bus/epson_qx/option.h new file mode 100644 index 00000000000..0204e54f0f7 --- /dev/null +++ b/src/devices/bus/epson_qx/option.h @@ -0,0 +1,280 @@ +// license:BSD-3-Clause +// copyright-holders:Brian Johnson +/* + QX-10 Option bus + + 1 GND 2 GND + 3 DTB0 4 DTB1 + 5 DTB2 6 DTB3 + 7 DTB4 8 DTB5 + 9 DTB6 10 DTB7 + 11 -12V 12 -12V + 13 ADR0 14 ADR1 + 15 ADR2 16 ADR3 + 17 ADR4 18 ADR5 + 19 ADR6 20 ADR7 + 21 ADR8 22 ADR9 + 23 ADR10 24 ADR11 + 25 ADR12 26 ADR13 + 27 ADR14 28 ADR15 + 29 GND 30 GND + 31 CLK 32 GND + 33 /BSAK 34 /MEMX + 35 /IRD 36 /IWR + 37 /MRD 38 /MWR + 39 /RSIN 40 INTH1 + 41 INTH2 42 INTL + 43 +5V 44 /RSET + 45 +5V 46 +5V + 47 /DRQF 48 /DRQS + 49 /RDYF 50 /RDYS + 51 /WAIT 52 /IWS + 53 /DAKF 54 /DAKS + 55 /EOPF 56 /EOPS + 57 +12V 58 +12V + 59 GND 60 GND + + The INTH1 and INTH2 singals are the two hihg priority interrupts and are + global to the entire option bus. The INTL signal is the low priority interrupt + and is local to each of the 5 option slots. + + 5 4 3 2 1 + |---| |---| |---| |---| |---| + | | | | | | | | | | + | | | | | | | | | | + | | | | | | | | | | + | | | | | | | | | | + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------IRQH1 (Master IR2) + | | | | | | | | | | + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------IRQH2 (Master IR3) + | | | | | | | | | | + | | | | | | | | | | + | | | | | | | | | *-|--------IRQL (Slave IR1) + | | | | | | | | | | + | | | | | | | *-|--|---|--------IRQL (Slave IR3) + | | | | | | | | | | + | | | | | *-|--|---|--|---|--------IRQL (Slave IR4) + | | | | | | | | | | + | | | *-|--|---|--|---|--|---|--------IRQL (Slave IR6) + | | | | | | | | | | + | *-|--|---|--|---|--|---|--|---|--------IRQL (Slave IR7) + | | | | | | | | | | + | | | | | | | | | | + | | | | | | | | | | + | | | | | | | | | | + |---| |---| |---| |---| |---| + + The DREQ/DACK(F) signals are the high priorty DMA signals and are shared between all option slots. + The DREQ/DACK(S) signals are the lower priority DMA signals and are local to each slot, with the + exception of slot 5 which does not provide low priority DMA signals. The RDY/EOP(S) signals are + also connected to all 5 options slots since the DREQ(S) signals are all connected to the same + DMA controller. + + 5 4 3 2 1 + |---| |---| |---| |---| |---| + | | | | | | | | | | + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------DREQF (Master CH3) + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------DACKF (Master Ch3) + | | | | | | | | | | + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------RDYF (Master RDY) + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------EOPF (Master EOP) + | | | | | | | | | | + | | | | | | | | | *-|--------DREQS (Slave CH0) + | | | | | | | | | *-|--------DACKS (Slave CH0) + | | | | | | | | | | + | | | | | | | *-|--|---|--------DREQS (Slave CH1) + | | | | | | | *-|--|---|--------DACKS (Slave CH1) + | | | | | | | | | | + | | | | | *-|--|---|--|---|--------DREQS (Slave CH2) + | | | | | *-|--|---|--|---|--------DACKS (Slave CH2) + | | | | | | | | | | + | | | *-|--|---|--|---|--|---|--------DREQS (Slave CH3) + | | | *-|--|---|--|---|--|---|--------DACKS (Slave CH3) + | | | | | | | | | | + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------RDYS (Slave RDY) + | *-|--|-*-|--|-*-|--|-*-|--|-*-|--------EOPS (Slave EOP) + | | | | | | | | | | + |---| |---| |---| |---| |---| + +*/ +#ifndef MAME_BUS_EPSON_QX_BUS_H +#define MAME_BUS_EPSON_QX_BUS_H + +#pragma once + +#include + +namespace bus::epson_qx { + +//************************************************************************** +// FORWARD DECLARATIONS +//************************************************************************** + +class option_bus_device; +class device_option_expansion_interface; + + +//************************************************************************** +// TYPE DEFINITIONS +//************************************************************************** + +/* Epson Slot Device */ + +class option_slot_device : public device_t, public device_single_card_slot_interface +{ +public: + friend class option_bus_device; + // construction/destruction + template + option_slot_device(const machine_config &mconfig, const char *tag, device_t *owner, T &&bus_tag, int slot, U &&opts, const char *dflt) + : option_slot_device(mconfig, tag, owner, bus_tag->clock()) + { + option_reset(); + opts(*this); + set_default_option(dflt); + set_fixed(false); + m_bus.set_tag(std::forward(bus_tag)); + m_slot = slot; + } + option_slot_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + + DECLARE_WRITE_LINE_MEMBER(inth1_w); + DECLARE_WRITE_LINE_MEMBER(inth2_w); + DECLARE_WRITE_LINE_MEMBER(intl_w); + + DECLARE_WRITE_LINE_MEMBER(drqf_w); + DECLARE_WRITE_LINE_MEMBER(drqs_w); + + DECLARE_WRITE_LINE_MEMBER(rdyf_w); + DECLARE_WRITE_LINE_MEMBER(rdys_w); + + DECLARE_WRITE_LINE_MEMBER(eopf); + DECLARE_WRITE_LINE_MEMBER(eops); + + auto dmas_w_callback() { m_dmas_w_cb.bind(); } + auto dmas_r_callback() { m_dmas_r_cb.bind(); } + auto dmaf_w_callback() { m_dmaf_w_cb.bind(); } + auto dmaf_r_callback() { m_dmaf_r_cb.bind(); } + + auto in_eopf_callback() { return m_eopf_cb.bind(); } + auto in_eops_callback() { return m_eops_cb.bind(); } +protected: + // device-level overrides + virtual void device_start() override; + + // configuration + required_device m_bus; + devcb_write8 m_dmas_w_cb; + devcb_read8 m_dmas_r_cb; + devcb_write8 m_dmaf_w_cb; + devcb_read8 m_dmaf_r_cb; + + devcb_write_line m_eopf_cb; + devcb_write_line m_eops_cb;; + + int m_slot; +}; + + +/* Epson Bus Device */ + +class option_bus_device : public device_t +{ +public: + // construction/destruction + option_bus_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + + template void set_iospace(T &&tag, int spacenum) { m_iospace.set_tag(std::forward(tag), spacenum); } + void set_memview(memory_view::memory_view_entry &view) { m_view = &view; } + + auto out_inth1_callback() { return m_inth1_cb.bind(); } + auto out_inth2_callback() { return m_inth2_cb.bind(); } + template auto out_intl_callback() { return m_intl_cb[Slot].bind(); } + + auto out_drqf_callback() { return m_drqf_cb.bind(); } + template auto out_drqs_callback() { return m_drqs_cb[Slot].bind(); } + + auto out_rdyf_callback() { return m_rdyf_cb.bind(); } + auto out_rdys_callback() { return m_rdys_cb.bind(); } + + memory_view::memory_view_entry& memview() const { return *m_view; } + address_space &iospace() const { return *m_iospace; } + + void dackf_w(uint8_t data); + uint8_t dackf_r(); + template void dacks_w(uint8_t data) { (*this)[Slot]->m_dmas_w_cb(data); } + template uint8_t dacks_r() { return (*this)[Slot]->m_dmas_r_cb(); } + + template void slots_w(int state) { + for (option_slot_device *slot : m_slot_list) { + (slot->*slot_callback)(state); + } + } + + void set_inth1_line(uint8_t state, uint8_t slot); + void set_inth2_line(uint8_t state, uint8_t slot); + void set_intl_line(uint8_t state, uint8_t slot) { m_intl_cb[slot](state); } + void set_drqf_line(uint8_t state, uint8_t slot); + void set_drqs_line(uint8_t state, uint8_t slot) { m_drqs_cb[slot](state); } + void set_rdyf_line(uint8_t state, uint8_t slot); + void set_rdys_line(uint8_t state, uint8_t slot); + + void add_slot(option_slot_device &slot); + option_slot_device* operator[](int index) const {assert(index < m_slot_list.size()); return m_slot_list[index]; } + +protected: + // device-level overrides + virtual void device_start() override; + virtual void device_reset() override; + + required_address_space m_iospace; + memory_view::memory_view_entry *m_view; + + devcb_write_line m_inth1_cb; + devcb_write_line m_inth2_cb; + devcb_write_line::array<5> m_intl_cb; + + devcb_write_line m_drqf_cb; + devcb_write_line::array<4> m_drqs_cb; + + devcb_write_line m_rdyf_cb; + devcb_write_line m_rdys_cb; + + std::vector m_slot_list; + + uint8_t m_inth1; + uint8_t m_inth2; + + uint8_t m_drqf; + + uint8_t m_rdyf; + uint8_t m_rdys; +}; + + +/* Epson Option Card interface */ +class device_option_expansion_interface : public device_interface +{ +public: + void set_option_bus(option_bus_device &bus, int slot) { assert(!device().started()); m_bus = &bus; m_slot = slot; } + +protected: + device_option_expansion_interface(const machine_config &mconfig, device_t &device); + + virtual void interface_pre_start() override; + option_slot_device* get_slot() { return (*m_bus)[m_slot]; } + + option_bus_device *m_bus; + int m_slot; +}; + +void option_bus_devices(device_slot_interface &device); + +} // namespace bus::epson_qx + + +// device type definition +DECLARE_DEVICE_TYPE_NS(EPSON_QX_OPTION_BUS_SLOT, bus::epson_qx, option_slot_device) +DECLARE_DEVICE_TYPE_NS(EPSON_QX_OPTION_BUS, bus::epson_qx, option_bus_device) + +#endif diff --git a/src/mame/drivers/qx10.cpp b/src/mame/drivers/qx10.cpp index 7d13a9c06d1..e68f362d892 100644 --- a/src/mame/drivers/qx10.cpp +++ b/src/mame/drivers/qx10.cpp @@ -1,5 +1,5 @@ // license:BSD-3-Clause -// copyright-holders:Mariusz Wojcieszek, Angelo Salese +// copyright-holders:Mariusz Wojcieszek, Angelo Salese, Brian Johnson /*************************************************************************** QX-10 @@ -35,6 +35,7 @@ #include "emu.h" #include "bus/centronics/ctronics.h" +#include "bus/epson_qx/option.h" #include "bus/rs232/rs232.h" #include "cpu/z80/z80.h" #include "imagedev/floppy.h" @@ -85,13 +86,15 @@ public: m_rtc(*this, "rtc"), m_kbd(*this, "kbd"), m_centronics(*this, "centronics"), + m_bus(*this, "bus"), m_speaker(*this, "speaker"), m_vram_bank(0), m_char_rom(*this, "chargen"), m_maincpu(*this, "maincpu"), m_screen(*this, "screen"), m_ram(*this, RAM_TAG), - m_palette(*this, "palette") + m_palette(*this, "palette"), + m_ram_view(*this, "ramview") { } @@ -168,6 +171,7 @@ private: required_device m_rtc; required_device m_kbd; required_device m_centronics; + required_device m_bus; required_device m_speaker; uint8_t m_vram_bank; //required_shared_ptr m_video_ram; @@ -197,6 +201,8 @@ private: /* memory */ + memory_view m_ram_view; + int m_external_bank; int m_membank; int m_memprom; int m_memcmos; @@ -323,7 +329,7 @@ void qx10_state::update_speaker() */ void qx10_state::update_memory_mapping() { - int drambank = 0; + int drambank = -1; if (m_membank & 1) { @@ -342,28 +348,45 @@ void qx10_state::update_memory_mapping() drambank = 3; } - if (!m_memprom) + if (drambank >= 0 || !m_memprom || m_memcmos) { - membank("bank1")->set_base(memregion("maincpu")->base()); + m_ram_view.select(0); + if (!m_memprom) + { + membank("bank1")->set_base(memregion("maincpu")->base()); + } + else + { + membank("bank1")->set_base(m_ram->pointer() + drambank*64*1024); + } + if (m_memcmos) + { + membank("bank2")->set_base(m_cmosram); + } + else + { + membank("bank2")->set_base(m_ram->pointer() + drambank*64*1024 + 32*1024); + } } else { - membank("bank1")->set_base(m_ram->pointer() + drambank*64*1024); - } - if (m_memcmos) - { - membank("bank2")->set_base(m_cmosram); - } - else - { - membank("bank2")->set_base(m_ram->pointer() + drambank*64*1024 + 32*1024); + if (m_external_bank) + { + m_ram_view.select(1);; + } + else + { + m_ram_view.disable(); + } } + } void qx10_state::qx10_18_w(uint8_t data) { m_membank = (data >> 4) & 0x0f; m_spkr_enable = (data >> 2) & 0x01; + m_external_bank = (data >> 3) & 0x01; m_pit_1->write_gate0(data & 1); update_speaker(); update_memory_mapping(); @@ -534,6 +557,7 @@ WRITE_LINE_MEMBER( qx10_state::tc_w ) { /* floppy terminal count */ m_fdc->tc_w(!state); + m_bus->slots_w<&bus::epson_qx::option_slot_device::eopf>(state); } /* @@ -661,8 +685,10 @@ void qx10_state::vram_bank_w(uint8_t data) void qx10_state::qx10_mem(address_map &map) { map.unmap_value_high(); - map(0x0000, 0x7fff).bankrw("bank1"); - map(0x8000, 0xdfff).bankrw("bank2"); + map(0x0000, 0xdfff).view(m_ram_view); + m_ram_view[0](0x0000, 0x7fff).bankrw("bank1"); + m_ram_view[0](0x8000, 0xdfff).bankrw("bank2"); + m_ram_view[1](0x0000, 0xdfff).unmaprw(); map(0xe000, 0xffff).ram(); } @@ -688,7 +714,6 @@ void qx10_state::qx10_io(address_map &map) map(0x3c, 0x3d).rw(FUNC(qx10_state::mc146818_r), FUNC(qx10_state::mc146818_w)); map(0x40, 0x4f).rw(m_dma_1, FUNC(am9517a_device::read), FUNC(am9517a_device::write)); map(0x50, 0x5f).rw(m_dma_2, FUNC(am9517a_device::read), FUNC(am9517a_device::write)); -// map(0xfc, 0xfd) Multi-Font comms } /* Input ports */ @@ -743,6 +768,7 @@ INPUT_PORTS_END void qx10_state::machine_start() { + m_bus->set_memview(m_ram_view[1]); } void qx10_state::machine_reset() @@ -755,6 +781,7 @@ void qx10_state::machine_reset() m_zoom = 0; + m_external_bank = 0; m_memprom = 0; m_memcmos = 0; m_membank = 0; @@ -965,6 +992,39 @@ void qx10_state::qx10(machine_config &config) /* internal ram */ RAM(config, RAM_TAG).set_default_size("256K"); + EPSON_QX_OPTION_BUS(config, m_bus, MAIN_CLK / 4); + m_dma_1->out_iow_callback<2>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dackf_w)); + m_dma_1->in_ior_callback<2>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dackf_r)); + m_dma_2->out_iow_callback<0>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_w<0>)); + m_dma_2->in_ior_callback<0>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_r<0>)); + m_dma_2->out_iow_callback<1>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_w<1>)); + m_dma_2->in_ior_callback<1>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_r<1>)); + m_dma_2->out_iow_callback<2>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_w<2>)); + m_dma_2->in_ior_callback<2>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_r<2>)); + m_dma_2->out_iow_callback<3>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_w<3>)); + m_dma_2->in_ior_callback<3>().set(m_bus, FUNC(bus::epson_qx::option_bus_device::dacks_r<3>)); + m_dma_2->out_eop_callback().set(m_bus, FUNC(bus::epson_qx::option_bus_device::slots_w<&bus::epson_qx::option_slot_device::eops>)); + m_bus->out_drqf_callback().set(m_dma_1, FUNC(am9517a_device::dreq2_w)); + m_bus->out_rdyf_callback().set(m_dma_1, FUNC(am9517a_device::ready_w)); + m_bus->out_drqs_callback<0>().set(m_dma_2, FUNC(am9517a_device::dreq0_w)); + m_bus->out_drqs_callback<1>().set(m_dma_2, FUNC(am9517a_device::dreq1_w)); + m_bus->out_drqs_callback<2>().set(m_dma_2, FUNC(am9517a_device::dreq2_w)); + m_bus->out_drqs_callback<3>().set(m_dma_2, FUNC(am9517a_device::dreq3_w)); + m_bus->out_rdys_callback().set(m_dma_2, FUNC(am9517a_device::ready_w)); + m_bus->out_inth1_callback().set(m_pic_m, FUNC(pic8259_device::ir2_w)); + m_bus->out_inth2_callback().set(m_pic_m, FUNC(pic8259_device::ir3_w)); + m_bus->out_intl_callback<0>().set(m_pic_s, FUNC(pic8259_device::ir1_w)); + m_bus->out_intl_callback<1>().set(m_pic_s, FUNC(pic8259_device::ir3_w)); + m_bus->out_intl_callback<2>().set(m_pic_s, FUNC(pic8259_device::ir4_w)); + m_bus->out_intl_callback<3>().set(m_pic_s, FUNC(pic8259_device::ir6_w)); + m_bus->out_intl_callback<4>().set(m_pic_s, FUNC(pic8259_device::ir7_w)); + m_bus->set_iospace(m_maincpu, AS_IO); + EPSON_QX_OPTION_BUS_SLOT(config, "option1", m_bus, 0, bus::epson_qx::option_bus_devices, nullptr); + EPSON_QX_OPTION_BUS_SLOT(config, "option2", m_bus, 1, bus::epson_qx::option_bus_devices, nullptr); + EPSON_QX_OPTION_BUS_SLOT(config, "option3", m_bus, 2, bus::epson_qx::option_bus_devices, nullptr); + EPSON_QX_OPTION_BUS_SLOT(config, "option4", m_bus, 3, bus::epson_qx::option_bus_devices, nullptr); + EPSON_QX_OPTION_BUS_SLOT(config, "option5", m_bus, 4, bus::epson_qx::option_bus_devices, nullptr); + // software lists SOFTWARE_LIST(config, "flop_list").set_original("qx10_flop"); @@ -979,12 +1039,6 @@ ROM_START( qx10 ) ROM_SYSTEM_BIOS(1, "v003", "v0.03") ROMX_LOAD( "ipl003.bin", 0x0000, 0x0800, CRC(3cbc4008) SHA1(cc8c7d1aa0cca8f9753d40698b2dc6802fd5f890), ROM_BIOS(1)) - /* This is probably the i8039 program ROM for the Q10MF Multifont card, and the actual font ROMs are missing (6 * HM43128) */ - /* The first part of this rom looks like code for an embedded controller? - From 0300 on, is a keyboard lookup table */ - ROM_REGION( 0x0800, "i8039", 0 ) - ROM_LOAD( "m12020a.3e", 0x0000, 0x0800, CRC(fa27f333) SHA1(73d27084ca7b002d5f370220d8da6623a6e82132)) - ROM_REGION( 0x1000, "chargen", 0 ) // ROM_LOAD( "qge.2e", 0x0000, 0x0800, BAD_DUMP CRC(ed93cb81) SHA1(579e68bde3f4184ded7d89b72c6936824f48d10b)) //this one contains special characters only // ROM_LOAD( "qge.2e", 0x0000, 0x1000, BAD_DUMP CRC(eb31a2d5) SHA1(6dc581bf2854a07ae93b23b6dfc9c7abd3c0569e))