void c64h156_device::live_run(const attotime &limit) { if(cur_live.state == IDLE || cur_live.next_state != -1) return; for(;;) { switch(cur_live.state) { case RUNNING: { bool syncpoint = false; if (cur_live.tm > limit) return; int bit = get_next_bit(cur_live.tm, limit); if(bit < 0) return; int cell_counter = cur_live.cell_counter; if (bit) { cur_live.cycle_counter = cur_live.ds; cur_live.cell_counter = 0; } else { cur_live.cycle_counter++; } if (cur_live.cycle_counter == 16) { cur_live.cycle_counter = cur_live.ds; cur_live.cell_counter++; cur_live.cell_counter &= 0xf; } if (!BIT(cell_counter, 1) && BIT(cur_live.cell_counter, 1)) { // read bit cur_live.shift_reg <<= 1; cur_live.shift_reg |= !(BIT(cur_live.cell_counter, 3) || BIT(cur_live.cell_counter, 2)); cur_live.shift_reg &= 0x3ff; if (LOG) logerror("%s read bit %u (%u) >> %03x, oe=%u soe=%u sync=%u byte=%u\n", cur_live.tm.as_string(), cur_live.bit_counter, !(BIT(cur_live.cell_counter, 3) || BIT(cur_live.cell_counter, 2)), cur_live.shift_reg, cur_live.oe, cur_live.soe, cur_live.sync, cur_live.byte); syncpoint = true; } if (BIT(cell_counter, 1) && !BIT(cur_live.cell_counter, 1) && !cur_live.oe) { write_next_bit(BIT(cur_live.shift_reg_write, 7), limit); } int sync = !((cur_live.shift_reg == 0x3ff) && cur_live.oe); if (!sync) { cur_live.bit_counter = 8; } else if (!BIT(cell_counter, 1) && BIT(cur_live.cell_counter, 1) && cur_live.sync) { cur_live.bit_counter++; cur_live.bit_counter &= 0xf; } int byte = !(((cur_live.bit_counter & 7) == 7) && cur_live.soe && !(cur_live.cell_counter & 2)); int load = !(((cur_live.bit_counter & 7) == 7) && ((cur_live.cell_counter & 3) == 3)); if (!load) { if (cur_live.oe) { cur_live.shift_reg_write = cur_live.shift_reg; if (LOG) logerror("%s load write shift register from read shift register %02x\n",cur_live.tm.as_string(),cur_live.shift_reg_write); } else { cur_live.shift_reg_write = cur_live.yb; if (LOG) logerror("%s load write shift register from YB %02x\n",cur_live.tm.as_string(),cur_live.shift_reg_write); } } else if (!BIT(cell_counter, 1) && BIT(cur_live.cell_counter, 1)) { cur_live.shift_reg_write <<= 1; cur_live.shift_reg_write &= 0xff; if (LOG) logerror("%s shift write register << %02x\n", cur_live.tm.as_string(), cur_live.shift_reg_write); } // update signals if (byte != cur_live.byte) { if (!byte || !cur_live.accl) { if (LOG) logerror("%s BYTE %u\n", cur_live.tm.as_string(),byte); cur_live.byte = byte; syncpoint = true; } if (!byte) { cur_live.accl_yb = cur_live.shift_reg & 0xff; } } if (sync != cur_live.sync) { if (LOG) logerror("%s SYNC %u\n", cur_live.tm.as_string(),sync); cur_live.sync = sync; syncpoint = true; } if (syncpoint) { commit(cur_live.tm); cur_live.tm += m_period; live_delay(RUNNING_SYNCPOINT); return; } cur_live.tm += m_period; break; } case RUNNING_SYNCPOINT: { m_write_sync(cur_live.sync); m_write_byte(cur_live.byte); cur_live.state = RUNNING; checkpoint(); break; } } } }
void c2040_fdc_t::live_run(const attotime &limit) { if(cur_live.state == IDLE || cur_live.next_state != -1) return; for(;;) { switch(cur_live.state) { case RUNNING: { bool syncpoint = false; if (cur_live.tm > limit) return; int bit = get_next_bit(cur_live.tm, limit); if(bit < 0) return; int cell_counter = cur_live.cell_counter; if (bit) { cur_live.cycle_counter = cur_live.ds; cur_live.cell_counter = 0; } else { cur_live.cycle_counter++; } if (cur_live.cycle_counter == 16) { cur_live.cycle_counter = cur_live.ds; cur_live.cell_counter++; cur_live.cell_counter &= 0xf; } if (!BIT(cell_counter, 1) && BIT(cur_live.cell_counter, 1)) { // read bit cur_live.shift_reg <<= 1; cur_live.shift_reg |= !(BIT(cur_live.cell_counter, 3) || BIT(cur_live.cell_counter, 2)); cur_live.shift_reg &= 0x3ff; if (LOG) logerror("%s read bit %u (%u) >> %03x, rw=%u mode=%u\n", cur_live.tm.as_string(), cur_live.bit_counter, !(BIT(cur_live.cell_counter, 3) || BIT(cur_live.cell_counter, 2)), cur_live.shift_reg, cur_live.rw_sel, cur_live.mode_sel); // write bit if (!cur_live.rw_sel) { // TODO WPS write_next_bit(BIT(cur_live.shift_reg_write, 9), limit); } syncpoint = true; } int sync = !((cur_live.shift_reg == 0x3ff) && cur_live.rw_sel); if (!sync) { cur_live.bit_counter = 0; } else if (!BIT(cell_counter, 1) && BIT(cur_live.cell_counter, 1) && cur_live.sync) { cur_live.bit_counter++; if (cur_live.bit_counter == 10) { cur_live.bit_counter = 0; } } // update GCR if (cur_live.rw_sel) { cur_live.i = (cur_live.rw_sel << 10) | cur_live.shift_reg; } else { cur_live.i = (cur_live.rw_sel << 10) | ((cur_live.pi & 0xf0) << 1) | (cur_live.mode_sel << 4) | (cur_live.pi & 0x0f); } cur_live.e = m_gcr_rom->base()[cur_live.i]; int ready = !(BIT(cell_counter, 1) && !BIT(cur_live.cell_counter, 1) && (cur_live.bit_counter == 9)); if (!ready) { // load write shift register cur_live.shift_reg_write = GCR_ENCODE(cur_live.e, cur_live.i); if (LOG) logerror("%s load write shift register %03x\n",cur_live.tm.as_string(),cur_live.shift_reg_write); } else if (BIT(cell_counter, 1) && !BIT(cur_live.cell_counter, 1)) { // clock write shift register cur_live.shift_reg_write <<= 1; cur_live.shift_reg_write &= 0x3ff; if (LOG) logerror("%s write shift << %03x\n",cur_live.tm.as_string(),cur_live.shift_reg_write); } int error = !(BIT(cur_live.e, 3) || ready); if (ready != cur_live.ready) { if (LOG) logerror("%s READY %u\n", cur_live.tm.as_string(),ready); cur_live.ready = ready; syncpoint = true; } if (sync != cur_live.sync) { if (LOG) logerror("%s SYNC %u\n", cur_live.tm.as_string(),sync); cur_live.sync = sync; syncpoint = true; } if (error != cur_live.error) { cur_live.error = error; syncpoint = true; } if (syncpoint) { commit(cur_live.tm); cur_live.tm += m_period; live_delay(RUNNING_SYNCPOINT); return; } cur_live.tm += m_period; break; } case RUNNING_SYNCPOINT: { m_write_ready(cur_live.ready); m_write_sync(cur_live.sync); m_write_error(cur_live.error); cur_live.state = RUNNING; checkpoint(); break; } } } }
void c8050_fdc_t::live_run(const attotime &limit) { if(cur_live.state == IDLE || cur_live.next_state != -1) return; for(;;) { switch(cur_live.state) { case RUNNING: { bool syncpoint = false; if (cur_live.tm > limit) return; // read bit int bit = 0; if (cur_live.rw_sel) { bit = pll_get_next_bit(cur_live.tm, get_floppy(), limit); if(bit < 0) return; } // write bit int write_bit = BIT(cur_live.shift_reg_write, 9); if (!cur_live.rw_sel) { // TODO WPS /* write precompensation UA5.A = UM6.Qc UA5.B = !(!(!BRDY && UM6.Qa) && !(BRDY && E7)) UA5.C0 = UA4.Qb = bit clock delayed 333ns UA5.C1 = UA4.Qa = bit clock delayed 166ns UA5.C2 = UA4.Qc = bit clock delayed 499ns UA5.C3 = UA5.Qb = bit clock delayed 333ns DATA OUT = !(!BITCLK || !(UA5.Y && !(WRITE_ENABLE && !UM6.Qb))) */ if (pll_write_next_bit(write_bit, cur_live.tm, get_floppy(), limit)) return; } // clock read shift register cur_live.shift_reg <<= 1; cur_live.shift_reg |= bit; cur_live.shift_reg &= 0x3ff; // sync int sync = !((cur_live.shift_reg == 0x3ff) && cur_live.rw_sel); // bit counter if (!sync) { cur_live.bit_counter = 0; } else if (cur_live.sync) { cur_live.bit_counter++; if (cur_live.bit_counter == 10) { cur_live.bit_counter = 0; } } // GCR decoder if (cur_live.rw_sel) { cur_live.i = (cur_live.rw_sel << 10) | cur_live.shift_reg; } else { cur_live.i = (cur_live.rw_sel << 10) | ((cur_live.pi & 0xf0) << 1) | (cur_live.mode_sel << 4) | (cur_live.pi & 0x0f); } cur_live.e = m_gcr_rom->base()[cur_live.i]; // byte ready int ready = !(cur_live.bit_counter == 9); // 74190 _RC, should be triggered on the falling edge of the clock int brdy = ready; // 74190 TC // GCR error int error = !(ready || BIT(cur_live.e, 3)); if (LOG_BITS) { if (cur_live.rw_sel) { logerror("%s cyl %u bit %u sync %u bc %u sr %03x i %03x e %02x\n",cur_live.tm.as_string(),get_floppy()->get_cyl(),bit,sync,cur_live.bit_counter,cur_live.shift_reg,cur_live.i,cur_live.e); } else { logerror("%s cyl %u writing bit %u bc %u sr %03x i %03x e %02x\n",cur_live.tm.as_string(),get_floppy()->get_cyl(),write_bit,cur_live.bit_counter,cur_live.shift_reg_write,cur_live.i,cur_live.e); } } if (!ready) { // load write shift register cur_live.shift_reg_write = GCR_ENCODE(cur_live.e, cur_live.i); if (LOG_BITS) logerror("%s load write shift register %03x\n",cur_live.tm.as_string(),cur_live.shift_reg_write); } else { // clock write shift register cur_live.shift_reg_write <<= 1; cur_live.shift_reg_write &= 0x3ff; } if (ready != cur_live.ready) { if (cur_live.rw_sel && !ready) if (LOG) logerror("%s READY %u : %02x\n", cur_live.tm.as_string(),ready,GCR_DECODE(cur_live.e, cur_live.i)); cur_live.ready = ready; syncpoint = true; } if (brdy != cur_live.brdy) { if (LOG_MORE) logerror("%s BRDY %u\n", cur_live.tm.as_string(), brdy); cur_live.brdy = brdy; syncpoint = true; } if (sync != cur_live.sync) { if (LOG) logerror("%s SYNC %u\n", cur_live.tm.as_string(), sync); cur_live.sync = sync; syncpoint = true; } if (error != cur_live.error) { if (LOG_MORE) logerror("%s ERROR %u\n", cur_live.tm.as_string(), error); cur_live.error = error; syncpoint = true; } if (syncpoint) { live_delay(RUNNING_SYNCPOINT); return; } break; } case RUNNING_SYNCPOINT: { m_write_ready(cur_live.ready); m_write_brdy(cur_live.brdy); m_write_sync(cur_live.sync); m_write_error(cur_live.error); cur_live.state = RUNNING; checkpoint(); break; } } } }