hd63450_device: converted to devcb2 (nw)

This commit is contained in:
Ivan Vangelista 2014-03-22 14:33:09 +00:00
parent fdc538eb29
commit 7e12918ace
5 changed files with 187 additions and 78 deletions

View File

@ -10,7 +10,17 @@ const device_type HD63450 = &device_creator<hd63450_device>;
hd63450_device::hd63450_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
: device_t(mconfig, HD63450, "Hitachi HD63450", tag, owner, clock, "hd63450", __FILE__),
m_cpu(NULL)
m_dma_end(*this),
m_dma_error(*this),
m_dma_read_0(*this),
m_dma_read_1(*this),
m_dma_read_2(*this),
m_dma_read_3(*this),
m_dma_write_0(*this),
m_dma_write_1(*this),
m_dma_write_2(*this),
m_dma_write_3(*this),
m_cpu(NULL)
{
for (int i = 0; i < 4; i++)
{
@ -52,6 +62,18 @@ void hd63450_device::device_start()
m_cpu = machine().device<cpu_device>(m_cpu_tag);
assert(m_cpu != NULL);
// resolve callbacks
m_dma_end.resolve();
m_dma_error.resolve_safe();
m_dma_read_0.resolve();
m_dma_read_1.resolve();
m_dma_read_2.resolve();
m_dma_read_3.resolve();
m_dma_write_0.resolve();
m_dma_write_1.resolve();
m_dma_write_2.resolve();
m_dma_write_3.resolve();
// Initialise timers and registers
for (int x = 0; x < 4 ; x++)
{
@ -147,7 +169,7 @@ WRITE16_MEMBER(hd63450_device::write)
if(ACCESSING_BITS_0_7)
{
m_reg[channel].ccr = data & 0x00ff;
if((data & 0x0080))// && !dma_read[channel] && !dma_write[channel])
if((data & 0x0080))// && !m_dma_read[channel] && !m_dma_write[channel])
dma_transfer_start(channel,0);
if(data & 0x0010) // software abort
dma_transfer_abort(channel);
@ -300,9 +322,33 @@ void hd63450_device::single_transfer(int x)
{
if(m_reg[x].ocr & 0x80) // direction: 1 = device -> memory
{
if(dma_read[x])
if((x == 0) && !m_dma_read_0.isnull())
{
data = dma_read[x](machine(),m_reg[x].mar);
data = m_dma_read_0(m_reg[x].mar);
if(data == -1)
return; // not ready to receive data
space.write_byte(m_reg[x].mar,data);
datasize = 1;
}
else if((x == 1) && !m_dma_read_1.isnull())
{
data = m_dma_read_1(m_reg[x].mar);
if(data == -1)
return; // not ready to receive data
space.write_byte(m_reg[x].mar,data);
datasize = 1;
}
else if((x == 2) && !m_dma_read_2.isnull())
{
data = m_dma_read_2(m_reg[x].mar);
if(data == -1)
return; // not ready to receive data
space.write_byte(m_reg[x].mar,data);
datasize = 1;
}
else if((x == 3) && !m_dma_read_3.isnull())
{
data = m_dma_read_3(m_reg[x].mar);
if(data == -1)
return; // not ready to receive data
space.write_byte(m_reg[x].mar,data);
@ -340,10 +386,28 @@ void hd63450_device::single_transfer(int x)
}
else // memory -> device
{
if(dma_write[x])
if((x == 0) && !m_dma_write_0.isnull())
{
data = space.read_byte(m_reg[x].mar);
dma_write[x](machine(), m_reg[x].mar,data);
m_dma_write_0((offs_t)m_reg[x].mar,data);
datasize = 1;
}
else if((x == 1) && !m_dma_write_1.isnull())
{
data = space.read_byte(m_reg[x].mar);
m_dma_write_1((offs_t)m_reg[x].mar,data);
datasize = 1;
}
else if((x == 2) && !m_dma_write_2.isnull())
{
data = space.read_byte(m_reg[x].mar);
m_dma_write_2((offs_t)m_reg[x].mar,data);
datasize = 1;
}
else if((x == 3) && !m_dma_write_3.isnull())
{
data = space.read_byte(m_reg[x].mar);
m_dma_write_3((offs_t)m_reg[x].mar,data);
datasize = 1;
}
else
@ -417,8 +481,8 @@ void hd63450_device::single_transfer(int x)
m_cpu->set_input_line(INPUT_LINE_HALT, CLEAR_LINE);
}
if(dma_end)
dma_end(machine(),x,m_reg[x].ccr & 0x08);
if(!m_dma_end.isnull())
m_dma_end((offs_t)x, m_reg[x].ccr & 0x08);
}
}
}

View File

@ -5,6 +5,37 @@
#include "emu.h"
#define MCFG_HD63450_DMA_END_CB(_devcb) \
devcb = &hd63450_device::set_dma_end_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_ERROR_CB(_devcb) \
devcb = &hd63450_device::set_dma_error_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_READ_0_CB(_devcb) \
devcb = &hd63450_device::set_dma_read_0_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_READ_1_CB(_devcb) \
devcb = &hd63450_device::set_dma_read_1_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_READ_2_CB(_devcb) \
devcb = &hd63450_device::set_dma_read_2_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_READ_3_CB(_devcb) \
devcb = &hd63450_device::set_dma_read_3_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_WRITE_0_CB(_devcb) \
devcb = &hd63450_device::set_dma_write_0_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_WRITE_1_CB(_devcb) \
devcb = &hd63450_device::set_dma_write_1_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_WRITE_2_CB(_devcb) \
devcb = &hd63450_device::set_dma_write_2_callback(*device, DEVCB2_##_devcb);
#define MCFG_HD63450_DMA_WRITE_3_CB(_devcb) \
devcb = &hd63450_device::set_dma_write_3_callback(*device, DEVCB2_##_devcb);
struct hd63450_regs
{ // offsets in bytes
unsigned char csr; // [00] Channel status register (R/W)
@ -32,10 +63,6 @@ struct hd63450_interface
const char *m_cpu_tag;
attotime m_our_clock[4];
attotime m_burst_clock[4];
void (*dma_end)(running_machine &machine,int channel,int irq); // called when the DMA transfer ends
void (*dma_error)(running_machine &machine,int channel, int irq); // called when a DMA transfer error occurs
int (*dma_read[4])(running_machine &machine,int addr); // special read / write handlers for each channel
void (*dma_write[4])(running_machine &machine,int addr,int data);
};
class hd63450_device : public device_t,
@ -45,6 +72,17 @@ public:
hd63450_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
~hd63450_device() {}
template<class _Object> static devcb2_base &set_dma_end_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_end.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_error_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_error.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_read_0_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_read_0.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_read_1_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_read_1.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_read_2_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_read_2.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_read_3_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_read_3.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_write_0_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_write_0.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_write_1_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_write_1.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_write_2_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_write_2.set_callback(object); }
template<class _Object> static devcb2_base &set_dma_write_3_callback(device_t &device, _Object object) { return downcast<hd63450_device &>(device).m_dma_write_3.set_callback(object); }
DECLARE_READ16_MEMBER( read );
DECLARE_WRITE16_MEMBER( write );
@ -59,6 +97,17 @@ protected:
virtual void device_start();
private:
devcb2_write8 m_dma_end;
devcb2_write8 m_dma_error;
devcb2_read8 m_dma_read_0;
devcb2_read8 m_dma_read_1;
devcb2_read8 m_dma_read_2;
devcb2_read8 m_dma_read_3;
devcb2_write8 m_dma_write_0;
devcb2_write8 m_dma_write_1;
devcb2_write8 m_dma_write_2;
devcb2_write8 m_dma_write_3;
// internal state
hd63450_regs m_reg[4];
emu_timer* m_timer[4]; // for timing data reading/writing each channel
@ -75,8 +124,3 @@ private:
};
extern const device_type HD63450;
#define MCFG_HD63450_ADD(_tag, _config) \
MCFG_DEVICE_ADD(_tag, HD63450, 0) \
MCFG_DEVICE_CONFIG(_config)

View File

@ -222,6 +222,12 @@ public:
DECLARE_INPUT_CHANGED_MEMBER(key_stroke);
IRQ_CALLBACK_MEMBER(maincpu_irq_acknowledge_callback);
DECLARE_WRITE_LINE_MEMBER(esq5505_otis_irq);
//dmac
DECLARE_WRITE8_MEMBER(dma_end);
DECLARE_WRITE8_MEMBER(dma_error);
DECLARE_READ8_MEMBER(fdc_read_byte);
DECLARE_WRITE8_MEMBER(fdc_write_byte);
};
FLOPPY_FORMATS_MEMBER( esq5505_state::floppy_formats )
@ -505,53 +511,46 @@ WRITE_LINE_MEMBER(esq5505_state::duart_tx_b)
m_panel->rx_w(state);
}
static void esq_dma_end(running_machine &machine, int channel, int irq)
WRITE8_MEMBER(esq5505_state::dma_end)
{
esq5505_state *state = machine.driver_data<esq5505_state>();
if (irq != 0)
if (data != 0)
{
printf("DMAC IRQ, vector = %x\n", state->m_dmac->get_vector(channel));
state->dmac_irq_state = 1;
state->dmac_irq_vector = state->m_dmac->get_vector(channel);
printf("DMAC IRQ, vector = %x\n", m_dmac->get_vector(offset));
dmac_irq_state = 1;
dmac_irq_vector = m_dmac->get_vector(offset);
}
else
{
state->dmac_irq_state = 0;
dmac_irq_state = 0;
}
state->update_irq_to_maincpu();
update_irq_to_maincpu();
}
static void esq_dma_error(running_machine &machine, int channel, int irq)
WRITE8_MEMBER(esq5505_state::dma_error)
{
esq5505_state *state = machine.driver_data<esq5505_state>();
if(irq != 0)
if(data != 0)
{
printf("DMAC error, vector = %x\n", state->m_dmac->get_error_vector(channel));
state->dmac_irq_state = 1;
state->dmac_irq_vector = state->m_dmac->get_vector(channel);
printf("DMAC error, vector = %x\n", m_dmac->get_error_vector(offset));
dmac_irq_state = 1;
dmac_irq_vector = m_dmac->get_vector(offset);
}
else
{
state->dmac_irq_state = 0;
dmac_irq_state = 0;
}
state->update_irq_to_maincpu();
update_irq_to_maincpu();
}
static int esq_fdc_read_byte(running_machine &machine, int addr)
READ8_MEMBER(esq5505_state::fdc_read_byte)
{
esq5505_state *state = machine.driver_data<esq5505_state>();
return state->m_fdc->data_r();
return m_fdc->data_r();
}
static void esq_fdc_write_byte(running_machine &machine, int addr, int data)
WRITE8_MEMBER(esq5505_state::fdc_write_byte)
{
esq5505_state *state = machine.driver_data<esq5505_state>();
state->m_fdc->data_w(data & 0xff);
m_fdc->data_w(data & 0xff);
}
#if KEYBOARD_HACK
@ -607,10 +606,6 @@ static const hd63450_interface dmac_interface =
"maincpu", // CPU - 68000
{attotime::from_usec(32),attotime::from_nsec(450),attotime::from_usec(4),attotime::from_hz(15625/2)}, // Cycle steal mode timing (guesstimate)
{attotime::from_usec(32),attotime::from_nsec(450),attotime::from_nsec(50),attotime::from_nsec(50)}, // Burst mode timing (guesstimate)
esq_dma_end,
esq_dma_error,
{ esq_fdc_read_byte, 0, 0, 0 }, // ch 0 = fdc, ch 1 = 340001 (ADC?)
{ esq_fdc_write_byte, 0, 0, 0 }
};
static const es5505_interface es5505_config =
@ -675,7 +670,12 @@ static MACHINE_CONFIG_DERIVED(eps, vfx)
MCFG_WD1772x_ADD("wd1772", 8000000)
MCFG_FLOPPY_DRIVE_ADD("wd1772:0", ensoniq_floppies, "35dd", esq5505_state::floppy_formats)
MCFG_HD63450_ADD( "mc68450", dmac_interface ) // MC68450 compatible
MCFG_DEVICE_ADD("mc68450", HD63450, 0) // MC68450 compatible
MCFG_DEVICE_CONFIG(dmac_interface)
MCFG_HD63450_DMA_END_CB(WRITE8(esq5505_state, dma_end))
MCFG_HD63450_DMA_ERROR_CB(WRITE8(esq5505_state, dma_error))
MCFG_HD63450_DMA_READ_0_CB(READ8(esq5505_state, fdc_read_byte)) // ch 0 = fdc, ch 1 = 340001 (ADC?)
MCFG_HD63450_DMA_WRITE_0_CB(WRITE8(esq5505_state, fdc_write_byte))
MACHINE_CONFIG_END
static MACHINE_CONFIG_DERIVED(vfxsd, vfx)

