diff options
Diffstat (limited to 'src/devices/bus/ieee488/hp9122c.cpp')
| -rw-r--r-- | src/devices/bus/ieee488/hp9122c.cpp | 183 |
1 files changed, 161 insertions, 22 deletions
diff --git a/src/devices/bus/ieee488/hp9122c.cpp b/src/devices/bus/ieee488/hp9122c.cpp index f533ecb8b11..6331e0e3ba1 100644 --- a/src/devices/bus/ieee488/hp9122c.cpp +++ b/src/devices/bus/ieee488/hp9122c.cpp @@ -10,34 +10,169 @@ #include "emu.h" #include "hp9122c.h" + +#include "cpu/m6809/m6809.h" #include "cpu/m6809/m6809.h" +#include "imagedev/floppy.h" +#include "machine/fdc_pll.h" #include "machine/i8291a.h" +#include "machine/i8291a.h" +#include "machine/wd_fdc.h" #include "machine/wd_fdc.h" + #include "formats/flopimg.h" + #include "hp9122c.lh" -DEFINE_DEVICE_TYPE(HP9122C, hp9122c_device, "hp9122c", "HP9122C Dual High density disk drive") - -hp9122c_device::hp9122c_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : device_t{mconfig, HP9122C, tag, owner, clock}, - device_ieee488_interface{mconfig, *this}, - m_cpu{*this , "cpu"}, - m_i8291a{*this, "i8291a"}, - m_fdc{*this, "mb8876"}, - m_floppy{*this, "floppy%u", 0}, - m_hpib_addr{*this , "ADDRESS"}, - m_testmode{*this, "TESTMODE"}, - m_leds{*this, "led%d", 0U}, - m_intsel{3}, - m_fdc_irq{false}, - m_i8291a_irq{false}, - m_fdc_drq{false}, - m_i8291a_drq{false}, - m_cpuirq{false}, - m_cpufirq{false}, - m_index_int{false}, - m_ds0{false}, - m_ds1{false} +namespace { + +class hp9122c_device : public device_t, + public device_ieee488_interface +{ +public: + // construction/destruction + hp9122c_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock); + +protected: + // device_t implementation + virtual void device_start() override ATTR_COLD; + virtual void device_reset() override ATTR_COLD; + virtual ioport_constructor device_input_ports() const override ATTR_COLD; + virtual const tiny_rom_entry *device_rom_region() const override ATTR_COLD; + virtual void device_add_mconfig(machine_config &config) override ATTR_COLD; + + // device_ieee488_interface implementation + virtual void ieee488_eoi(int state) override; + virtual void ieee488_dav(int state) override; + virtual void ieee488_nrfd(int state) override; + virtual void ieee488_ndac(int state) override; + virtual void ieee488_ifc(int state) override; + virtual void ieee488_srq(int state) override; + virtual void ieee488_atn(int state) override; + virtual void ieee488_ren(int state) override; + +private: + + + /* Control register bits: + * 0 - Head select + * 1 - unused + * 2 - FDC Clock selector - 0 - 1Mhz, 1 - 2Mhz + * 3 - IntSel1 + * 4 - DS1# + * 5 - DS0# + * 6 - LED + * 7 - IntSel0 + * + * Intsel: + * * - FIRQ IRQ + * 0 - FDCIRQ FDCOrg + * 1 - HPIBINT HPIBDReq + * 2 - GND IndexInt + * 3 - GND GND + */ + + constexpr static int REG_CNTL_HEADSEL = 1 << 0; + constexpr static int REG_CNTL_CLOCK_SEL = 1 << 2; + constexpr static int REG_CNTL_INTSEL1 = 1 << 3; + constexpr static int REG_CNTL_DS1 = 1 << 4; + constexpr static int REG_CNTL_DS0 = 1 << 5; + constexpr static int REG_CNTL_LED = 1 << 6; + constexpr static int REG_CNTL_INTSEL0 = 1 << 7; + + /* Status register bits: + * 0 - Addr0 + * 1 - Addr1 + * 2 - Addr2 + * 3 - Dual(H)/Single(L) + * 4 - T(L) + * 5 - Diskchg# + * 6 - Addr3 + * 7 - density indicatior: H - DD, L - HD + */ + + static constexpr int REG_STATUS_DUAL = 1 << 3; + static constexpr int REG_STATUS_TEST = 1 << 4; + static constexpr int REG_STATUS_DISKCHG = 1 << 5; + static constexpr int REG_STATUS_LOW_DENSITY = 1 << 7; + + void i8291a_eoi_w(int state); + void i8291a_dav_w(int state); + void i8291a_nrfd_w(int state); + void i8291a_ndac_w(int state); + void i8291a_ifc_w(int state); + void i8291a_srq_w(int state); + void i8291a_atn_w(int state); + void i8291a_ren_w(int state); + + uint8_t i8291a_dio_r(); + void i8291a_dio_w(uint8_t data); + + void i8291a_int_w(int state); + void i8291a_dreq_w(int state); + + void fdc_intrq_w(int state); + void fdc_drq_w(int state); + + void cmd_w(uint8_t data); + uint8_t status_r(); + void clridx_w(uint8_t data); + + void cpu_map(address_map &map) ATTR_COLD; + + void index_pulse_cb(floppy_image_device *floppy, int state); + void update_intsel(void); + + TIMER_CALLBACK_MEMBER(motor_timeout); + + required_device<cpu_device> m_cpu; + required_device<i8291a_device> m_i8291a; + required_device<mb8876_device> m_fdc; + required_device_array<floppy_connector, 2> m_floppy; + + required_ioport m_hpib_addr; + required_ioport m_testmode; + + output_finder<3> m_leds; + + int m_intsel; + + bool m_fdc_irq; + bool m_i8291a_irq; + bool m_fdc_drq; + bool m_i8291a_drq; + + bool m_cpuirq; + bool m_cpufirq; + + bool m_index_int; + + bool m_ds0; + bool m_ds1; + + emu_timer *m_motor_timer; +}; + +hp9122c_device::hp9122c_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : + device_t{mconfig, GPIB_HP9122C, tag, owner, clock}, + device_ieee488_interface{mconfig, *this}, + m_cpu{*this , "cpu"}, + m_i8291a{*this, "i8291a"}, + m_fdc{*this, "mb8876"}, + m_floppy{*this, "floppy%u", 0}, + m_hpib_addr{*this , "ADDRESS"}, + m_testmode{*this, "TESTMODE"}, + m_leds{*this, "led%d", 0U}, + m_intsel{3}, + m_fdc_irq{false}, + m_i8291a_irq{false}, + m_fdc_drq{false}, + m_i8291a_drq{false}, + m_cpuirq{false}, + m_cpufirq{false}, + m_index_int{false}, + m_ds0{false}, + m_ds1{false} { } @@ -398,3 +533,7 @@ void hp9122c_device::device_add_mconfig(machine_config &config) FLOPPY_CONNECTOR(config, "floppy1" , hp9122c_floppies , "35hd" , floppy_image_device::default_mfm_floppy_formats, true).enable_sound(true); config.set_default_layout(layout_hp9122c); } + +} // anonymous namespace + +DEFINE_DEVICE_TYPE_PRIVATE(GPIB_HP9122C, device_ieee488_interface, hp9122c_device, "hp9122c", "HP9122C Dual High density disk drive") |
