diff options
Diffstat (limited to 'src/devices/bus/abcbus/lux4105.cpp')
-rw-r--r-- | src/devices/bus/abcbus/lux4105.cpp | 432 |
1 files changed, 280 insertions, 152 deletions
diff --git a/src/devices/bus/abcbus/lux4105.cpp b/src/devices/bus/abcbus/lux4105.cpp index fbcf1dec72c..1db5d0d3869 100644 --- a/src/devices/bus/abcbus/lux4105.cpp +++ b/src/devices/bus/abcbus/lux4105.cpp @@ -48,8 +48,12 @@ Notes: // MACROS / CONSTANTS //************************************************************************** -#define SASIBUS_TAG "sasi" +#define LOG 0 +#define SASIBUS_TAG "sasi" +#define DMA_O1 BIT(m_dma, 0) +#define DMA_O2 BIT(m_dma, 1) +#define DMA_O3 BIT(m_dma, 2) //************************************************************************** @@ -59,64 +63,23 @@ Notes: DEFINE_DEVICE_TYPE(LUXOR_4105, luxor_4105_device, "lux4105", "Luxor 4105") -WRITE_LINE_MEMBER( luxor_4105_device::write_sasi_bsy ) -{ - m_sasi_bsy = state; - - if (m_sasi_bsy) - { - m_sasibus->write_sel(0); - } -} - -WRITE_LINE_MEMBER( luxor_4105_device::write_sasi_io ) -{ - m_sasi_io = state; - - if (!m_sasi_io) - { - m_sasi_data_out->write(m_data); - } - - update_trrq_int(); -} - -WRITE_LINE_MEMBER( luxor_4105_device::write_sasi_req ) -{ - m_sasi_req = state; - - if (m_sasi_req) - { - m_sasibus->write_ack(0); - } - - update_trrq_int(); -} - -WRITE_LINE_MEMBER( luxor_4105_device::write_sasi_cd ) -{ - m_sasi_cd = state; -} - - //------------------------------------------------- // device_add_mconfig - add device configuration //------------------------------------------------- void luxor_4105_device::device_add_mconfig(machine_config &config) { - SCSI_PORT(config, m_sasibus); - m_sasibus->set_data_input_buffer(m_sasi_data_in); - m_sasibus->bsy_handler().set(FUNC(luxor_4105_device::write_sasi_bsy)); - m_sasibus->req_handler().set(FUNC(luxor_4105_device::write_sasi_req)); - m_sasibus->cd_handler().set(FUNC(luxor_4105_device::write_sasi_cd)); - m_sasibus->io_handler().set(FUNC(luxor_4105_device::write_sasi_io)); - m_sasibus->set_slot_device(1, "harddisk", S1410, DEVICE_INPUT_DEFAULTS_NAME(SCSI_ID_0)); - - OUTPUT_LATCH(config, m_sasi_data_out); - m_sasibus->set_output_latch(*m_sasi_data_out); - - INPUT_BUFFER(config, m_sasi_data_in); + NSCSI_BUS(config, "sasi"); + NSCSI_CONNECTOR(config, "sasi:0", default_scsi_devices, "s1410"); + NSCSI_CONNECTOR(config, "sasi:7", default_scsi_devices, "scsicb", true) + .option_add_internal("scsicb", NSCSI_CB) + .machine_config([this](device_t* device) { + downcast<nscsi_callback_device&>(*device).cd_callback().set(*this, FUNC(luxor_4105_device::write_sasi_cd)); + downcast<nscsi_callback_device&>(*device).bsy_callback().set(*this, FUNC(luxor_4105_device::write_sasi_bsy)); + downcast<nscsi_callback_device&>(*device).req_callback().set(*this, FUNC(luxor_4105_device::write_sasi_req)); + downcast<nscsi_callback_device&>(*device).msg_callback().set(*this, FUNC(luxor_4105_device::write_sasi_msg)); + downcast<nscsi_callback_device&>(*device).io_callback().set(*this, FUNC(luxor_4105_device::write_sasi_io)); + }); } @@ -126,26 +89,31 @@ void luxor_4105_device::device_add_mconfig(machine_config &config) INPUT_PORTS_START( luxor_4105 ) PORT_START("1E") - PORT_DIPNAME( 0x03, 0x00, "Stepping" ) PORT_DIPLOCATION("1E:1,2") + PORT_DIPNAME( 0x03, 0x03, "Stepping" ) PORT_DIPLOCATION("1E:1,2") PORT_DIPSETTING( 0x00, DEF_STR( Normal ) ) PORT_DIPSETTING( 0x01, "Half (Seagate/Texas)" ) PORT_DIPSETTING( 0x02, "Half (Tandon)" ) PORT_DIPSETTING( 0x03, "Buffered" ) - PORT_DIPNAME( 0x0c, 0x00, "Heads" ) PORT_DIPLOCATION("1E:3,4") + PORT_DIPNAME( 0x0c, 0x04, "Heads" ) PORT_DIPLOCATION("1E:3,4") PORT_DIPSETTING( 0x00, "2" ) PORT_DIPSETTING( 0x04, "4" ) PORT_DIPSETTING( 0x08, "6" ) PORT_DIPSETTING( 0x0c, "8" ) - PORT_DIPNAME( 0xf0, 0x00, "Drive Type" ) PORT_DIPLOCATION("1E:5,6,7,8") + PORT_DIPNAME( 0xf0, 0x30, "Drive Type" ) PORT_DIPLOCATION("1E:5,6,7,8") PORT_DIPSETTING( 0x00, "Seagate ST506" ) PORT_DIPSETTING( 0x10, "Rodime RO100" ) PORT_DIPSETTING( 0x20, "Shugart SA600" ) PORT_DIPSETTING( 0x30, "Seagate ST412" ) PORT_START("5E") - PORT_DIPNAME( 0x7f, 0x25, "Card Address" ) PORT_DIPLOCATION("5E:1,2,3,4,5,6,7") + PORT_DIPNAME( 0x3f, 0x25, "Card Address" ) PORT_DIPLOCATION("5E:1,2,3,4,5,6") PORT_DIPSETTING( 0x25, "37" ) PORT_DIPSETTING( 0x2d, "45" ) + + PORT_START("S1") + PORT_CONFNAME( 0x01, 0x01, "DMA Timing" ) + PORT_CONFSETTING( 0x00, "1043/1044" ) // a. TREN connected via delay circuit to OUT latch enable + PORT_CONFSETTING( 0x01, "1045/1046" ) // b. TREN connected directly to OUT latch enable INPUT_PORTS_END @@ -159,36 +127,6 @@ ioport_constructor luxor_4105_device::device_input_ports() const } -//************************************************************************** -// INLINE HELPERS -//************************************************************************** - -inline void luxor_4105_device::update_trrq_int() -{ - bool cd = !m_sasi_cd; - bool req = !m_sasi_req; - int trrq = (cd & !req) ? 0 : 1; - - if (BIT(m_dma, 5)) - { - m_slot->irq_w(trrq ? CLEAR_LINE : ASSERT_LINE); - } - else - { - m_slot->irq_w(CLEAR_LINE); - } - - if (BIT(m_dma, 6)) - { - m_slot->trrq_w(trrq); - } - else - { - m_slot->trrq_w(1); - } -} - - //************************************************************************** // LIVE DEVICE @@ -201,18 +139,14 @@ inline void luxor_4105_device::update_trrq_int() luxor_4105_device::luxor_4105_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) : device_t(mconfig, LUXOR_4105, tag, owner, clock), device_abcbus_card_interface(mconfig, *this), - m_sasibus(*this, SASIBUS_TAG), - m_sasi_data_out(*this, "sasi_data_out"), - m_sasi_data_in(*this, "sasi_data_in"), + m_sasi(*this, "sasi:7:scsicb"), m_1e(*this, "1E"), m_5e(*this, "5E"), m_cs(false), - m_data(0), m_dma(0), - m_sasi_bsy(false), - m_sasi_req(false), - m_sasi_cd(false), - m_sasi_io(false) + m_pren(1), + m_prac(1), + m_trrq(1) { } @@ -225,8 +159,12 @@ void luxor_4105_device::device_start() { // state saving save_item(NAME(m_cs)); - save_item(NAME(m_data)); + save_item(NAME(m_data_out)); save_item(NAME(m_dma)); + save_item(NAME(m_req)); + save_item(NAME(m_drq)); + save_item(NAME(m_pren)); + save_item(NAME(m_trrq)); } @@ -237,13 +175,165 @@ void luxor_4105_device::device_start() void luxor_4105_device::device_reset() { m_cs = false; - m_data = 0; - m_dma = 0; - m_sasibus->write_rst(1); - m_sasibus->write_rst(0); + internal_reset(); +} + - m_slot->trrq_w(1); +void luxor_4105_device::internal_reset() +{ + write_dma_register(0); + + m_data_out = 0; + + m_sasi->sel_w(0); + + m_sasi->rst_w(1); + m_sasi->rst_w(0); +} + + +void luxor_4105_device::update_dma() +{ + // TRRQ + bool req = m_sasi->req_r() && !m_req; + bool cd = m_sasi->cd_r(); + m_trrq = !(req && !cd); + if (DMA_O2) + { + if (m_prac && !m_trrq) + { + // set REQ FF + m_req = 1; + + update_ack(); + + req = m_sasi->req_r() && !m_req; + m_trrq = !(req && !cd); + } + } + m_slot->trrq_w(DMA_O2 ? m_trrq : 1); + + // DRQ + bool io = m_sasi->io_r(); + m_drq = (!((!cd || !io) && !(!cd && !DMA_O2))) && req; + + // IRQ + bool irq = 1; + if (DMA_O2) + { + if (DMA_O1 && m_drq) + { + irq = 0; + } + } + else if (DMA_O3) + { + irq = 0; + } + m_slot->irq_w(!irq); +} + + +void luxor_4105_device::update_ack() +{ + m_sasi->ack_w(m_sasi->req_r() && (m_sasi->msg_r() || m_req)); +} + + +void luxor_4105_device::write_dma_register(uint8_t data) +{ + /* + + bit description + + 0 + 1 + 2 + 3 + 4 + 5 byte interrupt enable? + 6 DMA/CPU mode (1=DMA, 0=CPU)? + 7 error interrupt enable? + + */ + + m_dma = BIT(data, 5) << 2 | BIT(data, 6) << 1 | BIT(data, 7); + if (LOG) logerror("%s DMA O1 %u O2 %u O3 %u\n", machine().describe_context(), DMA_O1, DMA_O2, DMA_O3); + + // PREN + m_pren = !DMA_O2; + m_slot->pren_w(m_pren); + + update_dma(); +} + + +void luxor_4105_device::write_sasi_data(uint8_t data) +{ + m_data_out = data; + + if (!m_sasi->io_r()) + { + m_sasi->write(data); + } + + // clock REQ FF + m_req = m_sasi->req_r(); + + update_ack(); + update_dma(); +} + + +void luxor_4105_device::write_sasi_bsy(int state) +{ + if (state) + { + m_sasi->sel_w(0); + } +} + + +void luxor_4105_device::write_sasi_cd(int state) +{ + update_dma(); +} + + +void luxor_4105_device::write_sasi_req(int state) +{ + if (LOG) logerror("%s REQ %u\n", machine().describe_context(), state); + + if (!state) + { + // reset REQ FF + m_req = 0; + } + + update_ack(); + update_dma(); +} + + +void luxor_4105_device::write_sasi_msg(int state) +{ + update_ack(); +} + + +void luxor_4105_device::write_sasi_io(int state) +{ + if (state) + { + m_sasi->write(0); + } + else + { + m_sasi->write(m_data_out); + } + + update_dma(); } @@ -281,21 +371,25 @@ uint8_t luxor_4105_device::abcbus_stat() bit description - 0 ? - 1 ? - 2 ? - 3 ? - 4 - 5 - 6 ? (tested at 014D9A, after command 08 sent and 1 byte read from SASI, should be 1) - 7 + 0 REQ + 1 C/D + 2 BSY + 3 I/O + 4 0 + 5 DMA !O3 + 6 PREN + 7 DMA request */ - data = m_sasi_bsy ? 0 : (1 << 0); - data |= m_sasi_req ? 0 : (1 << 2); - data |= m_sasi_cd ? 0 : (1 << 3); - data |= m_sasi_io ? 0 : (1 << 6); + data = m_sasi->req_r() && !m_req; + data |= !m_sasi->cd_r() << 1; + data |= m_sasi->bsy_r() << 2; + data |= !m_sasi->io_r() << 3; + + data |= !DMA_O3 << 5; + data |= !m_pren << 6; + data |= !m_drq << 7; } return data; @@ -312,22 +406,22 @@ uint8_t luxor_4105_device::abcbus_inp() if (m_cs) { - if (!m_sasi_bsy) + if (m_sasi->bsy_r()) { - data = m_1e->read(); + data = m_sasi->read(); } else { - if (m_sasi_io) - { - data = m_sasi_data_in->read(); - - if (m_sasi_req) - { - m_sasibus->write_ack(1); - } - } + data = m_1e->read(); } + + // clock REQ FF + m_req = m_sasi->req_r(); + + update_ack(); + update_dma(); + + if (LOG) logerror("%s INP %02x\n", machine().describe_context(), data); } return data; @@ -342,17 +436,9 @@ void luxor_4105_device::abcbus_out(uint8_t data) { if (m_cs) { - m_data = data; - - if (!m_sasi_io) - { - m_sasi_data_out->write(m_data); + if (LOG) logerror("%s OUT %02x\n", machine().describe_context(), data); - if (m_sasi_req) - { - m_sasibus->write_ack(1); - } - } + write_sasi_data(data); } } @@ -365,7 +451,9 @@ void luxor_4105_device::abcbus_c1(uint8_t data) { if (m_cs) { - m_sasibus->write_sel(1); + if (LOG) logerror("%s SELECT\n", machine().describe_context()); + + m_sasi->sel_w(1); } } @@ -378,11 +466,9 @@ void luxor_4105_device::abcbus_c3(uint8_t data) { if (m_cs) { - m_data = 0; - m_dma = 0; + if (LOG) logerror("%s RESET\n", machine().describe_context()); - m_sasibus->write_rst(1); - m_sasibus->write_rst(0); + internal_reset(); } } @@ -395,23 +481,65 @@ void luxor_4105_device::abcbus_c4(uint8_t data) { if (m_cs) { - /* + if (LOG) logerror("%s DMA %02x\n", machine().describe_context(), data); - bit description + write_dma_register(data); + } +} - 0 - 1 - 2 - 3 - 4 - 5 byte interrupt enable? - 6 DMA/CPU mode (1=DMA, 0=CPU)? - 7 error interrupt enable? - */ +//------------------------------------------------- +// abcbus_tren - +//------------------------------------------------- + +uint8_t luxor_4105_device::abcbus_tren() +{ + uint8_t data = 0xff; + + if (DMA_O2) + { + if (m_sasi->bsy_r()) + { + data = m_sasi->read(); + } + + // clock REQ FF + m_req = m_sasi->req_r(); - m_dma = data; + update_ack(); + update_dma(); - update_trrq_int(); + if (LOG) logerror("%s TREN R %02x\n", machine().describe_context(), data); } + + return data; +} + + +//------------------------------------------------- +// abcbus_tren - +//------------------------------------------------- + +void luxor_4105_device::abcbus_tren(uint8_t data) +{ + if (DMA_O2) + { + if (LOG) logerror("%s TREN W %02x\n", machine().describe_context(), data); + + write_sasi_data(data); + } +} + + +//------------------------------------------------- +// abcbus_prac - +//------------------------------------------------- + +void luxor_4105_device::abcbus_prac(int state) +{ + if (LOG) logerror("%s PRAC %u\n", machine().describe_context(), state); + + m_prac = state; + + update_dma(); } |