View File

@ -726,16 +726,14 @@ WRITE_LINE_MEMBER( x68k_state::fdc_irq )
}
}
static int x68k_fdc_read_byte(running_machine &machine,int addr)
READ8_MEMBER(x68k_state::fdc_read_byte)
{
x68k_state *state = machine.driver_data<x68k_state>();
return state->m_fdc.fdc->dma_r();
return m_fdc.fdc->dma_r();
}
static void x68k_fdc_write_byte(running_machine &machine,int addr, int data)
WRITE8_MEMBER(x68k_state::fdc_write_byte)
{
x68k_state *state = machine.driver_data<x68k_state>();
return state->m_fdc.fdc->dma_w(data);
return m_fdc.fdc->dma_w(data);
}
WRITE_LINE_MEMBER( x68k_state::fdc_drq )
@ -1157,36 +1155,33 @@ WRITE16_MEMBER(x68k_state::x68k_exp_w)
}
}
static void x68k_dma_irq(running_machine &machine, int channel)
void x68k_state::dma_irq(int channel)
{
x68k_state *state = machine.driver_data<x68k_state>();
state->m_current_vector[3] = state->m_hd63450->get_vector(channel);
state->m_current_irq_line = 3;
logerror("DMA#%i: DMA End (vector 0x%02x)\n",channel,state->m_current_vector[3]);
state->m_maincpu->set_input_line_and_vector(3,ASSERT_LINE,state->m_current_vector[3]);
m_current_vector[3] = m_hd63450->get_vector(channel);
m_current_irq_line = 3;
logerror("DMA#%i: DMA End (vector 0x%02x)\n",channel,m_current_vector[3]);
m_maincpu->set_input_line_and_vector(3,ASSERT_LINE,m_current_vector[3]);
}
static void x68k_dma_end(running_machine &machine, int channel,int irq)
WRITE8_MEMBER(x68k_state::dma_end)
{
if(irq != 0)
if(data != 0)
{
x68k_dma_irq(machine, channel);
dma_irq(offset);
}
if(channel == 0)
if(offset == 0)
{
x68k_state *state = machine.driver_data<x68k_state>();
state->m_fdc_tc->adjust(attotime::from_usec(1), 0, attotime::never);
m_fdc_tc->adjust(attotime::from_usec(1), 0, attotime::never);
}
}
static void x68k_dma_error(running_machine &machine, int channel, int irq)
WRITE8_MEMBER(x68k_state::dma_error)
{
x68k_state *state = machine.driver_data<x68k_state>();
if(irq != 0)
if(data != 0)
{
state->m_current_vector[3] = state->m_hd63450->get_error_vector(channel);
state->m_current_irq_line = 3;
state->m_maincpu->set_input_line_and_vector(3,ASSERT_LINE,state->m_current_vector[3]);
m_current_vector[3] = m_hd63450->get_error_vector(offset);
m_current_irq_line = 3;
m_maincpu->set_input_line_and_vector(3,ASSERT_LINE,m_current_vector[3]);
}
}
@ -1411,12 +1406,6 @@ static const hd63450_interface dmac_interface =
"maincpu", // CPU - 68000
{attotime::from_usec(32),attotime::from_nsec(450),attotime::from_usec(4),attotime::from_hz(15625/2)}, // Cycle steal mode timing (guesstimate)
{attotime::from_usec(32),attotime::from_nsec(450),attotime::from_nsec(50),attotime::from_nsec(50)}, // Burst mode timing (guesstimate)
x68k_dma_end,
x68k_dma_error,
{ x68k_fdc_read_byte, 0, 0, 0 },
{ x68k_fdc_write_byte, 0, 0, 0 }
// { 0, 0, 0, 0 },
// { 0, 0, 0, 0 }
};
static const okim6258_interface x68k_okim6258_interface =
@ -1897,7 +1886,12 @@ static MACHINE_CONFIG_FRAGMENT( x68000_base )
MCFG_I8255A_ADD( "ppi8255", ppi_interface )
MCFG_HD63450_ADD( "hd63450", dmac_interface )
MCFG_DEVICE_ADD( "hd63450", HD63450, 0 )
MCFG_DEVICE_CONFIG(dmac_interface)
MCFG_HD63450_DMA_END_CB(WRITE8(x68k_state, dma_end))
MCFG_HD63450_DMA_ERROR_CB(WRITE8(x68k_state, dma_error))
MCFG_HD63450_DMA_READ_0_CB(READ8(x68k_state, fdc_read_byte))
MCFG_HD63450_DMA_WRITE_0_CB(WRITE8(x68k_state, fdc_write_byte))
MCFG_DEVICE_ADD( "scc", SCC8530, 5000000 )

View File

@ -247,6 +247,13 @@ public:
DECLARE_WRITE_LINE_MEMBER(mfp_irq_callback);
DECLARE_WRITE_LINE_MEMBER(x68k_scsi_irq);
DECLARE_WRITE_LINE_MEMBER(x68k_scsi_drq);
//dmac
void dma_irq(int channel);
DECLARE_WRITE8_MEMBER(dma_end);
DECLARE_WRITE8_MEMBER(dma_error);
DECLARE_READ8_MEMBER(fdc_read_byte);
DECLARE_WRITE8_MEMBER(fdc_write_byte);
int x68k_read_mouse();
void x68k_set_adpcm();