summaryrefslogtreecommitdiffstatshomepage
path: root/src/devices/machine/ncr5380.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/devices/machine/ncr5380.h')
-rw-r--r--src/devices/machine/ncr5380.h210
1 files changed, 163 insertions, 47 deletions
diff --git a/src/devices/machine/ncr5380.h b/src/devices/machine/ncr5380.h
index 9d9d7b96617..e7107ae285e 100644
--- a/src/devices/machine/ncr5380.h
+++ b/src/devices/machine/ncr5380.h
@@ -1,70 +1,186 @@
// license:BSD-3-Clause
-// copyright-holders:R. Belmont
-/*
- * ncr5380.h SCSI controller
- *
- */
+// copyright-holders:Patrick Mackinlay
#ifndef MAME_MACHINE_NCR5380_H
#define MAME_MACHINE_NCR5380_H
#pragma once
-#include "legscsi.h"
+#include "machine/nscsi_bus.h"
-// 5380 registers
-enum
-{
- R5380_CURDATA = 0, // current SCSI data (read only)
- R5380_OUTDATA = 0, // output data (write only)
- R5380_INICOMMAND, // initiator command
- R5380_MODE, // mode
- R5380_TARGETCMD, // target command
- R5380_SELENABLE, // select enable (write only)
- R5380_BUSSTATUS = R5380_SELENABLE, // bus status (read only)
- R5380_STARTDMA, // start DMA send (write only)
- R5380_BUSANDSTAT = R5380_STARTDMA, // bus and status (read only)
- R5380_DMATARGET, // DMA target (write only)
- R5380_INPUTDATA = R5380_DMATARGET, // input data (read only)
- R5380_DMAINIRECV, // DMA initiator receive (write only)
- R5380_RESETPARITY = R5380_DMAINIRECV // reset parity/interrupt (read only)
-};
-
-// special Mac Plus registers - they implemented it weird
-#define R5380_OUTDATA_DTACK (R5380_OUTDATA | 0x10)
-#define R5380_CURDATA_DTACK (R5380_CURDATA | 0x10)
-
-// device stuff
-
-
-class ncr5380_device : public legacy_scsi_host_adapter
+class ncr5380_device
+ : public nscsi_device
+ , public nscsi_slot_card_interface
{
public:
- // construction/destruction
- ncr5380_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock);
+ ncr5380_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
- auto irq_callback() { return m_irq_cb.bind(); }
+ // device configuration
+ auto irq_handler() { return m_irq_handler.bind(); }
+ auto drq_handler() { return m_drq_handler.bind(); }
- // our API
- uint8_t ncr5380_read_reg(uint32_t offset);
- void ncr5380_write_reg(uint32_t offset, uint8_t data);
+ // register access
+ void map(address_map &map);
+ u8 read(offs_t offset);
+ void write(offs_t offset, u8 data);
+
+ // dma access
+ void eop_w(int state);
+ u8 dma_r();
+ void dma_w(u8 val);
protected:
- // device-level overrides
+ ncr5380_device(machine_config const &mconfig, device_type type, char const *tag, device_t *owner, u32 clock, bool has_lbs = false);
+
+ // device_t overrides
virtual void device_start() override;
virtual void device_reset() override;
- virtual void device_stop() override;
+
+ // ncsci_device overrides
+ virtual void scsi_ctrl_changed() override;
+
+ // register read handlers
+ u8 csdata_r();
+ u8 icmd_r();
+ u8 mode_r();
+ u8 tcmd_r();
+ u8 csstat_r();
+ u8 bas_r();
+ u8 idata_r();
+ u8 rpi_r();
+
+ // register write handlers
+ void odata_w(u8 data);
+ void icmd_w(u8 data);
+ void mode_w(u8 data);
+ void tcmd_w(u8 data);
+ void selen_w(u8 data);
+ void sds_w(u8 data);
+ void sdtr_w(u8 data);
+ void sdir_w(u8 data);
+
+ // state machine
+ void state_timer(s32 param);
+ int state_step();
+
+ // other helpers
+ void scsi_data_w(u8 data);
+ void set_irq(bool irq_state);
+ void set_drq(bool drq_state);
private:
- uint8_t m_5380_Registers[8];
- uint8_t m_last_id;
- uint8_t m_5380_Command[32];
- int32_t m_cmd_ptr, m_d_ptr, m_d_limit, m_next_req_flag;
- uint8_t m_5380_Data[512];
- devcb_write_line m_irq_cb; /* irq callback */
+ enum icmd_mask : u8
+ {
+ IC_RST = 0x80, // assert R̅S̅T̅
+ IC_TEST = 0x40, // test mode (wo)
+ IC_AIP = 0x40, // arbitration in progress (ro)
+ IC_LA = 0x20, // lost arbitration (ro)
+ IC_ACK = 0x10, // assert A̅C̅K̅
+ IC_BSY = 0x08, // assert B̅S̅Y̅
+ IC_SEL = 0x04, // assert S̅E̅L̅
+ IC_ATN = 0x02, // assert A̅T̅N̅
+ IC_DBUS = 0x01, // assert data bus
+
+ IC_PHASE = 0x9e,
+ IC_WRITE = 0x9f,
+ };
+ enum mode_mask : u8
+ {
+ MODE_BLOCKDMA = 0x80,
+ MODE_TARGET = 0x40,
+ MODE_PARITYCHK = 0x20,
+ MODE_PARITYIRQ = 0x10,
+ MODE_EOPIRQ = 0x08,
+ MODE_BSYIRQ = 0x04,
+ MODE_DMA = 0x02,
+ MODE_ARBITRATE = 0x01,
+ };
+ enum tcmd_mask : u8
+ {
+ TC_LBS = 0x80, // last byte sent
+ TC_REQ = 0x08, // assert R̅E̅Q̅
+ TC_MSG = 0x04, // assert M̅S̅G̅
+ TC_CD = 0x02, // assert C̅/D
+ TC_IO = 0x01, // assert I̅/O
+
+ TC_PHASE = 0x07,
+ };
+ enum csstat_mask : u8
+ {
+ ST_RST = 0x80,
+ ST_BSY = 0x40,
+ ST_REQ = 0x20,
+ ST_MSG = 0x10,
+ ST_CD = 0x08,
+ ST_IO = 0x04,
+ ST_SEL = 0x02,
+ ST_DBP = 0x01,
+ };
+ enum bas_mask : u8
+ {
+ BAS_ENDOFDMA = 0x80,
+ BAS_DMAREQUEST = 0x40,
+ BAS_PARITYERROR = 0x20,
+ BAS_IRQACTIVE = 0x10,
+ BAS_PHASEMATCH = 0x08,
+ BAS_BUSYERROR = 0x04,
+ BAS_ATN = 0x02,
+ BAS_ACK = 0x01,
+ };
+
+ devcb_write_line m_irq_handler;
+ devcb_write_line m_drq_handler;
+
+ // state machine
+ emu_timer *m_state_timer;
+ enum state : uint32_t
+ {
+ IDLE,
+
+ // arbitration
+ ARB_BUS_FREE,
+ ARB_START,
+ ARB_EVALUATE,
+
+ // dma transfer
+ DMA_IN_REQ,
+ DMA_IN_ACK,
+ DMA_OUT_REQ,
+ DMA_OUT_DRQ,
+ DMA_OUT_ACK,
+ }
+ m_state;
+
+ // registers
+ u8 m_odata;
+ u8 m_icmd;
+ u8 m_mode;
+ u8 m_tcmd;
+ u8 m_bas;
+ u8 m_idata;
+
+ // line state
+ u32 m_scsi_ctrl;
+ bool m_irq_state;
+ bool m_drq_state;
+
+ bool const m_has_lbs;
+};
+
+class ncr53c80_device : public ncr5380_device
+{
+public:
+ ncr53c80_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
+};
+
+class cxd1180_device : public ncr5380_device
+{
+public:
+ cxd1180_device(machine_config const &mconfig, char const *tag, device_t *owner, u32 clock = 0);
};
-// device type definition
DECLARE_DEVICE_TYPE(NCR5380, ncr5380_device)
+DECLARE_DEVICE_TYPE(NCR53C80, ncr53c80_device)
+DECLARE_DEVICE_TYPE(CXD1180, cxd1180_device)
#endif // MAME_MACHINE_NCR5380_H