diff --git a/src/emu/machine/ctronics.h b/src/emu/machine/ctronics.h index 1f55977c348..a4540ebf19b 100644 --- a/src/emu/machine/ctronics.h +++ b/src/emu/machine/ctronics.h @@ -63,8 +63,10 @@ public: centronics_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); virtual ~centronics_device(); - DECLARE_WRITE8_MEMBER( write ) { if (m_dev) m_dev->write(data); } - DECLARE_READ8_MEMBER( read ) { return (m_dev) ? m_dev->read() : 0x00; } + void write(UINT8 data) { if (m_dev) m_dev->write(data); } + DECLARE_WRITE8_MEMBER( write ) { write(data); } + UINT8 read() { return (m_dev) ? m_dev->read() : 0x00; } + DECLARE_READ8_MEMBER( read ) { return read(); } /* access to the individual bits */ DECLARE_WRITE_LINE_MEMBER( d0_w ) { if (m_dev) m_dev->set_line(0, state); } diff --git a/src/mess/drivers/bw2.c b/src/mess/drivers/bw2.c index f5b575b7a1a..e067de7a3a9 100644 --- a/src/mess/drivers/bw2.c +++ b/src/mess/drivers/bw2.c @@ -409,8 +409,8 @@ WRITE8_MEMBER( bw2_state::ppi_pa_w ) // drive select m_floppy = NULL; - if (BIT(data, 4)) m_floppy = m_floppy0->get_device(); - if (BIT(data, 5)) m_floppy = m_floppy1->get_device(); + if (!BIT(data, 4)) m_floppy = m_floppy0->get_device(); + if (!BIT(data, 5)) m_floppy = m_floppy1->get_device(); m_fdc->set_floppy(m_floppy); if (m_floppy) m_floppy->mon_w(m_mtron); diff --git a/src/mess/drivers/v1050.c b/src/mess/drivers/v1050.c index b597c86a8ba..1557909621b 100644 --- a/src/mess/drivers/v1050.c +++ b/src/mess/drivers/v1050.c @@ -463,7 +463,7 @@ static ADDRESS_MAP_START( v1050_io, AS_IO, 8, v1050_state ) AM_RANGE(0x8c, 0x8c) AM_DEVREADWRITE(I8251A_SIO_TAG, i8251_device, data_r, data_w) AM_RANGE(0x8d, 0x8d) AM_DEVREADWRITE(I8251A_SIO_TAG, i8251_device, status_r, control_w) AM_RANGE(0x90, 0x93) AM_DEVREADWRITE(I8255A_MISC_TAG, i8255_device, read, write) - AM_RANGE(0x94, 0x97) AM_DEVREADWRITE_LEGACY(MB8877_TAG, wd17xx_r, wd17xx_w) + AM_RANGE(0x94, 0x97) AM_DEVREADWRITE(MB8877_TAG, fd1793_t, read, write) AM_RANGE(0x9c, 0x9f) AM_DEVREADWRITE(I8255A_RTC_TAG, i8255_device, read, write) AM_RANGE(0xa0, 0xa0) AM_READWRITE(vint_clr_r, vint_clr_w) AM_RANGE(0xb0, 0xb0) AM_READWRITE(dint_clr_r, dint_clr_w) @@ -697,31 +697,29 @@ WRITE8_MEMBER( v1050_state::misc_ppi_pa_w ) */ - int f_motor_on = !BIT(data, 6); - // floppy drive select - if (!BIT(data, 0)) wd17xx_set_drive(m_fdc, 0); - if (!BIT(data, 1)) wd17xx_set_drive(m_fdc, 1); - if (!BIT(data, 2)) wd17xx_set_drive(m_fdc, 2); - if (!BIT(data, 3)) wd17xx_set_drive(m_fdc, 3); + floppy_image_device *floppy = NULL; + + if (!BIT(data, 0)) floppy = m_floppy0->get_device(); + if (!BIT(data, 1)) floppy = m_floppy1->get_device(); + if (!BIT(data, 2)) floppy = m_floppy2->get_device(); + if (!BIT(data, 3)) floppy = m_floppy3->get_device(); + + m_fdc->set_floppy(floppy); // floppy side select - wd17xx_set_side(m_fdc, BIT(data, 4)); + if (floppy) floppy->ss_w(BIT(data, 4)); // floppy motor - floppy_mon_w(m_floppy0, BIT(data, 6)); - floppy_mon_w(m_floppy1, BIT(data, 6)); - floppy_drive_set_ready_state(m_floppy0, f_motor_on, 1); - floppy_drive_set_ready_state(m_floppy1, f_motor_on, 1); + if (floppy) floppy->mon_w(BIT(data, 6)); // density select - wd17xx_dden_w(m_fdc, BIT(data, 7)); + m_fdc->dden_w(BIT(data, 7)); } WRITE8_MEMBER(v1050_state::misc_ppi_pb_w) { - centronics_device *centronics = machine().device(CENTRONICS_TAG); - centronics->write( machine().driver_data()->generic_space() , 0, ~data & 0xff); + m_centronics->write(~data & 0xff); } READ8_MEMBER(v1050_state::misc_ppi_pc_r) @@ -742,9 +740,9 @@ READ8_MEMBER(v1050_state::misc_ppi_pc_r) */ UINT8 data = 0; - centronics_device *centronics = machine().device(CENTRONICS_TAG); - data |= centronics->not_busy_r() << 4; - data |= centronics->pe_r() << 5; + + data |= m_centronics->not_busy_r() << 4; + data |= m_centronics->pe_r() << 5; return data; } @@ -922,14 +920,14 @@ WRITE_LINE_MEMBER( v1050_state::sio_rxrdy_w ) { m_rxrdy = state; - set_interrupt(INT_RS_232, m_rxrdy | m_txrdy); + set_interrupt(INT_RS_232, m_rxrdy || m_txrdy); } WRITE_LINE_MEMBER( v1050_state::sio_txrdy_w ) { m_txrdy = state; - set_interrupt(INT_RS_232, m_rxrdy | m_txrdy); + set_interrupt(INT_RS_232, m_rxrdy || m_txrdy); } static const i8251_interface sio_8251_intf = @@ -947,11 +945,15 @@ static const i8251_interface sio_8251_intf = // MB8877 Interface -WRITE_LINE_MEMBER( v1050_state::fdc_intrq_w ) +static SLOT_INTERFACE_START( v1050_floppies ) + SLOT_INTERFACE( "525dd", FLOPPY_525_DD ) // Teac FD-55F +SLOT_INTERFACE_END + +void v1050_state::fdc_intrq_w(bool state) { if (m_f_int_enb) { - set_interrupt(INT_FLOPPY, state); + set_interrupt(INT_FLOPPY, state ? 1 : 0); } else { @@ -959,11 +961,11 @@ WRITE_LINE_MEMBER( v1050_state::fdc_intrq_w ) } } -WRITE_LINE_MEMBER( v1050_state::fdc_drq_w ) +void v1050_state::fdc_drq_w(bool state) { if (m_f_int_enb) { - m_maincpu->set_input_line(INPUT_LINE_NMI, state); + m_maincpu->set_input_line(INPUT_LINE_NMI, state ? ASSERT_LINE : CLEAR_LINE); } else { @@ -971,14 +973,7 @@ WRITE_LINE_MEMBER( v1050_state::fdc_drq_w ) } } -static const wd17xx_interface fdc_intf = -{ - DEVCB_NULL, - DEVCB_DRIVER_LINE_MEMBER(v1050_state, fdc_intrq_w), - DEVCB_DRIVER_LINE_MEMBER(v1050_state, fdc_drq_w), - { FLOPPY_0, FLOPPY_1, NULL, NULL } -}; - +/* static LEGACY_FLOPPY_OPTIONS_START( v1050 ) LEGACY_FLOPPY_OPTION( v1050, "dsk", "Visual 1050 disk image", basicdsk_identify_default, basicdsk_construct_default, NULL, HEADS([1]) @@ -987,20 +982,7 @@ static LEGACY_FLOPPY_OPTIONS_START( v1050 ) SECTOR_LENGTH([512]) FIRST_SECTOR_ID([1])) LEGACY_FLOPPY_OPTIONS_END - -static const floppy_interface v1050_floppy_interface = -{ - DEVCB_NULL, - DEVCB_NULL, - DEVCB_NULL, - DEVCB_NULL, - DEVCB_NULL, - FLOPPY_STANDARD_5_25_DSHD, - LEGACY_FLOPPY_OPTIONS_NAME(v1050), - "floppy_5_25", - NULL -}; - +*/ // Machine Initialization @@ -1021,6 +1003,10 @@ void v1050_state::machine_start() { address_space &program = m_maincpu->space(AS_PROGRAM); + // floppy callbacks + m_fdc->setup_intrq_cb(fd1793_t::line_cb(FUNC(v1050_state::fdc_intrq_w), this)); + m_fdc->setup_drq_cb(fd1793_t::line_cb(FUNC(v1050_state::fdc_drq_w), this)); + // initialize I8214 m_pic->etlg_w(1); m_pic->inte_w(1); @@ -1103,8 +1089,11 @@ static MACHINE_CONFIG_START( v1050, v1050_state ) MCFG_I8255A_ADD(I8255A_M6502_TAG, m6502_ppi_intf) MCFG_I8251_ADD(I8251A_KB_TAG, /*XTAL_16MHz/8,*/ kb_8251_intf) MCFG_I8251_ADD(I8251A_SIO_TAG, /*XTAL_16MHz/8,*/ sio_8251_intf) - MCFG_MB8877_ADD(MB8877_TAG, /*XTAL_16MHz/16,*/ fdc_intf ) - MCFG_LEGACY_FLOPPY_2_DRIVES_ADD(v1050_floppy_interface) + MCFG_FD1793x_ADD(MB8877_TAG, XTAL_16MHz/16) + MCFG_FLOPPY_DRIVE_ADD(MB8877_TAG":0", v1050_floppies, "525dd", NULL, floppy_image_device::default_floppy_formats) + MCFG_FLOPPY_DRIVE_ADD(MB8877_TAG":1", v1050_floppies, "525dd", NULL, floppy_image_device::default_floppy_formats) + MCFG_FLOPPY_DRIVE_ADD(MB8877_TAG":2", v1050_floppies, NULL, NULL, floppy_image_device::default_floppy_formats) + MCFG_FLOPPY_DRIVE_ADD(MB8877_TAG":3", v1050_floppies, NULL, NULL, floppy_image_device::default_floppy_formats) MCFG_TIMER_DRIVER_ADD_PERIODIC(TIMER_KB_TAG, v1050_state, kb_8251_tick, attotime::from_hz((double)XTAL_16MHz/4/13/8)) MCFG_TIMER_DRIVER_ADD(TIMER_SIO_TAG, v1050_state, sio_8251_tick) diff --git a/src/mess/includes/v1050.h b/src/mess/includes/v1050.h index 90c008b74b2..095ff864d95 100644 --- a/src/mess/includes/v1050.h +++ b/src/mess/includes/v1050.h @@ -17,7 +17,7 @@ #include "machine/ram.h" #include "machine/scsicb.h" #include "machine/v1050kb.h" -#include "machine/wd17xx.h" +#include "machine/wd1772.h" #include "video/mc6845.h" #define SCREEN_TAG "screen" @@ -69,14 +69,16 @@ public: m_crtc(*this, H46505_TAG), m_centronics(*this, CENTRONICS_TAG), m_ram(*this, RAM_TAG), - m_floppy0(*this, FLOPPY_0), - m_floppy1(*this, FLOPPY_1), + m_floppy0(*this, MB8877_TAG":0"), + m_floppy1(*this, MB8877_TAG":1"), + m_floppy2(*this, MB8877_TAG":2"), + m_floppy3(*this, MB8877_TAG":3"), m_timer_sio(*this, TIMER_SIO_TAG), m_timer_ack(*this, TIMER_ACK_TAG), m_timer_rst(*this, TIMER_RST_TAG), - m_sasibus(*this, SASIBUS_TAG ":host") - , - m_video_ram(*this, "video_ram"){ } + m_sasibus(*this, SASIBUS_TAG ":host"), + m_video_ram(*this, "video_ram") + { } required_device m_maincpu; required_device m_subcpu; @@ -84,12 +86,14 @@ public: required_device m_rtc; required_device m_uart_kb; required_device m_uart_sio; - required_device m_fdc; + required_device m_fdc; required_device m_crtc; required_device m_centronics; required_device m_ram; - required_device m_floppy0; - required_device m_floppy1; + required_device m_floppy0; + required_device m_floppy1; + required_device m_floppy2; + required_device m_floppy3; required_device m_timer_sio; required_device m_timer_ack; required_device m_timer_rst; @@ -121,8 +125,8 @@ public: DECLARE_WRITE_LINE_MEMBER( kb_rxrdy_w ); DECLARE_WRITE_LINE_MEMBER( sio_rxrdy_w ); DECLARE_WRITE_LINE_MEMBER( sio_txrdy_w ); - DECLARE_WRITE_LINE_MEMBER( fdc_intrq_w ); - DECLARE_WRITE_LINE_MEMBER( fdc_drq_w ); + void fdc_intrq_w(bool state); + void fdc_drq_w(bool state); DECLARE_READ8_MEMBER( attr_r ); DECLARE_WRITE8_MEMBER( attr_w ); DECLARE_READ8_MEMBER( videoram_r ); diff --git a/src/mess/machine/wd1772.c b/src/mess/machine/wd1772.c index a88cf96ef85..ccc182d8db3 100644 --- a/src/mess/machine/wd1772.c +++ b/src/mess/machine/wd1772.c @@ -40,6 +40,7 @@ const device_type WD1772x = &device_creator; const device_type WD1773x = &device_creator; const device_type WD2793x = &device_creator; const device_type WD2797x = &device_creator; +const device_type FD1793x = &device_creator; wd177x_t::wd177x_t(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock) : device_t(mconfig, type, name, tag, owner, clock) @@ -61,6 +62,7 @@ void wd177x_t::device_start() save_item(NAME(sub_state)); save_item(NAME(track)); save_item(NAME(sector)); + save_item(NAME(intrq_cond)); save_item(NAME(cmd_buffer)); save_item(NAME(track_buffer)); save_item(NAME(sector_buffer)); @@ -85,6 +87,7 @@ void wd177x_t::device_reset() last_dir = 1; intrq = false; drq = false; + hld = false; live_abort(); } @@ -117,6 +120,16 @@ void wd177x_t::setup_drq_cb(line_cb cb) drq_cb = cb; } +void wd177x_t::setup_hld_cb(line_cb cb) +{ + hld_cb = cb; +} + +void wd177x_t::setup_enp_cb(line_cb cb) +{ + enp_cb = cb; +} + void wd177x_t::dden_w(bool _dden) { dden = _dden; @@ -163,6 +176,13 @@ void wd177x_t::seek_start(int state) { main_state = state; status = (status & ~(S_CRC|S_RNF|S_SPIN)) | S_BUSY; + if(has_head_load()) { + // TODO get value from HLT callback + if (command & 8) + status |= S_HLD; + else + status &= ~S_HLD; + } sub_state = has_motor() ? SPINUP : SPINUP_DONE; status_type_1 = true; seek_continue(); @@ -295,7 +315,7 @@ bool wd177x_t::sector_matches() const { if(cur_live.idbuf[0] != track || cur_live.idbuf[2] != sector) return false; - if(!has_side_check()) + if(!has_side_check() || (command & 2)) return true; if(command & 8) return cur_live.idbuf[1] & 1; @@ -303,8 +323,16 @@ bool wd177x_t::sector_matches() const return !(cur_live.idbuf[1] & 1); } +bool wd177x_t::is_ready() +{ + return (floppy && !floppy->ready_r()); +} + void wd177x_t::read_sector_start() { + if(has_ready() && !is_ready()) + command_end(); + main_state = READ_SECTOR; status = (status & ~(S_CRC|S_LOST|S_RNF|S_WP|S_DDM)) | S_BUSY; drop_drq(); @@ -359,6 +387,7 @@ void wd177x_t::read_sector_continue() live_start(SEARCH_ADDRESS_MARK_HEADER); return; } + // TODO WD2795/7 alternate sector size sector_size = 128 << (cur_live.idbuf[3] & 3); sub_state = SECTOR_READ; live_start(SEARCH_ADDRESS_MARK_DATA); @@ -391,6 +420,9 @@ void wd177x_t::read_sector_continue() void wd177x_t::read_track_start() { + if(has_ready() && !is_ready()) + command_end(); + main_state = READ_TRACK; status = (status & ~(S_LOST|S_RNF)) | S_BUSY; drop_drq(); @@ -455,6 +487,9 @@ void wd177x_t::read_track_continue() void wd177x_t::read_id_start() { + if(has_ready() && !is_ready()) + command_end(); + main_state = READ_ID; status = (status & ~(S_WP|S_DDM|S_LOST|S_RNF)) | S_BUSY; drop_drq(); @@ -517,6 +552,9 @@ void wd177x_t::read_id_continue() void wd177x_t::write_track_start() { + if(has_ready() && !is_ready()) + command_end(); + main_state = WRITE_TRACK; status = (status & ~(S_WP|S_DDM|S_LOST|S_RNF)) | S_BUSY; drop_drq(); @@ -596,6 +634,9 @@ void wd177x_t::write_track_continue() void wd177x_t::write_sector_start() { + if(has_ready() && !is_ready()) + command_end(); + main_state = WRITE_SECTOR; status = (status & ~(S_CRC|S_LOST|S_RNF|S_WP|S_DDM)) | S_BUSY; drop_drq(); @@ -650,6 +691,7 @@ void wd177x_t::write_sector_continue() live_start(SEARCH_ADDRESS_MARK_HEADER); return; } + // TODO WD2795/7 alternate sector size sector_size = 128 << (cur_live.idbuf[3] & 3); sub_state = SECTOR_WRITE; live_start(WRITE_SECTOR_PRE); @@ -686,12 +728,20 @@ void wd177x_t::interrupt_start() drop_drq(); motor_timeout = 0; } - if(command & 0x08) { + + if(!(command & 0x0f)) { + intrq_cond = 0; + } else { + intrq_cond = (intrq_cond & I_IMM) | (command & 0x07); + } + + if(intrq_cond & I_IMM) { intrq = true; if(!intrq_cb.isnull()) intrq_cb(intrq); } - if(command & 0x07) { + + if(command & 0x03) { logerror("%s: unhandled interrupt generation (%02x)\n", ttsn().cstr(), command); } } @@ -791,7 +841,9 @@ void wd177x_t::do_cmd_w() void wd177x_t::cmd_w(UINT8 val) { - if(intrq && ((command & 0xf8) != 0xd8)) { + logerror("wd1772 cmd: %02x\n", val); + + if(intrq && !(intrq_cond & I_IMM)) { intrq = false; if(!intrq_cb.isnull()) intrq_cb(intrq); @@ -808,22 +860,12 @@ void wd177x_t::cmd_w(UINT8 val) UINT8 wd177x_t::status_r() { - if(intrq && ((command & 0xf8) != 0xd8)) { + if(intrq && !(intrq_cond & I_IMM)) { intrq = false; if(!intrq_cb.isnull()) intrq_cb(intrq); } - if(status_type_1) { - status &= ~(S_TR00|S_WP); - if(floppy) { - if(floppy->wpt_r()) - status |= S_WP; - if(!floppy->trk00_r()) - status |= S_TR00; - } - } - if(main_state == IDLE || status_type_1) { if(floppy && floppy->idx_r()) status |= S_IP; @@ -836,6 +878,23 @@ UINT8 wd177x_t::status_r() status &= ~S_DRQ; } + if(status_type_1) { + status &= ~(S_TR00|S_WP); + if(floppy) { + if(floppy->wpt_r()) + status |= S_WP; + if(!floppy->trk00_r()) + status |= S_TR00; + } + } + + if(has_ready()) { + if(!is_ready()) + status |= S_NRDY; + else + status &= ~S_NRDY; + } + return status; } @@ -943,6 +1002,12 @@ void wd177x_t::index_callback(floppy_image_device *floppy, int state) return; } + if(intrq_cond & I_IDX) { + intrq = true; + if(!intrq_cb.isnull()) + intrq_cb(intrq); + } + switch(sub_state) { case IDLE: if(has_motor()) { @@ -1018,6 +1083,21 @@ bool wd177x_t::drq_r() return drq; } +bool wd177x_t::hld_r() +{ + return hld; +} + +void wd177x_t::hlt_w(bool state) +{ + hlt = state; +} + +bool wd177x_t::enp_r() +{ + return enp; +} + void wd177x_t::live_start(int state) { cur_live.tm = machine().time(); @@ -1747,6 +1827,16 @@ int wd177x_t::settle_time() const return 240000; } +bool wd177x_t::has_ready() const +{ + return false; +} + +bool wd177x_t::has_head_load() const +{ + return false; +} + bool wd177x_t::has_side_check() const { return false; @@ -1757,24 +1847,24 @@ bool wd177x_t::has_side_select() const return false; } +bool wd177x_t::has_sector_length_select() const +{ + return false; +} + +bool wd177x_t::has_precompensation() const +{ + return false; +} + wd1770_t::wd1770_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) : wd177x_t(mconfig, WD1770x, "WD1770", tag, owner, clock) { } -bool wd1770_t::has_motor() const -{ - return true; -} - wd1772_t::wd1772_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) : wd177x_t(mconfig, WD1772x, "WD1772", tag, owner, clock) { } -bool wd1772_t::has_motor() const -{ - return true; -} - int wd1772_t::step_time(int mode) const { const static int step_times[4] = { 48000, 96000, 16000, 24000 }; @@ -1790,45 +1880,14 @@ wd1773_t::wd1773_t(const machine_config &mconfig, const char *tag, device_t *own { } -bool wd1773_t::has_motor() const -{ - return false; -} - -bool wd1773_t::has_side_check() const -{ - return false; -} - wd2793_t::wd2793_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) : wd177x_t(mconfig, WD2793x, "WD2793", tag, owner, clock) { } -bool wd2793_t::has_motor() const -{ - return false; -} - -bool wd2793_t::has_side_check() const -{ - return true; -} - wd2797_t::wd2797_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) : wd177x_t(mconfig, WD2797x, "WD2797", tag, owner, clock) { } -bool wd2797_t::has_motor() const +fd1793_t::fd1793_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock) : wd177x_t(mconfig, FD1793x, "FD1793", tag, owner, clock) { - return false; -} - -bool wd2797_t::has_side_check() const -{ - return false; -} - -bool wd2797_t::has_side_select() const -{ - return true; } diff --git a/src/mess/machine/wd1772.h b/src/mess/machine/wd1772.h index 8a27ea60cb7..b530ca1212b 100644 --- a/src/mess/machine/wd1772.h +++ b/src/mess/machine/wd1772.h @@ -19,6 +19,9 @@ #define MCFG_WD2797x_ADD(_tag, _clock) \ MCFG_DEVICE_ADD(_tag, WD2797x, _clock) +#define MCFG_FD1793x_ADD(_tag, _clock) \ + MCFG_DEVICE_ADD(_tag, FD1793x, _clock) + class wd177x_t : public device_t { public: typedef delegate line_cb; @@ -29,6 +32,8 @@ public: void set_floppy(floppy_image_device *floppy); void setup_intrq_cb(line_cb cb); void setup_drq_cb(line_cb cb); + void setup_hld_cb(line_cb cb); + void setup_enp_cb(line_cb cb); void cmd_w(UINT8 val); UINT8 status_r(); @@ -52,21 +57,29 @@ public: void gen_w(int reg, UINT8 val); UINT8 gen_r(int reg); + DECLARE_READ8_MEMBER( read ) { return gen_r(offset);} + DECLARE_WRITE8_MEMBER( write ) { gen_w(offset,data); } bool intrq_r(); bool drq_r(); - DECLARE_READ8_MEMBER( read ) { return gen_r(offset);} - DECLARE_WRITE8_MEMBER( write ) { gen_w(offset,data); } + bool hld_r(); + void hlt_w(bool state); + + bool enp_r(); protected: virtual void device_start(); virtual void device_reset(); virtual void device_timer(emu_timer &timer, device_timer_id id, int param, void *ptr); + virtual bool has_ready() const; virtual bool has_motor() const = 0; + virtual bool has_head_load() const; virtual bool has_side_check() const; virtual bool has_side_select() const; + virtual bool has_sector_length_select() const; + virtual bool has_precompensation() const; virtual int step_time(int mode) const; virtual int settle_time() const; @@ -223,19 +236,29 @@ private: S_LOST = 0x04, S_CRC = 0x08, S_RNF = 0x10, - S_SPIN = 0x20, + S_HLD = 0x20, + S_SPIN = 0x20, // WD1770, WD1772 S_DDM = 0x20, + S_WF = 0x20, // WD1773 S_WP = 0x40, - S_MON = 0x80 + S_NRDY = 0x80, + S_MON = 0x80 // WD1770, WD1772 + }; + + enum { + I_RDY = 0x01, + I_NRDY = 0x02, + I_IDX = 0x04, + I_IMM = 0x08 }; floppy_image_device *floppy; emu_timer *t_gen, *t_cmd, *t_track, *t_sector; - bool dden, status_type_1, intrq, drq; + bool dden, status_type_1, intrq, drq, hld, hlt, enp; int main_state, sub_state; - UINT8 command, track, sector, data, status; + UINT8 command, track, sector, data, status, intrq_cond; int last_dir; int counter, motor_timeout, sector_size; @@ -243,7 +266,7 @@ private: int cmd_buffer, track_buffer, sector_buffer; live_info cur_live, checkpoint_live; - line_cb intrq_cb, drq_cb; + line_cb intrq_cb, drq_cb, hld_cb, enp_cb; static astring tts(attotime t); astring ttsn(); @@ -284,6 +307,7 @@ private: void spinup(); void index_callback(floppy_image_device *floppy, int state); bool sector_matches() const; + bool is_ready(); void live_start(int live_state); void live_abort(); @@ -307,7 +331,8 @@ public: wd1770_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); protected: - virtual bool has_motor() const; + virtual bool has_motor() const { return true; } + virtual bool has_precompensation() const { return true; } }; class wd1772_t : public wd177x_t { @@ -315,7 +340,8 @@ public: wd1772_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); protected: - virtual bool has_motor() const; + virtual bool has_motor() const { return true; } + virtual bool has_precompensation() const { return true; } virtual int step_time(int mode) const; virtual int settle_time() const; }; @@ -325,8 +351,9 @@ public: wd1773_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); protected: - virtual bool has_motor() const; - virtual bool has_side_check() const; + virtual bool has_motor() const { return false; } + virtual bool has_head_load() const { return true; } + virtual bool has_side_check() const { return true; } }; class wd2793_t : public wd177x_t { @@ -334,8 +361,10 @@ public: wd2793_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); protected: - virtual bool has_motor() const; - virtual bool has_side_check() const; + virtual bool has_ready() const { return true; } + virtual bool has_motor() const { return false; } + virtual bool has_head_load() const { return true; } + virtual bool has_side_check() const { return true; } }; class wd2797_t : public wd177x_t { @@ -343,9 +372,22 @@ public: wd2797_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); protected: - virtual bool has_motor() const; - virtual bool has_side_check() const; - virtual bool has_side_select() const; + virtual bool has_ready() const { return true; } + virtual bool has_motor() const { return false; } + virtual bool has_head_load() const { return true; } + virtual bool has_side_select() const { return true; } + virtual bool has_sector_length_select() const { return true; } +}; + +class fd1793_t : public wd177x_t { +public: + fd1793_t(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock); + +protected: + virtual bool has_ready() const { return true; } + virtual bool has_motor() const { return false; } + virtual bool has_head_load() const { return true; } + virtual bool has_side_check() const { return true; } }; extern const device_type WD1770x; @@ -353,5 +395,6 @@ extern const device_type WD1772x; extern const device_type WD1773x; extern const device_type WD2793x; extern const device_type WD2797x; +extern const device_type FD1793x; #endif