From ffe5c0772c036b037a688826fd6d0307005a8949 Mon Sep 17 00:00:00 2001 From: 68bit Date: Fri, 8 Nov 2019 11:08:20 +1100 Subject: [PATCH] swtpc, swtpc09: save state, port change, cleanups --- src/mame/drivers/swtpc.cpp | 21 ++++-- src/mame/drivers/swtpc09.cpp | 34 ++++----- src/mame/includes/swtpc09.h | 20 +++--- src/mame/machine/swtpc09.cpp | 132 +++++++++++++++++++++-------------- 4 files changed, 124 insertions(+), 83 deletions(-) diff --git a/src/mame/drivers/swtpc.cpp b/src/mame/drivers/swtpc.cpp index a1ca20ecef5..fc00330f8c0 100644 --- a/src/mame/drivers/swtpc.cpp +++ b/src/mame/drivers/swtpc.cpp @@ -109,14 +109,16 @@ public: , m_maincpu(*this, "maincpu") , m_ram(*this, "ram") , m_brg(*this, "brg") - , m_maincpu_clock(*this, "maincpu_clock") - , m_swtbug_ready_wait(*this, "swtbug_ready_wait") - , m_swtbug_load_at_a100(*this, "swtbug_load_at_a100") + , m_maincpu_clock(*this, "MAINCPU_CLOCK") + , m_swtbug_ready_wait(*this, "SWTBUG_READY_WAIT") + , m_swtbug_load_at_a100(*this, "SWTBUG_LOAD_AT_A100") { } void swtpcm(machine_config &config); void swtpc(machine_config &config); + DECLARE_INPUT_CHANGED_MEMBER(maincpu_clock_change); + private: virtual void machine_reset() override; virtual void machine_start() override; @@ -158,8 +160,8 @@ static INPUT_PORTS_START( swtpc ) // the CPU clock and the frequency was variable. The 6800 was // available at speeds up to 2MHz so that might not have been // impossible. An overclock option of 4MHz is also implemented. - PORT_START("maincpu_clock") - PORT_CONFNAME(0xffffff, 1000000, "CPU clock") + PORT_START("MAINCPU_CLOCK") + PORT_CONFNAME(0xffffff, 1000000, "CPU clock") PORT_CHANGED_MEMBER(DEVICE_SELF, swtpc_state, maincpu_clock_change, 0) PORT_CONFSETTING( 898550, "0.89855 MHz") // MIKBUG PORT_CONFSETTING( 921600, "0.92160 MHz") // SWTPC PORT_CONFSETTING(1000000, "1.0 MHz") @@ -172,7 +174,7 @@ static INPUT_PORTS_START( swtpc ) // the motor when accessing the control register, the drive does not // have time to become ready before commands are issued and the boot // fails. This workaround is necessary in practice. - PORT_START("swtbug_ready_wait") + PORT_START("SWTBUG_READY_WAIT") PORT_CONFNAME(0x1, 1, "SWTBUG ready wait patch") PORT_CONFSETTING(0, "No") PORT_CONFSETTING(1, "Yes - apply patch") @@ -184,7 +186,7 @@ static INPUT_PORTS_START( swtpc ) // 0xa100 or perhaps better implement support for the high PROM to // allow custom code to be used which is needed anyway as even NEWBUG // appears to have issues and is not optimized for the DC5 FDC. - PORT_START("swtbug_load_at_a100") + PORT_START("SWTBUG_LOAD_AT_A100") PORT_CONFNAME(0x1, 1, "SWTBUG disk boot patch, to load at 0xa100") PORT_CONFSETTING(0, "No") PORT_CONFSETTING(1, "Yes - apply patch") @@ -195,6 +197,11 @@ static DEVICE_INPUT_DEFAULTS_START( dc5 ) DEVICE_INPUT_DEFAULTS("address_mode", 0xf, 0) DEVICE_INPUT_DEFAULTS_END +INPUT_CHANGED_MEMBER(swtpc_state::maincpu_clock_change) +{ + m_maincpu->set_clock(newval); +} + void swtpc_state::machine_reset() { uint32_t maincpu_clock = m_maincpu_clock->read(); diff --git a/src/mame/drivers/swtpc09.cpp b/src/mame/drivers/swtpc09.cpp index 6b7b85ba262..32f7a8044ff 100644 --- a/src/mame/drivers/swtpc09.cpp +++ b/src/mame/drivers/swtpc09.cpp @@ -206,8 +206,8 @@ static INPUT_PORTS_START( swtpc09 ) // Run the 6809 at 2MHz (an 8MHz XTAL) so that manual polling of FDC can // keep up with higher rate operation. The MPU09 did have the option of // 1MHz or 2MHz operation. - PORT_START("maincpu_clock") - PORT_CONFNAME(0xffffff, 2000000, "CPU clock") + PORT_START("MAINCPU_CLOCK") + PORT_CONFNAME(0xffffff, 2000000, "CPU clock") PORT_CHANGED_MEMBER(DEVICE_SELF, swtpc09_state, maincpu_clock_change, 0) PORT_CONFSETTING(1000000, "1.0 MHz") PORT_CONFSETTING(2000000, "2.0 MHz") PORT_CONFSETTING(4000000, "4.0 MHz") @@ -219,20 +219,20 @@ static INPUT_PORTS_START( swtpc09 ) // 'standard' 3.5" - 1.2MHz // 3.5" hd - 2.0MHz // 8" 360rpm - 2.4MHz - PORT_START("fdc_clock") - PORT_DIPNAME(0xffffff, 2000000, "DMAF2/3 FDC clock") - PORT_DIPSETTING(1000000, "1.0 MHz") - PORT_DIPSETTING(1200000, "1.2 MHz") - PORT_DIPSETTING(2000000, "2.0 MHz") - PORT_DIPSETTING(2400000, "2.4 MHz") + PORT_START("FDC_CLOCK") + PORT_CONFNAME(0xffffff, 2000000, "DMAF2/3 FDC clock") PORT_CHANGED_MEMBER(DEVICE_SELF, swtpc09_state, fdc_clock_change, 0) + PORT_CONFSETTING(1000000, "1.0 MHz") + PORT_CONFSETTING(1200000, "1.2 MHz") + PORT_CONFSETTING(2000000, "2.0 MHz") + PORT_CONFSETTING(2400000, "2.4 MHz") // The MP-ID board has jumpers to vary the baud rates generated. The // most useful is the Low/High rate jumper that provide a four times // rate increase. - PORT_START("baud_rate_high") - PORT_DIPNAME(0x1, 0, "High baud rate") - PORT_DIPSETTING(0, "Low (x1)") - PORT_DIPSETTING(1, "High (x4)") + PORT_START("BAUD_RATE_HIGH") + PORT_CONFNAME(0x1, 0, "High baud rate") PORT_CHANGED_MEMBER(DEVICE_SELF, swtpc09_state, baud_rate_high_change, 0) + PORT_CONFSETTING(0, "Low (x1)") + PORT_CONFSETTING(1, "High (x4)") // Debug aid to hard code the density. The FLEX format uses single // density for track zero. Many virtual disks 'fix' the format to be @@ -240,7 +240,7 @@ static INPUT_PORTS_START( swtpc09 ) // driver support for that. This setting is an aid to report // unexpected usage, and it attempts to correct that. It is possible // to patch the software to work with these pure double density disks. - PORT_START("floppy_expected_density") + PORT_START("FLOPPY_EXPECTED_DENSITY") PORT_CONFNAME(0xff, 0, "DMAF2/3 expected density") PORT_CONFSETTING(0, "-") PORT_CONFSETTING(1, "single density") @@ -259,7 +259,7 @@ static INPUT_PORTS_START( swtpc09 ) // the head based track zero being single density. This aid is not // intended to be a substitute for fixing the drivers but it does help // work through the issues while patching the disks. - PORT_START("floppy_expected_sectors") + PORT_START("FLOPPY_EXPECTED_SECTORS") PORT_CONFNAME(0xff, 0, "DMAF2/3 expected sectors per side") PORT_CONFSETTING(0, "-") PORT_CONFSETTING(10, "10") // 5 1/4" single density 256B @@ -271,7 +271,7 @@ static INPUT_PORTS_START( swtpc09 ) // 6800 disks did format track zero in single density and if the // driver sticks to that and if using a double density disk then set a // single density size here. - PORT_START("floppy_track_zero_expected_sectors") + PORT_START("FLOPPY_TRACK_ZERO_EXPECTED_SECTORS") PORT_CONFNAME(0xff, 0, "DMAF2/3 track zero expected sectors per side") PORT_CONFSETTING(0, "-") PORT_CONFSETTING(10, "10") // 5 1/4" single density 256B @@ -280,7 +280,7 @@ static INPUT_PORTS_START( swtpc09 ) PORT_CONFSETTING(26, "26") // 8" double density 256B PORT_CONFSETTING(36, "36") // 3.5" 1.4M QD 256B - PORT_START("sbug_double_density") + PORT_START("SBUG_DOUBLE_DENSITY") PORT_CONFNAME(0x1, 0, "SBUG patch for double density (SSO) disk boot") PORT_CONFSETTING(0, "No - single density") PORT_CONFSETTING(1, "Yes - double density") @@ -289,7 +289,7 @@ static INPUT_PORTS_START( swtpc09 ) // after the disk boot code has loaded FLEX, and then it jumps to // 0xc850 to cold start FLEX. Have seen 0xcd00 being the cold start // address, so add an option to patch the PROM for that. - PORT_START("piaide_flex_boot_cd00") + PORT_START("PIAIDE_FLEX_BOOT_CD00") PORT_CONFNAME(0x1, 0, "PIA IDE PROM patch FLEX entry to 0xcd00") PORT_CONFSETTING(0, "No - FLEX entry 0xc850") PORT_CONFSETTING(1, "Yes - FLEX entry 0xcd00") diff --git a/src/mame/includes/swtpc09.h b/src/mame/includes/swtpc09.h index b3e310c5487..ada157e8f7f 100644 --- a/src/mame/includes/swtpc09.h +++ b/src/mame/includes/swtpc09.h @@ -44,14 +44,14 @@ public: , m_via_cb2(*this, "via_cb2") , m_dat(*this, "dat") , m_bankdev(*this, "bankdev") - , m_maincpu_clock(*this, "maincpu_clock") - , m_fdc_clock(*this, "fdc_clock") - , m_baud_rate_high(*this, "baud_rate_high") - , m_floppy_expected_density(*this, "floppy_expected_density") - , m_floppy_expected_sectors(*this, "floppy_expected_sectors") - , m_floppy_track_zero_expected_sectors(*this, "floppy_track_zero_expected_sectors") - , m_sbug_double_density(*this, "sbug_double_density") - , m_piaide_flex_boot_cd00(*this, "piaide_flex_boot_cd00") + , m_maincpu_clock(*this, "MAINCPU_CLOCK") + , m_fdc_clock(*this, "FDC_CLOCK") + , m_baud_rate_high(*this, "BAUD_RATE_HIGH") + , m_floppy_expected_density(*this, "FLOPPY_EXPECTED_DENSITY") + , m_floppy_expected_sectors(*this, "FLOPPY_EXPECTED_SECTORS") + , m_floppy_track_zero_expected_sectors(*this, "FLOPPY_TRACK_ZERO_EXPECTED_SECTORS") + , m_sbug_double_density(*this, "SBUG_DOUBLE_DENSITY") + , m_piaide_flex_boot_cd00(*this, "PIAIDE_FLEX_BOOT_CD00") { } void swtpc09_base(machine_config &config); @@ -65,6 +65,10 @@ public: void init_swtpc09u(); void init_swtpc09d3(); + DECLARE_INPUT_CHANGED_MEMBER(maincpu_clock_change); + DECLARE_INPUT_CHANGED_MEMBER(fdc_clock_change); + DECLARE_INPUT_CHANGED_MEMBER(baud_rate_high_change); + private: DECLARE_FLOPPY_FORMATS(floppy_flex_formats); DECLARE_FLOPPY_FORMATS(floppy_uniflex_formats); diff --git a/src/mame/machine/swtpc09.cpp b/src/mame/machine/swtpc09.cpp index ad84096fc79..ddf424b02e8 100644 --- a/src/mame/machine/swtpc09.cpp +++ b/src/mame/machine/swtpc09.cpp @@ -45,7 +45,7 @@ WRITE_LINE_MEMBER(swtpc09_state::io_irq_w) /******* MC6840 PTM on MPID Board *******/ -/* 6840 PTM handlers */ +// 6840 PTM handlers WRITE_LINE_MEMBER( swtpc09_state::ptm_o1_callback ) { m_pia_counter++; @@ -55,7 +55,7 @@ WRITE_LINE_MEMBER( swtpc09_state::ptm_o1_callback ) WRITE_LINE_MEMBER( swtpc09_state::ptm_o3_callback ) { - /* the output from timer3 is the input clock for timer2 */ + // the output from timer3 is the input clock for timer2 //m_ptm->set_c2(state); } @@ -604,25 +604,17 @@ offs_t swtpc09_state::dat_translate(offs_t offset) const READ8_MEMBER(swtpc09_state::main_r) { if (offset < 0xff00) - { return m_banked_space->read_byte(dat_translate(offset)); - } else - { return m_banked_space->read_byte(offset | 0xfff00); - } } WRITE8_MEMBER(swtpc09_state::main_w) { if (offset < 0xff00) - { m_banked_space->write_byte(dat_translate(offset), data); - } else - { m_banked_space->write_byte(offset | 0xfff00, data); - } } /* MC6844 DMA controller I/O */ @@ -735,10 +727,10 @@ READ8_MEMBER( swtpc09_state::m6844_r ) { uint8_t result = 0; - /* switch off the offset we were given */ + // switch off the offset we were given switch (offset) { - /* upper byte of address */ + // upper byte of address case 0x00: case 0x04: case 0x08: @@ -746,7 +738,7 @@ READ8_MEMBER( swtpc09_state::m6844_r ) result = m_m6844_channel[offset / 4].address >> 8; break; - /* lower byte of address */ + // lower byte of address case 0x01: case 0x05: case 0x09: @@ -754,7 +746,7 @@ READ8_MEMBER( swtpc09_state::m6844_r ) result = m_m6844_channel[offset / 4].address & 0xff; break; - /* upper byte of counter */ + // upper byte of counter case 0x02: case 0x06: case 0x0a: @@ -762,7 +754,7 @@ READ8_MEMBER( swtpc09_state::m6844_r ) result = m_m6844_channel[offset / 4].counter >> 8; break; - /* lower byte of counter */ + // lower byte of counter case 0x03: case 0x07: case 0x0b: @@ -770,7 +762,7 @@ READ8_MEMBER( swtpc09_state::m6844_r ) result = m_m6844_channel[offset / 4].counter & 0xff; break; - /* channel control */ + // channel control case 0x10: case 0x11: case 0x12: @@ -787,33 +779,30 @@ READ8_MEMBER( swtpc09_state::m6844_r ) } break; - /* priority control */ + // priority control case 0x14: result = m_m6844_priority; break; - /* interrupt control */ + // interrupt control case 0x15: result = m_m6844_interrupt; break; - /* chaining control */ + // chaining control case 0x16: result = m_m6844_chain; break; - /* 0x17-0x1f not used */ + // 0x17-0x1f not used default: break; } - if (m_system_type == UNIFLEX_DMAF2 || m_system_type == FLEX_DMAF2) // if DMAF2 controller data bus is inverted to 6844 - { + // if DMAF2 controller data bus is inverted to 6844 + if (m_system_type == UNIFLEX_DMAF2 || m_system_type == FLEX_DMAF2) return ~result & 0xff; - } else - { return result & 0xff; - } } @@ -821,13 +810,14 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) { int i; - if (m_system_type == UNIFLEX_DMAF2 || m_system_type == FLEX_DMAF2) // if DMAF2 controller data bus is inverted to 6844 + // if DMAF2 controller data bus is inverted to 6844 + if (m_system_type == UNIFLEX_DMAF2 || m_system_type == FLEX_DMAF2) data = ~data & 0xff; - /* switch off the offset we were given */ + // switch off the offset we were given switch (offset) { - /* upper byte of address */ + // upper byte of address case 0x00: case 0x04: case 0x08: @@ -835,7 +825,7 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) m_m6844_channel[offset / 4].address = (m_m6844_channel[offset / 4].address & 0xff) | (data << 8); break; - /* lower byte of address */ + // lower byte of address case 0x01: case 0x05: case 0x09: @@ -843,7 +833,7 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) m_m6844_channel[offset / 4].address = (m_m6844_channel[offset / 4].address & 0xff00) | (data & 0xff); break; - /* upper byte of counter */ + // upper byte of counter case 0x02: case 0x06: case 0x0a: @@ -851,7 +841,7 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) m_m6844_channel[offset / 4].counter = (m_m6844_channel[offset / 4].counter & 0xff) | (data << 8); break; - /* lower byte of counter */ + // lower byte of counter case 0x03: case 0x07: case 0x0b: @@ -859,7 +849,7 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) m_m6844_channel[offset / 4].counter = (m_m6844_channel[offset / 4].counter & 0xff00) | (data & 0xff); break; - /* channel control */ + // channel control case 0x10: case 0x11: case 0x12: @@ -867,57 +857,73 @@ WRITE8_MEMBER( swtpc09_state::m6844_w ) m_m6844_channel[offset - 0x10].control = (m_m6844_channel[offset - 0x10].control & 0xc0) | (data & 0x3f); break; - /* priority control */ + // priority control case 0x14: m_m6844_priority = data; - /* update each channel */ + // update each channel for (i = 0; i < 4; i++) { - /* if we're going active... */ + // if we're going active... if (!m_m6844_channel[i].active && (data & (1 << i))) { - /* mark us active */ + // mark us active m_m6844_channel[i].active = 1; - /* set the DMA busy bit and clear the DMA end bit */ + // set the DMA busy bit and clear the DMA end bit m_m6844_channel[i].control |= 0x40; m_m6844_channel[i].control &= ~0x80; - /* set the starting address, counter, and time */ + // set the starting address, counter, and time m_m6844_channel[i].start_address = m_m6844_channel[i].address; m_m6844_channel[i].start_counter = m_m6844_channel[i].counter; - - - /* generate and play the sample */ - //play_cvsd(space->machine, i); } - /* if we're going inactive... */ + // if we're going inactive... else if (m_m6844_channel[i].active && !(data & (1 << i))) { - /* mark us inactive */ + //mark us inactive m_m6844_channel[i].active = 0; } } break; - /* interrupt control */ + // interrupt control case 0x15: m_m6844_interrupt = (m_m6844_interrupt & 0x80) | (data & 0x7f); m6844_update_interrupt(); break; - /* chaining control */ + // chaining control case 0x16: m_m6844_chain = data; break; - /* 0x17-0x1f not used */ + // 0x17-0x1f not used default: break; } } +INPUT_CHANGED_MEMBER(swtpc09_state::maincpu_clock_change) +{ + m_maincpu->set_clock(newval * 4); +} + +INPUT_CHANGED_MEMBER(swtpc09_state::fdc_clock_change) +{ + if (m_system_type == FLEX_DMAF2 || + m_system_type == UNIFLEX_DMAF2 || + m_system_type == UNIFLEX_DMAF3) + { + m_fdc->set_unscaled_clock(newval); + } +} + +INPUT_CHANGED_MEMBER(swtpc09_state::baud_rate_high_change) +{ + m_brg->rsa_w(newval); +} + void swtpc09_state::machine_reset() { uint32_t maincpu_clock = m_maincpu_clock->read(); @@ -933,8 +939,8 @@ void swtpc09_state::machine_reset() // Divider select X64 is the default Low baud rate setting. A High // baud rate setting is also available that selects a X16 divider, so - // gives rate four times as high. Note the schematic appears to have - // mislabeled the this setting. + // gives a rate four times as high. Note the schematic appears to have + // mislabeled this setting. uint8_t baud_rate_high = m_baud_rate_high->read(); m_brg->rsa_w(baud_rate_high); m_brg->rsb_w(1); @@ -947,7 +953,7 @@ void swtpc09_state::machine_reset() // Note UNIBUG has a smarter boot loader in ROM and will toggle the // density on failure so this is not necessary for UniFLEX. if ((m_system_type == FLEX_DMAF2 || - m_system_type == FLEX_DC5_PIAIDE) && + m_system_type == FLEX_DC5_PIAIDE) && m_sbug_double_density->read()) { // Patch the boot ROM to load the boot sector in double density. @@ -971,7 +977,7 @@ void swtpc09_state::machine_reset() void swtpc09_state::machine_start() { - m_pia_counter = 0; // init ptm/pia counter to 0 + m_pia_counter = 0; // init ptm/pia counter to 0 m_fdc_status = 0; // for floppy controller m_interrupt = 0; m_active_interrupt = false; @@ -1000,6 +1006,30 @@ void swtpc09_state::machine_start() m_m6844_chain = 0x00; m_banked_space = &subdevice("bankdev")->space(AS_PROGRAM); + + save_item(NAME(m_pia_counter)); + save_item(NAME(m_dmaf_high_address)); + save_item(NAME(m_dmaf2_interrupt_enable)); + save_item(NAME(m_system_type)); + save_item(NAME(m_fdc_status)); + save_item(NAME(m_floppy_motor_on)); + save_item(NAME(m_fdc_side)); + save_item(NAME(m_dmaf3_via_porta)); + save_item(NAME(m_dmaf3_via_portb)); + save_item(NAME(m_active_interrupt)); + save_item(NAME(m_interrupt)); + for (int i = 0; i < 4; i++) + { + save_item(NAME(m_m6844_channel[i].active), i); + save_item(NAME(m_m6844_channel[i].address), i); + save_item(NAME(m_m6844_channel[i].counter), i); + save_item(NAME(m_m6844_channel[i].control), i); + save_item(NAME(m_m6844_channel[i].start_address), i); + save_item(NAME(m_m6844_channel[i].start_counter), i); + } + save_item(NAME(m_m6844_priority)); + save_item(NAME(m_m6844_interrupt)); + save_item(NAME(m_m6844_chain)); } void swtpc09_state::init_swtpc09()