diff options
Diffstat (limited to 'src/mame/machine/hp98x5_io_sys.cpp')
-rw-r--r-- | src/mame/machine/hp98x5_io_sys.cpp | 154 |
1 files changed, 154 insertions, 0 deletions
diff --git a/src/mame/machine/hp98x5_io_sys.cpp b/src/mame/machine/hp98x5_io_sys.cpp new file mode 100644 index 00000000000..855b48bc875 --- /dev/null +++ b/src/mame/machine/hp98x5_io_sys.cpp @@ -0,0 +1,154 @@ +// License:BSD-3-Clause +// copyright-holders:F. Ulivi +/********************************************************************* + + hp98x5_io_sys.cpp + + HP98x5 I/O sub-system + +*********************************************************************/ + +#include "emu.h" +#include "hp98x5_io_sys.h" +#include "cpu/hphybrid/hphybrid.h" + +// Bit manipulation +namespace { + template<typename T> constexpr T BIT_MASK(unsigned n) + { + return (T)1U << n; + } + + template<typename T> void BIT_CLR(T& w , unsigned n) + { + w &= ~BIT_MASK<T>(n); + } + + template<typename T> void BIT_SET(T& w , unsigned n) + { + w |= BIT_MASK<T>(n); + } +} + +// Device type definition +DEFINE_DEVICE_TYPE(HP98X5_IO_SYS, hp98x5_io_sys_device, "hp98x5_io_sys", "HP98x5 I/O sub-system") + +hp98x5_io_sys_device::hp98x5_io_sys_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) +: device_t(mconfig , HP98X5_IO_SYS , tag , owner , clock) + , m_irl_handler(*this) + , m_irh_handler(*this) + , m_flg_handler(*this) + , m_sts_handler(*this) + , m_dmar_handler(*this) +{ +} + +void hp98x5_io_sys_device::device_start() +{ + m_irl_handler.resolve_safe(); + m_irh_handler.resolve_safe(); + m_flg_handler.resolve_safe(); + m_sts_handler.resolve_safe(); + m_dmar_handler.resolve_safe(); + + save_item(NAME(m_irq_pending)); + save_item(NAME(m_pa)); + save_item(NAME(m_flg_status)); + save_item(NAME(m_sts_status)); + save_item(NAME(m_dmar_status)); +} + +void hp98x5_io_sys_device::device_reset() +{ + m_irq_pending = 0; + update_irq(); + m_pa = 0; + m_flg_status = 0; + m_sts_status = 0; + update_flg_sts(); + m_dmar_status = 0; + update_dmar(); +} + +IRQ_CALLBACK_MEMBER(hp98x5_io_sys_device::irq_callback) +{ + if (irqline == HPHYBRID_IRL) { + return m_irq_pending & 0xff; + } else { + return m_irq_pending >> 8; + } +} + +WRITE8_MEMBER(hp98x5_io_sys_device::pa_w) +{ + m_pa = data; + update_flg_sts(); +} + +void hp98x5_io_sys_device::set_irq(uint8_t sc , int state) +{ + if (state) { + BIT_SET(m_irq_pending, sc); + } else { + BIT_CLR(m_irq_pending, sc); + } + update_irq(); +} + +void hp98x5_io_sys_device::set_sts(uint8_t sc , int state) +{ + if (state) { + BIT_SET(m_sts_status, sc); + } else { + BIT_CLR(m_sts_status, sc); + } + if (sc == m_pa) { + update_flg_sts(); + } +} + +void hp98x5_io_sys_device::set_flg(uint8_t sc , int state) +{ + if (state) { + BIT_SET(m_flg_status, sc); + } else { + BIT_CLR(m_flg_status, sc); + } + if (sc == m_pa) { + update_flg_sts(); + } +} + +void hp98x5_io_sys_device::set_dmar(uint8_t sc , int state) +{ + if (state) { + BIT_SET(m_dmar_status, sc); + } else { + BIT_CLR(m_dmar_status, sc); + } + update_dmar(); +} + +bool hp98x5_io_sys_device::is_irq_pending(uint8_t sc) const +{ + return BIT(m_irq_pending , sc); +} + +void hp98x5_io_sys_device::update_irq() +{ + m_irl_handler((m_irq_pending & 0x00ff) != 0); + m_irh_handler((m_irq_pending & 0xff00) != 0); +} + +void hp98x5_io_sys_device::update_flg_sts() +{ + bool sts = BIT(m_sts_status , m_pa); + bool flg = BIT(m_flg_status , m_pa); + m_sts_handler(sts); + m_flg_handler(flg); +} + +void hp98x5_io_sys_device::update_dmar() +{ + m_dmar_handler(m_dmar_status != 0); +} |