i8257: Various small improvements (nw)

- Synchronize at a couple of critical points
- Allow read side effects to be suppressed while debugging
- Improve TC timing
- Allow HLDA to abort DMA cycle
- Don't clear request input state when device is reset
This commit is contained in:
AJR 2019-10-18 22:57:40 -04:00
parent 48ad5e3427
commit e2fc3f0cbe

View File

@ -82,7 +82,7 @@ enum
inline void i8257_device::dma_request(int channel, int state) inline void i8257_device::dma_request(int channel, int state)
{ {
LOG("I8257 Channel %u DMA Request: %u\n", channel, state); LOG("I8257 Channel %u DMA Request: %u (%sabled)\n", channel, state, MODE_CHAN_ENABLE(channel) ? "en" : "dis");
if (state) if (state)
m_request |= 1 << channel; m_request |= 1 << channel;
@ -114,6 +114,7 @@ inline void i8257_device::set_hreq(int state)
{ {
m_out_hrq_cb(state); m_out_hrq_cb(state);
m_hreq = state; m_hreq = state;
abort_timeslice();
} }
} }
@ -212,13 +213,13 @@ inline void i8257_device::dma_write()
inline void i8257_device::advance() inline void i8257_device::advance()
{ {
LOG("%s\n", FUNCNAME); LOG("%s\n", FUNCNAME);
bool tc = (m_channel[m_current_channel].m_count == 0); bool tc = m_tc;
bool al = (MODE_AUTOLOAD && (m_current_channel == 2)); bool al = (MODE_AUTOLOAD && (m_current_channel == 2));
set_tc(0);
if(tc) if(tc)
{ {
m_status |= 1 << m_current_channel; m_status |= 1 << m_current_channel;
set_tc(1);
if(al) if(al)
{ {
@ -337,7 +338,6 @@ void i8257_device::device_reset()
m_state = STATE_SI; m_state = STATE_SI;
m_transfer_mode = 0; m_transfer_mode = 0;
m_status = 0; m_status = 0;
m_request = 0;
m_msb = 0; m_msb = 0;
m_current_channel = -1; m_current_channel = -1;
m_last_channel = 3; m_last_channel = 3;
@ -400,8 +400,8 @@ void i8257_device::execute_run()
m_state = STATE_S0; m_state = STATE_S0;
else else
{ {
suspend_until_trigger(1, true);
m_icount = 0; m_icount = 0;
suspend_until_trigger(1, true);
} }
break; break;
@ -414,8 +414,8 @@ void i8257_device::execute_run()
} }
else else
{ {
suspend_until_trigger(1, true);
m_icount = 0; m_icount = 0;
suspend_until_trigger(1, true);
} }
break; break;
@ -437,11 +437,23 @@ void i8257_device::execute_run()
dma_write(); dma_write();
} }
m_state = m_ready ? STATE_S4 : STATE_SW; if (m_ready)
{
m_state = STATE_S4;
if (m_channel[m_current_channel].m_count == 0)
set_tc(1);
}
else
m_state = STATE_SW;
break; break;
case STATE_SW: case STATE_SW:
m_state = m_ready ? STATE_S4 : STATE_SW; if (m_ready)
{
m_state = STATE_S4;
if (m_channel[m_current_channel].m_count == 0)
set_tc(1);
}
break; break;
case STATE_S4: case STATE_S4:
@ -451,7 +463,7 @@ void i8257_device::execute_run()
} }
advance(); advance();
if(next_channel()) if(m_hack && next_channel())
m_state = STATE_S1; m_state = STATE_S1;
else else
{ {
@ -509,14 +521,16 @@ READ8_MEMBER( i8257_device::read )
break; break;
} }
m_msb = !m_msb; if (!machine().side_effects_disabled())
m_msb = !m_msb;
} }
else if(offset == REGISTER_STATUS) else if(offset == REGISTER_STATUS)
{ {
data = m_status; data = m_status;
// clear TC bits // clear TC bits
m_status &= 0xf0; if (!machine().side_effects_disabled())
m_status &= 0xf0;
} }
return data; return data;
@ -585,7 +599,12 @@ WRITE8_MEMBER( i8257_device::write )
LOGSETUP("I8257 Command Register: %02x\n", m_transfer_mode); LOGSETUP("I8257 Command Register: %02x\n", m_transfer_mode);
} }
trigger(1);
if ((m_transfer_mode & m_request & 0x0f) != 0)
{
machine().scheduler().eat_all_cycles();
trigger(1);
}
} }