From 7892bf71f943a4deda5883083208acae3ac7b977 Mon Sep 17 00:00:00 2001 From: Vas Crabb Date: Sat, 15 Jul 2017 00:03:34 +1000 Subject: intellec4: implement imm4-22 program/data storage module --- scripts/src/bus.lua | 2 + src/devices/bus/intellec4/insdatastor.cpp | 191 ++++++++++++++++++++++++++++ src/devices/bus/intellec4/insdatastor.h | 199 ++++++++++++++++++++++++++++++ src/devices/bus/intellec4/intellec4.cpp | 158 +++++++++++++++++++----- src/devices/bus/intellec4/intellec4.h | 35 ++++-- src/devices/bus/intellec4/tapereader.h | 4 +- src/devices/bus/sunkbd/hlekbd.cpp | 2 +- 7 files changed, 545 insertions(+), 46 deletions(-) create mode 100644 src/devices/bus/intellec4/insdatastor.cpp create mode 100644 src/devices/bus/intellec4/insdatastor.h diff --git a/scripts/src/bus.lua b/scripts/src/bus.lua index 5d384a7ddf7..9a3f271d68e 100644 --- a/scripts/src/bus.lua +++ b/scripts/src/bus.lua @@ -867,6 +867,8 @@ end if (BUSES["INTELLEC4"]~=null) then files { + MAME_DIR .. "src/devices/bus/intellec4/insdatastor.cpp", + MAME_DIR .. "src/devices/bus/intellec4/insdatastor.h", MAME_DIR .. "src/devices/bus/intellec4/intellec4.cpp", MAME_DIR .. "src/devices/bus/intellec4/intellec4.h", MAME_DIR .. "src/devices/bus/intellec4/prommemory.cpp", diff --git a/src/devices/bus/intellec4/insdatastor.cpp b/src/devices/bus/intellec4/insdatastor.cpp new file mode 100644 index 00000000000..a4114425844 --- /dev/null +++ b/src/devices/bus/intellec4/insdatastor.cpp @@ -0,0 +1,191 @@ +// license:BSD-3-Clause +// copyright-holders:Vas Crabb + +#include "emu.h" +#include "insdatastor.h" + + +DEFINE_DEVICE_TYPE_NS(INTELLEC4_INST_DATA_STORAGE, bus::intellec4, imm4_22_device, "intlc4_imm4_22", "Intel imm4-22 Instruction/Data Storage Module") + + +namespace bus { namespace intellec4 { + +namespace { + +INPUT_PORTS_START(imm4_22) + PORT_START("JUMPERS") + PORT_CONFNAME( 0x03, 0x01, "4002 RAM page" ) + PORT_CONFSETTING( 0x01, "1" ) + PORT_CONFSETTING( 0x02, "2" ) + PORT_CONFSETTING( 0x03, "3" ) + PORT_CONFNAME( 0x0c, 0x04, "PROM/GPIO page" ) + PORT_CONFSETTING( 0x04, "0x400-0x7FF" ) + PORT_CONFSETTING( 0x08, "0x800-0xBFF" ) + PORT_CONFSETTING( 0x0c, "0xC00-0xFFF" ) + PORT_CONFNAME( 0x10, 0x00, "PROM/GPIO mode" ) + PORT_CONFSETTING( 0x00, "All" ) + PORT_CONFSETTING( 0x10, "MON only" ) +INPUT_PORTS_END + +} // anonymous namespace + + +imm4_22_device::imm4_22_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock) + : device_t(mconfig, INTELLEC4_INST_DATA_STORAGE, tag, owner, clock) + , device_univ_card_interface(mconfig, *this) + , device_image_interface(mconfig, *this) + , m_jumpers(*this, "JUMPERS") + , m_ram_io_mapped(false) + , m_ram_page(0U), m_rom_page(0U), m_rom_mirror(false) + , m_prom() +{ + std::fill(std::begin(m_memory), std::end(m_memory), 0U); + std::fill(std::begin(m_status), std::end(m_status), 0U); +} + + +image_init_result imm4_22_device::call_load() +{ + if ((length() > 1024U) || (length() % 256U)) + return image_init_result::FAIL; + + allocate(); + if (fread(m_prom.get(), length()) != length()) + return image_init_result::FAIL; + + map_prom(); + + return image_init_result::PASS; +} + +void imm4_22_device::call_unload() +{ + unmap_prom(); +} + + +ioport_constructor imm4_22_device::device_input_ports() const +{ + return INPUT_PORTS_NAME(imm4_22); +} + +void imm4_22_device::device_start() +{ + m_ram_io_mapped = false; + + allocate(); + + save_item(NAME(m_ram_page)); + save_item(NAME(m_rom_page)); + save_item(NAME(m_rom_mirror)); + save_item(NAME(m_memory)); + save_item(NAME(m_status)); + save_pointer(NAME(m_prom.get()), 1024U); +} + +void imm4_22_device::device_reset() +{ + map_ram_io(); +} + + +WRITE_LINE_MEMBER(imm4_22_device::reset_4002_in) +{ + // FIXME: this takes several cycles to actually erase everything, and prevents writes while asserted + if (!state) + { + std::fill(std::begin(m_memory), std::end(m_memory), 0U); + std::fill(std::begin(m_status), std::end(m_status), 0U); + } +} + + +WRITE8_MEMBER(imm4_22_device::ram_out) +{ + // GPIO write - hooking this up would be a pain with MAME as it is + logerror("4002 A%u out %X\n", 13U + (offset & 0x03U), data & 0x0fU); +} + +WRITE8_MEMBER(imm4_22_device::rom_out) +{ + // GPIO write - hooking this up would be a pain with MAME as it is + logerror("ROM %u out %X\n", (m_rom_page << 2) | ((offset >> 4) & 0x03U), data & 0x0fU); +} + +READ8_MEMBER(imm4_22_device::rom_in) +{ + // GPIO read - hooking this up would be a pain with MAME as it is + if (!machine().side_effect_disabled()) + logerror("ROM %u in\n", (m_rom_page << 2) | ((offset >> 4) & 0x03U)); + return 0x0fU; +} + + +void imm4_22_device::allocate() +{ + if (!m_prom) + { + m_prom = std::make_unique(1024U); + std::fill(m_prom.get(), m_prom.get() + 1024U, 0U); + } +} + +void imm4_22_device::map_ram_io() +{ + if (!m_ram_io_mapped) + { + static constexpr offs_t ram_start[3][4] = { + { 0x01U, 0x04U, 0x05U, 0x07U }, + { 0x02U, 0x04U, 0x06U, 0x07U }, + { 0x03U, 0x05U, 0x06U, 0x07U } }; + + m_ram_io_mapped = true; + + ioport_value const jumpers(m_jumpers->read()); + m_ram_page = jumpers & 0x03U; + m_rom_page = (jumpers >> 2) & 0x03U; + m_rom_mirror = BIT(~jumpers, 4); + + if ((1U > m_ram_page) || (3U < m_ram_page)) + throw emu_fatalerror("imm4_22_device: invalid RAM page %u", m_ram_page); + if ((1U > m_rom_page) || (3U < m_rom_page)) + throw emu_fatalerror("imm4_22_device: invalid PROM/GPIO page %u", m_rom_page); + + for (offs_t const start : ram_start[m_ram_page - 1U]) + { + memory_space().install_ram(start << 8, (start << 8) | 0x00ffU, m_memory); + status_space().install_ram(start << 6, (start << 6) | 0x003fU, m_status); + ram_ports_space().install_write_handler(start << 2, (start << 2) | 0x03U, write8_delegate(FUNC(imm4_22_device::ram_out), this)); + } + + offs_t const rom_ports_start(offs_t(m_rom_page) << 6); + offs_t const rom_ports_end(rom_ports_start | 0x003fU); + offs_t const rom_ports_mirror(m_rom_mirror ? 0x1f00U : 0x0700U); + rom_ports_space().install_readwrite_handler( + rom_ports_start, rom_ports_end, 0U, rom_ports_mirror, 0U, + read8_delegate(FUNC(imm4_22_device::rom_in), this), write8_delegate(FUNC(imm4_22_device::rom_out), this)); + + if (is_loaded()) + map_prom(); + } +} + +void imm4_22_device::map_prom() +{ + if (m_ram_io_mapped) + { + // FIXME: gimme a cookie! + // FIXME: if mirror is on, this will fight console RAM for the bus in 0x2000 region and also appear in the "two switches" 0x3000 region + rom_space().install_rom( + offs_t(m_rom_page) << 10, offs_t((offs_t(m_rom_page) << 10) | length()), m_rom_mirror ? 0x1000U : 0x0000U, + m_prom.get()); + } +} + +void imm4_22_device::unmap_prom() +{ + // FIXME: where's my magic cookie? + rom_space().unmap_read(offs_t(m_rom_page) << 10, (offs_t(m_rom_page) << 10) | 0x03ffU, m_rom_mirror ? 0x1000U : 0x0000U); +} + +} } // namespace bus::intellec4 diff --git a/src/devices/bus/intellec4/insdatastor.h b/src/devices/bus/intellec4/insdatastor.h new file mode 100644 index 00000000000..fa342d1f5bc --- /dev/null +++ b/src/devices/bus/intellec4/insdatastor.h @@ -0,0 +1,199 @@ +// license:BSD-3-Clause +// copyright-holders:Vas Crabb +/* +imm4-22 Instruction/Data Storage Module + +This card has four 4002 RAMs configured as a page, sockets for four +1702A or similar 256×8 PROMs configured as a ROM page, buffers for four +4-bit input ports, and latches for four 4-bit output ports. + +The 4002 RAMs may be jumpered to be selected by CM-RAM1, CM-RAM2 or +CM-RAM3. Note that the CM-RAM lines are not decoded, so the 4002 RAMs +will be mirrored. (With two or more imm4-22 cards are installed, the +4002 RAMs will fight for the bus if pages 4-7 are selected.) + +The PROMs and I/O ports may be jumpered to be mapped at 0x04xx...0x07xx, +0x08xx...0x0bff or 0x0cff...0x0fff. Additionally, the card may be +jumpered to enable the PROMs and I/O ports only when /ENABLE MON PROM is +asserted, or at all times. + +This card may seem like a good way to expand three aspects of the system +at once, but in practice the PROMs are of limited use: +* If jumpered to enable the PROMs at all times, the PROMs will fight for + the bus if console RAM card program storage is selected. +* If jumpered to enable the PROMs only when /ENABLE MON PROM is + asserted, the PROMs become effectively inaccessible as the boot vector + is in the onboard monitor PROM region, and the onboard monitor PROM + program provides no way to jump to or read from arbitrary locations. + +This card was probably most useful as the cheapest way to double RAM and +I/O ports. Without PROMs installed, mapping I/O at 0x0400...0x07ff only +when /ENABLE MON PROM is asserted would be a convenient way to provide +the necessary connections for an imm4-90 high-speed paper tape reader. + +Image file for the PROMs must be an exact multiple of 256 bytes. PROMs +are assumed to be filled in order from lowest to highest address. +Jumper changes only take effect on hard reset. + + +P1 Universal Slot edge connector + + 1 2 + GND 3 4 GND + 5 6 + 7 8 + 9 10 + MA0 11 12 MA1 + MA2 13 14 MA3 + MA4 15 16 MA5 + MA6 17 18 MA7 + C0 19 20 C1 + 21 22 + /MDI0 23 24 + /MDI1 25 26 + /MDI3 27 28 + /MDI2 29 30 + /MDI5 31 32 + /MDI4 33 34 + /MDI7 35 36 + /MDI6 37 38 + 39 40 + /OUT 41 42 /ENABLE MON PROM + -10V 43 44 -10V + 45 46 + /CM-RAM2 47 48 /CM-RAM3 + 49 50 /CM-RAM1 + I/O 1 51 52 I/O 0 + I/O 2 53 54 /IN + 55 56 I/O 3 + 57 58 + 59 60 + 61 62 + 63 64 + 65 66 + 67 68 + 69 70 + 71 72 /D3 + 73 74 + 75 76 /D2 + 77 78 + /SYNC 79 80 /D1 + 81 82 + /D0 83 84 + 85 86 + 87 88 /RESET-4002 + 89 90 + 91 92 + /CM-ROM 93 94 C3 + 95 96 C2 + PHASE 2 97 98 PHASE 1 + +5V 99 100 +5V + + +P1 inputs (40-pin IDC) + + ROM 4/8/12 IN0 1 2 ROM 4/8/12 IN1 + ROM 4/8/12 IN2 3 4 ROM 4/8/12 IN3 + GND 5 6 ROM 5/9/13 IN0 + ROM 5/9/13 IN1 7 8 ROM 5/9/13 IN2 + ROM 5/9/13 IN3 9 10 GND + ROM 6/10/14 IN0 11 12 ROM 6/10/14 IN1 + ROM 6/10/14 IN2 13 14 ROM 6/10/14 IN3 + GND 15 16 ROM 7/11/15 IN0 + ROM 7/11/15 IN1 17 18 ROM 7/11/15 IN2 + ROM 7/11/15 IN3 19 20 GND + 21 22 + 23 24 + 25 26 + 27 28 + 29 30 + 31 32 + 33 34 + 35 36 + 37 38 + 39 40 + + +P2 outputs (40-pin IDC) + + ROM 4/8/12 OUT0 1 2 ROM 4/8/12 OUT1 + ROM 4/8/12 OUT2 3 4 ROM 4/8/12 OUT3 + GND 5 6 ROM 5/9/13 OUT0 + ROM 5/9/13 OUT1 7 8 ROM 5/9/13 OUT2 + ROM 5/9/13 OUT3 9 10 GND + ROM 6/10/14 OUT0 11 12 ROM 6/10/14 OUT1 + ROM 6/10/14 OUT2 13 14 ROM 6/10/14 OUT3 + GND 15 16 ROM 7/11/15 OUT0 + ROM 7/11/15 OUT1 17 18 ROM 7/11/15 OUT2 + ROM 7/11/15 OUT3 19 20 GND + RAM 4/8/12 OUT0 21 22 RAM 4/8/12 OUT1 + RAM 4/8/12 OUT2 23 24 RAM 4/8/12 OUT3 + GND 25 26 RAM 5/9/13 OUT0 + RAM 5/9/13 OUT1 27 28 RAM 5/9/13 OUT2 + RAM 5/9/13 OUT3 29 30 GND + RAM 6/10/14 OUT0 31 32 RAM 6/10/14 OUT1 + RAM 6/10/14 OUT2 33 34 RAM 6/10/14 OUT3 + GND 35 36 RAM 7/11/15 OUT0 + RAM 7/11/15 OUT1 37 38 RAM 7/11/15 OUT2 + RAM 7/11/15 OUT3 39 40 GND +*/ +#ifndef MAME_BUS_INTELLEC4_INSDATASTOR_H +#define MAME_BUS_INTELLEC4_INSDATASTOR_H + +#pragma once + +#include "intellec4.h" + +namespace bus { namespace intellec4 { + +class imm4_22_device : public device_t, public device_univ_card_interface, public device_image_interface +{ +public: + imm4_22_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock); + + virtual image_init_result call_load() override; + virtual void call_unload() override; + + virtual iodevice_t image_type() const override { return IO_ROM; } + virtual bool is_readable() const override { return true; } + virtual bool is_writeable() const override { return false; } + virtual bool is_creatable() const override { return false; } + virtual bool must_be_loaded() const override { return false; } + virtual bool is_reset_on_load() const override { return false; } + virtual char const *file_extensions() const override { return "rom,bin"; } + virtual char const *custom_instance_name() const override { return "promimage"; } + virtual char const *custom_brief_instance_name() const override { return "prom"; } + +protected: + virtual ioport_constructor device_input_ports() const override; + virtual void device_start() override; + virtual void device_reset() override; + + virtual DECLARE_WRITE_LINE_MEMBER(reset_4002_in) override; + +private: + DECLARE_WRITE8_MEMBER(ram_out); + DECLARE_WRITE8_MEMBER(rom_out); + DECLARE_READ8_MEMBER(rom_in); + + void allocate(); + void map_ram_io(); + void map_prom(); + void unmap_prom(); + + required_ioport m_jumpers; + + bool m_ram_io_mapped; + + u8 m_ram_page, m_rom_page; + bool m_rom_mirror; + + u8 m_memory[256], m_status[64]; + std::unique_ptr m_prom; +}; + +} } // namespace bus::intellec4 + +DECLARE_DEVICE_TYPE_NS(INTELLEC4_INST_DATA_STORAGE, bus::intellec4, imm4_22_device) + +#endif // MAME_BUS_INTELLEC4_INSDATASTOR_H diff --git a/src/devices/bus/intellec4/intellec4.cpp b/src/devices/bus/intellec4/intellec4.cpp index 1f456e22558..65ea12e743f 100644 --- a/src/devices/bus/intellec4/intellec4.cpp +++ b/src/devices/bus/intellec4/intellec4.cpp @@ -74,12 +74,12 @@ univ_bus_device::univ_bus_device(machine_config const &mconfig, char const *tag, , m_memory_space(-1) , m_status_space(-1) , m_ram_ports_space(-1) - , m_stop_out_cb(*this) , m_test_out_cb(*this) + , m_stop_out_cb(*this) , m_reset_4002_out_cb(*this) , m_user_reset_out_cb(*this) - , m_stop(0U) , m_test(0U) + , m_stop(0U) , m_reset_4002(0U) , m_user_reset(0U) { @@ -133,44 +133,35 @@ void univ_bus_device::set_ram_ports_space(device_t &device, char const *tag, int WRITE_LINE_MEMBER(univ_bus_device::sync_in) { - // FIXME: distribute to cards -} - -WRITE_LINE_MEMBER(univ_bus_device::test_in) -{ - if (state) - m_test &= ~u16(1U); - else - m_test |= 1U; - // FIXME: distribute to cards -} - -WRITE_LINE_MEMBER(univ_bus_device::stop_in) -{ - if (state) - m_stop &= ~u16(1U); - else - m_stop |= 1U; - // FIXME: distribute to cards + for (device_univ_card_interface *card : m_cards) + { + if (card) + card->sync_in(state); + else + break; + } } WRITE_LINE_MEMBER(univ_bus_device::stop_acknowledge_in) { - // FIXME: distribute to cards + for (device_univ_card_interface *card : m_cards) + { + if (card) + card->stop_acknowledge_in(state); + else + break; + } } WRITE_LINE_MEMBER(univ_bus_device::cpu_reset_in) { - // FIXME: distribute to cards -} - -WRITE_LINE_MEMBER(univ_bus_device::reset_4002_in) -{ - if (state) - m_reset_4002 &= ~u16(1U); - else - m_reset_4002 |= 1U; - // FIXME: distribute to cards + for (device_univ_card_interface *card : m_cards) + { + if (card) + card->cpu_reset_in(state); + else + break; + } } @@ -194,10 +185,15 @@ void univ_bus_device::device_validity_check(validity_checker &valid) const void univ_bus_device::device_start() { - m_stop_out_cb.resolve_safe(); m_test_out_cb.resolve_safe(); + m_stop_out_cb.resolve_safe(); m_reset_4002_out_cb.resolve_safe(); m_user_reset_out_cb.resolve_safe(); + + save_item(NAME(m_test)); + save_item(NAME(m_stop)); + save_item(NAME(m_reset_4002)); + save_item(NAME(m_user_reset)); } @@ -218,6 +214,98 @@ unsigned univ_bus_device::add_card(device_univ_card_interface &card) throw emu_fatalerror("univ_bus_device: maximum number of cards (%u) exceeded\n", unsigned(ARRAY_LENGTH(m_cards))); } +void univ_bus_device::set_test(unsigned index, int state) +{ + assert(ARRAY_LENGTH(m_cards) >= index); + bool const changed(bool(state) != !BIT(m_test, index)); + if (changed) + { + u16 const other(m_test & ~(u16(1U) << index)); + if (state) + m_test = other; + else + m_test |= u16(1U) << index; + + if ((ARRAY_LENGTH(m_cards) != index) && !(other & ~(u16(1U) << ARRAY_LENGTH(m_cards)))) + m_test_out_cb(state); + + for (unsigned card = 0U; (ARRAY_LENGTH(m_cards) > card) && m_cards[card]; ++card) + { + if ((index != card) && !(other & ~(u16(1U) << index))) + m_cards[card]->test_in(state); + } + } +} + +void univ_bus_device::set_stop(unsigned index, int state) +{ + assert(ARRAY_LENGTH(m_cards) >= index); + bool const changed(bool(state) != !BIT(m_stop, index)); + if (changed) + { + u16 const other(m_stop & ~(u16(1U) << index)); + if (state) + m_stop = other; + else + m_stop |= u16(1U) << index; + + if ((ARRAY_LENGTH(m_cards) != index) && !(other & ~(u16(1U) << ARRAY_LENGTH(m_cards)))) + m_stop_out_cb(state); + + for (unsigned card = 0U; (ARRAY_LENGTH(m_cards) > card) && m_cards[card]; ++card) + { + if ((index != card) && !(other & ~(u16(1U) << index))) + m_cards[card]->stop_in(state); + } + } +} + +void univ_bus_device::set_reset_4002(unsigned index, int state) +{ + assert(ARRAY_LENGTH(m_cards) >= index); + bool const changed(bool(state) != !BIT(m_reset_4002, index)); + if (changed) + { + u16 const other(m_reset_4002 & ~(u16(1U) << index)); + if (state) + m_reset_4002 = other; + else + m_reset_4002 |= u16(1U) << index; + + if ((ARRAY_LENGTH(m_cards) != index) && !(other & ~(u16(1U) << ARRAY_LENGTH(m_cards)))) + m_reset_4002_out_cb(state); + + for (unsigned card = 0U; (ARRAY_LENGTH(m_cards) > card) && m_cards[card]; ++card) + { + if ((index != card) && !(other & ~(u16(1U) << index))) + m_cards[card]->reset_4002_in(state); + } + } +} + +void univ_bus_device::set_user_reset(unsigned index, int state) +{ + assert(ARRAY_LENGTH(m_cards) > index); + bool const changed(bool(state) != !BIT(m_user_reset, index)); + if (changed) + { + u16 const other(m_user_reset & ~(u16(1U) << index)); + if (state) + m_user_reset = other; + else + m_user_reset |= u16(1U) << index; + + if (!other) + m_user_reset_out_cb(state); + + for (unsigned card = 0U; (ARRAY_LENGTH(m_cards) > card) && m_cards[card]; ++card) + { + if ((index != card) && !(other & ~(u16(1U) << index))) + m_cards[card]->user_reset_in(state); + } + } +} + /*********************************************************************** @@ -248,10 +336,12 @@ void device_univ_card_interface::set_bus(univ_bus_device &bus) +#include "insdatastor.h" #include "prommemory.h" #include "tapereader.h" SLOT_INTERFACE_START(intellec4_univ_cards) - SLOT_INTERFACE("imm4_90", INTELLEC4_TAPE_READER) + SLOT_INTERFACE("imm4_22", INTELLEC4_INST_DATA_STORAGE) SLOT_INTERFACE("imm6_26", INTELLEC4_PROM_MEMORY) + SLOT_INTERFACE("imm4_90", INTELLEC4_TAPE_READER) SLOT_INTERFACE_END diff --git a/src/devices/bus/intellec4/intellec4.h b/src/devices/bus/intellec4/intellec4.h index 61a77873d54..5165bdcb6d7 100644 --- a/src/devices/bus/intellec4/intellec4.h +++ b/src/devices/bus/intellec4/intellec4.h @@ -138,12 +138,12 @@ to implement the card in both systems. #define MCFG_INTELLEC4_UNIV_BUS_RAM_PORTS_SPACE(tag, space) \ bus::intellec4::univ_bus_device::set_ram_ports_space(*device, "^" tag, space); -#define MCFG_INTELLEC4_UNIV_BUS_STOP_CB(obj) \ - bus::intellec4::univ_bus_device::set_stop_out_cb(*device, DEVCB_##obj); - #define MCFG_INTELLEC4_UNIV_BUS_TEST_CB(obj) \ bus::intellec4::univ_bus_device::set_test_out_cb(*device, DEVCB_##obj); +#define MCFG_INTELLEC4_UNIV_BUS_STOP_CB(obj) \ + bus::intellec4::univ_bus_device::set_stop_out_cb(*device, DEVCB_##obj); + #define MCFG_INTELLEC4_UNIV_BUS_RESET_4002_CB(obj) \ bus::intellec4::univ_bus_device::set_reset_4002_out_cb(*device, DEVCB_##obj); @@ -202,15 +202,15 @@ public: // input lines DECLARE_WRITE_LINE_MEMBER(sync_in); - DECLARE_WRITE_LINE_MEMBER(test_in); - DECLARE_WRITE_LINE_MEMBER(stop_in); + DECLARE_WRITE_LINE_MEMBER(test_in) {set_test(ARRAY_LENGTH(m_cards), state); } + DECLARE_WRITE_LINE_MEMBER(stop_in) {set_stop(ARRAY_LENGTH(m_cards), state); } DECLARE_WRITE_LINE_MEMBER(stop_acknowledge_in); DECLARE_WRITE_LINE_MEMBER(cpu_reset_in); - DECLARE_WRITE_LINE_MEMBER(reset_4002_in); + DECLARE_WRITE_LINE_MEMBER(reset_4002_in) { set_reset_4002(ARRAY_LENGTH(m_cards), state); } // output lines - DECLARE_READ_LINE_MEMBER(stop_out) const { return (m_stop & ~u16(1U)) ? 0 : 1; } DECLARE_READ_LINE_MEMBER(test_out) const { return (m_test & ~u16(1U)) ? 0 : 1; } + DECLARE_READ_LINE_MEMBER(stop_out) const { return (m_stop & ~u16(1U)) ? 0 : 1; } DECLARE_READ_LINE_MEMBER(reset_4002_out) const { return (m_reset_4002 & ~u16(1U)) ? 0 : 1; } DECLARE_READ_LINE_MEMBER(user_reset_out) const { return (m_user_reset & ~u16(1U)) ? 0 : 1; } @@ -222,6 +222,10 @@ protected: private: // helpers for cards unsigned add_card(device_univ_card_interface &card); + void set_test(unsigned index, int state); + void set_stop(unsigned index, int state); + void set_reset_4002(unsigned index, int state); + void set_user_reset(unsigned index, int state); // finding address spaces required_device m_rom_device, m_rom_ports_device; @@ -230,8 +234,8 @@ private: int m_memory_space, m_status_space, m_ram_ports_space; // output line callbacks - devcb_write_line m_stop_out_cb; devcb_write_line m_test_out_cb; + devcb_write_line m_stop_out_cb; devcb_write_line m_reset_4002_out_cb; devcb_write_line m_user_reset_out_cb; @@ -239,7 +243,7 @@ private: device_univ_card_interface *m_cards[15]; // packed line states - u16 m_stop, m_test, m_reset_4002, m_user_reset; + u16 m_test, m_stop, m_reset_4002, m_user_reset; }; @@ -260,6 +264,19 @@ protected: address_space &status_space() { return m_bus->m_status_device->space(m_bus->m_status_space); } address_space &ram_ports_space() { return m_bus->m_ram_ports_device->space(m_bus->m_ram_ports_space); } + DECLARE_WRITE_LINE_MEMBER(test_out) { m_bus->set_test(m_index, state); } + DECLARE_WRITE_LINE_MEMBER(stop_out) { m_bus->set_stop(m_index, state); } + DECLARE_WRITE_LINE_MEMBER(reset_4002_out) { m_bus->set_reset_4002(m_index, state); } + DECLARE_WRITE_LINE_MEMBER(user_reset_out) { m_bus->set_user_reset(m_index, state); } + + virtual DECLARE_WRITE_LINE_MEMBER(sync_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(test_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(stop_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(stop_acknowledge_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(cpu_reset_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(reset_4002_in) { } + virtual DECLARE_WRITE_LINE_MEMBER(user_reset_in) { } + private: void set_bus(univ_bus_device &bus); diff --git a/src/devices/bus/intellec4/tapereader.h b/src/devices/bus/intellec4/tapereader.h index baba85dde73..71153f042df 100644 --- a/src/devices/bus/intellec4/tapereader.h +++ b/src/devices/bus/intellec4/tapereader.h @@ -8,8 +8,8 @@ device (use J command to select it), but it doesn't appear in any catalogues or manuals I've seen. Apparently it was announced in Computerworld. -In practice you needed a GPIO card (e.g. an imm4-60) to talk to the -paper taper reader. To simplify configuration we emulate the I/O +In practice you needed a GPIO card (e.g. an imm4-60 or imm4-22) to talk +to the paper taper reader. To simplify configuration we emulate the I/O interface and paper tape reader as a single device. */ #ifndef MAME_BUS_INTELLEC4_TAPEREADER_H diff --git a/src/devices/bus/sunkbd/hlekbd.cpp b/src/devices/bus/sunkbd/hlekbd.cpp index 60abf1e0c4b..8e25d09a028 100644 --- a/src/devices/bus/sunkbd/hlekbd.cpp +++ b/src/devices/bus/sunkbd/hlekbd.cpp @@ -95,7 +95,7 @@ 48 49 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 14 70 71 72 5f 61 77 13 78 79 7a 43 0d 18 1b 1c 5e 32 5a - 0f is a blank key + 0f has a blank keycap backspace immediately above return backslash and backtick/tilde at top right of main area control on home row, caps lock at bottom left corner of main area -- cgit v1.2.3