New model for populating devices in a driver_device class. Removed the

recently-introduced find_devices() method.

There are two new template classes optional_device<> and required_device<>.
Use these to declare the device pointers in the class. The only difference 
between the two is that required will fatalerror if the device is not found.

These new classes are "pass-through" so m_oki can be passed anywhere an
okim6295_device would work, and you can use m_oki->x to reference methods
or variables.

Each of these new classes needs to be specified in the initializer,
passing a reference to the driver_device object and the device tag. So,
for example:

class example_state : public driver_device
{
public:
    example_state(running_machine &machine, const driver_device_config_base &config)
		: driver_device(machine, config),
		  m_maincpu(*this, "maincpu"),
		  m_oki(*this, "oki") { }

    required_device<okim6295_device> m_oki;
    optional_device<cpu_device> m_maincpu;
};

Given that, the driver_device will auto-populate each device with a
pointer to the device prior to calling any of the initialization methods.
This commit is contained in:
Aaron Giles 2010-09-03 20:57:19 +00:00
parent 093c2682a2
commit 046250f179
18 changed files with 207 additions and 144 deletions

View File

@ -1048,16 +1048,6 @@ driver_device::~driver_device()
}
//-------------------------------------------------
// find_devices - default implementation which
// does nothing
//-------------------------------------------------
void driver_device::find_devices()
{
}
//-------------------------------------------------
// driver_start - default implementation which
// does nothing
@ -1186,8 +1176,9 @@ void driver_device::device_start()
if (next() != NULL)
throw device_missing_dependencies();
// first find devices
find_devices();
// find all the registered devices
for (auto_device_base *autodev = m_auto_device_list; autodev != NULL; autodev = autodev->m_next)
autodev->findit(*this);
// call the game-specific init
if (m_config.m_game->driver_init != NULL)
@ -1220,6 +1211,40 @@ void driver_device::device_reset()
}
//-------------------------------------------------
// auto_device_base - constructor
//-------------------------------------------------
void driver_device::register_auto_device(auto_device_base &autodev)
{
// add to this list
autodev.m_next = m_auto_device_list;
m_auto_device_list = &autodev;
}
//-------------------------------------------------
// auto_device_base - constructor
//-------------------------------------------------
driver_device::auto_device_base::auto_device_base(driver_device &base, const char *tag)
: m_next(NULL),
m_tag(tag)
{
// register ourselves with our device class
base.register_auto_device(*this);
}
//-------------------------------------------------
// ~auto_device_base - destructor
//-------------------------------------------------
driver_device::auto_device_base::~auto_device_base()
{
}
//**************************************************************************
// SYSTEM TIME

View File

@ -617,7 +617,6 @@ public:
protected:
// helpers called at startup
virtual void find_devices();
virtual void driver_start();
virtual void machine_start();
virtual void sound_start();
@ -633,23 +632,70 @@ protected:
virtual void device_start();
virtual void device_reset();
// device locators
template<class T>
bool optional_device(T *&device, const char *tag)
// helper class to request auto-device discovery in the constructor of a derived class
class auto_device_base
{
device = downcast<T *>(m_machine.device<T>(tag));
return (device != NULL);
}
public:
// construction/destruction
auto_device_base(driver_device &base, const char *tag);
virtual ~auto_device_base();
template<class T>
void required_device(T *&device, const char *tag)
// getters
virtual void findit(driver_device &base) = 0;
// internal state
auto_device_base *m_next;
const char *m_tag;
};
// optional device finder
template<class _DeviceClass>
class optional_device : public auto_device_base
{
if (!optional_device(device, tag))
throw emu_fatalerror("Unable to find device '%s'", tag);
}
public:
// construction/destruction
optional_device(driver_device &base, const char *tag)
: auto_device_base(base, tag),
m_device(NULL) { }
// operators to make use transparent
operator _DeviceClass *() { return m_device; }
operator _DeviceClass *() const { return m_device; }
_DeviceClass *operator->() { return m_device; }
// finder
virtual void findit(driver_device &base)
{
m_device = base.m_machine.device<_DeviceClass>(m_tag);
}
// internal state
_DeviceClass *m_device;
};
// required devices are similar but throw an error if they are not found
template<class _DeviceClass>
class required_device : public optional_device<_DeviceClass>
{
public:
// construction/destruction
required_device(driver_device &base, const char *tag)
: optional_device<_DeviceClass>(base, tag) { }
// finder
virtual void findit(driver_device &base)
{
this->m_device = base.m_machine.device<_DeviceClass>(this->m_tag);
if (this->m_device == NULL) throw emu_fatalerror("Unabled to find required device '%s'", this->m_tag);
}
};
// internal helpers
void register_auto_device(auto_device_base &autodev);
// internal state
const driver_device_config_base &m_config;
auto_device_base *m_auto_device_list;
};

View File

@ -11,17 +11,17 @@ class atarisy1_state : public atarigen_state
public:
atarisy1_state(running_machine &machine, const driver_device_config_base &config)
: atarigen_state(machine, config),
joystick_timer(machine.device<timer_device>("joystick_timer")),
yscroll_reset_timer(machine.device<timer_device>("yreset_timer")),
scanline_timer(machine.device<timer_device>("scan_timer")),
int3off_timer(machine.device<timer_device>("int3off_timer")) { }
joystick_timer(*this, "joystick_timer"),
yscroll_reset_timer(*this, "yreset_timer"),
scanline_timer(*this, "scan_timer"),
int3off_timer(*this, "int3off_timer") { }
UINT16 * bankselect;
UINT8 joystick_type;
UINT8 trackball_type;
timer_device * joystick_timer;
required_device<timer_device> joystick_timer;
UINT8 joystick_int;
UINT8 joystick_int_enable;
UINT8 joystick_value;
@ -30,12 +30,12 @@ public:
UINT16 playfield_lookup[256];
UINT8 playfield_tile_bank;
UINT16 playfield_priority_pens;
timer_device * yscroll_reset_timer;
required_device<timer_device> yscroll_reset_timer;
/* INT3 tracking */
int next_timer_scanline;
timer_device * scanline_timer;
timer_device * int3off_timer;
required_device<timer_device> scanline_timer;
required_device<timer_device> int3off_timer;
/* graphics bank tracking */
UINT8 bank_gfx[3][8];

View File

@ -31,8 +31,8 @@ class balsente_state : public driver_device
public:
balsente_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
scanline_timer(machine.device<timer_device>("scan_timer")),
counter_0_timer(machine.device<timer_device>("8253_0_timer"))
scanline_timer(*this, "scan_timer"),
counter_0_timer(*this, "8253_0_timer")
{
astring temp;
for (int i = 0; i < ARRAY_LENGTH(cem_device); i++)
@ -64,12 +64,12 @@ public:
UINT8 writebyte;
} counter[3];
timer_device *scanline_timer;
required_device<timer_device> scanline_timer;
/* manually clocked counter 0 states */
UINT8 counter_control;
UINT8 counter_0_ff;
timer_device *counter_0_timer;
required_device<timer_device> counter_0_timer;
UINT8 counter_0_timer_active;
/* random number generator states */

View File

@ -12,12 +12,8 @@ class beathead_state : public atarigen_state
{
public:
beathead_state(running_machine &machine, const driver_device_config_base &config)
: atarigen_state(machine, config) { }
virtual void find_devices()
{
required_device(m_maincpu, "maincpu");
}
: atarigen_state(machine, config),
m_maincpu(*this, "maincpu") { }
virtual void machine_start();
virtual void machine_reset();
@ -25,7 +21,7 @@ public:
virtual void video_start();
virtual bool video_update(screen_device &screen, bitmap_t &bitmap, const rectangle &cliprect);
asap_device * m_maincpu;
required_device<asap_device> m_maincpu;
UINT32 * m_videoram;
UINT32 * m_paletteram;

View File

@ -12,11 +12,11 @@ class boogwing_state : public driver_device
public:
boogwing_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
audiocpu(machine.device<cpu_device>("audiocpu")),
deco16ic(machine.device<deco16ic_device>("deco_custom")),
oki1(machine.device<okim6295_device>("oki1")),
oki2(machine.device<okim6295_device>("oki2")) { }
maincpu(*this, "maincpu"),
audiocpu(*this, "audiocpu"),
deco16ic(*this, "deco_custom"),
oki1(*this, "oki1"),
oki2(*this, "oki2") { }
/* memory pointers */
UINT16 * pf1_rowscroll;
@ -25,11 +25,11 @@ public:
UINT16 * pf4_rowscroll;
/* devices */
cpu_device *maincpu;
cpu_device *audiocpu;
deco16ic_device *deco16ic;
okim6295_device *oki1;
okim6295_device *oki2;
required_device<cpu_device> maincpu;
required_device<cpu_device> audiocpu;
required_device<deco16ic_device> deco16ic;
required_device<okim6295_device> oki1;
required_device<okim6295_device> oki2;
};

View File

@ -12,11 +12,11 @@ class cninja_state : public driver_device
public:
cninja_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
audiocpu(machine.device<cpu_device>("audiocpu")),
deco16ic(machine.device<deco16ic_device>("deco_custom")),
raster_irq_timer(machine.device<timer_device>("raster_timer")),
oki2(machine.device<okim6295_device>("oki2")) { }
maincpu(*this, "maincpu"),
audiocpu(*this, "audiocpu"),
deco16ic(*this, "deco_custom"),
raster_irq_timer(*this, "raster_timer"),
oki2(*this, "oki2") { }
/* memory pointers */
UINT16 * ram;
@ -29,11 +29,11 @@ public:
int scanline, irq_mask;
/* devices */
cpu_device *maincpu;
cpu_device *audiocpu;
deco16ic_device *deco16ic;
timer_device *raster_irq_timer;
okim6295_device *oki2;
required_device<cpu_device> maincpu;
required_device<cpu_device> audiocpu;
required_device<deco16ic_device> deco16ic;
required_device<timer_device> raster_irq_timer;
required_device<okim6295_device> oki2;
};
/*----------- defined in video/cninja.c -----------*/

View File

@ -12,11 +12,11 @@ class dassault_state : public driver_device
public:
dassault_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
audiocpu(machine.device<cpu_device>("audiocpu")),
subcpu(machine.device<cpu_device>("sub")),
deco16ic(machine.device<deco16ic_device>("deco_custom")),
oki2(machine.device<okim6295_device>("oki2")) { }
maincpu(*this, "maincpu"),
audiocpu(*this, "audiocpu"),
subcpu(*this, "sub"),
deco16ic(*this, "deco_custom"),
oki2(*this, "oki2") { }
/* memory pointers */
UINT16 * pf2_rowscroll;
@ -26,11 +26,11 @@ public:
UINT16 * shared_ram;
/* devices */
cpu_device *maincpu;
cpu_device *audiocpu;
cpu_device *subcpu;
deco16ic_device *deco16ic;
okim6295_device *oki2;
required_device<cpu_device> maincpu;
required_device<cpu_device> audiocpu;
required_device<cpu_device> subcpu;
required_device<deco16ic_device> deco16ic;
required_device<okim6295_device> oki2;
};

View File

@ -6,8 +6,8 @@ class drgnmst_state : public driver_device
public:
drgnmst_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
oki_1(machine.device<okim6295_device>("oki1")),
oki_2(machine.device<okim6295_device>("oki2")) { }
oki_1(*this, "oki1"),
oki_2(*this, "oki2") { }
/* memory pointers */
UINT16 * vidregs;
@ -33,8 +33,8 @@ public:
UINT8 oki1_bank;
/* devices */
okim6295_device *oki_1;
okim6295_device *oki_2;
required_device<okim6295_device> oki_1;
required_device<okim6295_device> oki_2;
};

View File

@ -7,9 +7,9 @@ class gcpinbal_state : public driver_device
public:
gcpinbal_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
oki(machine.device<okim6295_device>("oki")),
msm(machine.device<msm5205_device>("msm")) { }
maincpu(*this, "maincpu"),
oki(*this, "oki"),
msm(*this, "msm") { }
/* memory pointers */
UINT16 * tilemapram;
@ -32,9 +32,9 @@ public:
UINT8 adpcm_trigger, adpcm_data;
/* devices */
cpu_device *maincpu;
okim6295_device *oki;
msm5205_device *msm;
required_device<cpu_device> maincpu;
required_device<okim6295_device> oki;
required_device<msm5205_device> msm;
};

View File

@ -11,28 +11,24 @@ class harddriv_state : public atarigen_state
{
public:
harddriv_state(running_machine &machine, const driver_device_config_base &config)
: atarigen_state(machine, config) { }
: atarigen_state(machine, config),
maincpu(*this, "maincpu"),
gsp(*this, "gsp"),
msp(*this, "msp"),
adsp(*this, "adsp"),
soundcpu(*this, "soundcpu"),
sounddsp(*this, "sounddsp"),
jsacpu(*this, "jsacpu"),
dsp32(*this, "dsp32") { }
virtual void find_devices()
{
required_device(maincpu, "maincpu");
required_device(gsp, "gsp");
optional_device(msp, "msp");
required_device(adsp, "adsp");
optional_device(soundcpu, "soundcpu");
optional_device(sounddsp, "sounddsp");
optional_device(jsacpu, "jsacpu");
optional_device(dsp32, "dsp32");
}
cpu_device * maincpu;
tms34010_device * gsp;
cpu_device * msp;
cpu_device * adsp;
cpu_device * soundcpu;
cpu_device * sounddsp;
cpu_device * jsacpu;
cpu_device * dsp32;
required_device<cpu_device> maincpu;
required_device<tms34010_device> gsp;
optional_device<cpu_device> msp;
required_device<cpu_device> adsp;
optional_device<cpu_device> soundcpu;
optional_device<cpu_device> sounddsp;
optional_device<cpu_device> jsacpu;
optional_device<cpu_device> dsp32;
UINT8 hd34010_host_access;
UINT8 dsk_pio_access;

View File

@ -12,8 +12,8 @@ class kickgoal_state : public driver_device
public:
kickgoal_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
adpcm(machine.device<okim6295_device>("oki")),
eeprom(machine.device<eeprom_device>("eeprom")) { }
adpcm(*this, "oki"),
eeprom(*this, "eeprom") { }
/* memory pointers */
UINT16 * fgram;
@ -34,8 +34,8 @@ public:
UINT16 m6295_key_delay;
/* devices */
okim6295_device *adpcm;
eeprom_device *eeprom;
required_device<okim6295_device> adpcm;
required_device<eeprom_device> eeprom;
};

View File

@ -13,11 +13,11 @@ class metro_state : public driver_device
public:
metro_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
audiocpu(machine.device<cpu_device>("audiocpu")),
oki(machine.device<okim6295_device>("oki")),
ymsnd(machine.device("ymsnd")),
k053936(machine.device<k053936_device>("k053936")) { }
maincpu(*this, "maincpu"),
audiocpu(*this, "audiocpu"),
oki(*this, "oki"),
ymsnd(*this, "ymsnd"),
k053936(*this, "k053936") { }
/* memory pointers */
UINT16 * vram_0;
@ -80,11 +80,11 @@ public:
tilemap_t *vmetal_mid2tilemap;
/* devices */
cpu_device *maincpu;
cpu_device *audiocpu;
okim6295_device *oki;
device_t *ymsnd;
k053936_device *k053936;
required_device<cpu_device> maincpu;
required_device<cpu_device> audiocpu;
required_device<okim6295_device> oki;
required_device<device_t> ymsnd;
required_device<k053936_device> k053936;
};

View File

@ -11,8 +11,8 @@ class mitchell_state : public driver_device
public:
mitchell_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
audiocpu(machine.device<cpu_device>("audiocpu")),
oki(machine.device<okim6295_device>("oki")) { }
audiocpu(*this, "audiocpu"),
oki(*this, "oki") { }
/* memory pointers */
UINT8 * videoram;
@ -37,8 +37,8 @@ public:
int keymatrix;
/* devices */
cpu_device *audiocpu;
okim6295_device *oki;
required_device<cpu_device> audiocpu;
required_device<okim6295_device> oki;
};

View File

@ -12,11 +12,11 @@ class rohga_state : public driver_device
public:
rohga_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
audiocpu(machine.device<cpu_device>("audiocpu")),
deco16ic(machine.device<deco16ic_device>("deco_custom")),
oki1(machine.device<okim6295_device>("oki1")),
oki2(machine.device<okim6295_device>("oki2")) { }
maincpu(*this, "maincpu"),
audiocpu(*this, "audiocpu"),
deco16ic(*this, "deco_custom"),
oki1(*this, "oki1"),
oki2(*this, "oki2") { }
/* memory pointers */
UINT16 * pf1_rowscroll;
@ -26,11 +26,11 @@ public:
UINT16 * spriteram;
/* devices */
cpu_device *maincpu;
cpu_device *audiocpu;
deco16ic_device *deco16ic;
okim6295_device *oki1;
okim6295_device *oki2;
required_device<cpu_device> maincpu;
required_device<cpu_device> audiocpu;
required_device<deco16ic_device> deco16ic;
required_device<okim6295_device> oki1;
required_device<okim6295_device> oki2;
};

View File

@ -4,7 +4,7 @@ class segas1x_state : public driver_device
public:
segas1x_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
interrupt_timer(machine.device<timer_device>("int_timer")) { }
interrupt_timer(*this, "int_timer") { }
/* memory pointers */
// UINT16 * workram; // this is used in the nvram handler, hence it cannot be added here
@ -92,7 +92,7 @@ public:
running_device *n7751;
running_device *ppi8255_1;
running_device *ppi8255_2;
timer_device *interrupt_timer;
required_device<timer_device> interrupt_timer;
running_device *_315_5248_1;
running_device *_315_5250_1;
running_device *_315_5250_2;

View File

@ -13,10 +13,10 @@ class simpl156_state : public driver_device
public:
simpl156_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
maincpu(machine.device<cpu_device>("maincpu")),
deco16ic(machine.device<deco16ic_device>("deco_custom")),
eeprom(machine.device<eeprom_device>("eeprom")),
okimusic(machine.device<okim6295_device>("okimusic")) { }
maincpu(*this, "maincpu"),
deco16ic(*this, "deco_custom"),
eeprom(*this, "eeprom"),
okimusic(*this, "okimusic") { }
/* memory pointers */
UINT16 * pf1_rowscroll;
@ -25,10 +25,10 @@ public:
UINT32 * systemram;
/* devices */
cpu_device *maincpu;
deco16ic_device *deco16ic;
eeprom_device *eeprom;
okim6295_device *okimusic;
required_device<cpu_device> maincpu;
required_device<deco16ic_device> deco16ic;
required_device<eeprom_device> eeprom;
required_device<okim6295_device> okimusic;
};

View File

@ -15,7 +15,7 @@ class taitof2_state : public driver_device
public:
taitof2_state(running_machine &machine, const driver_device_config_base &config)
: driver_device(machine, config),
oki(machine.device<okim6295_device>("oki")) { }
oki(*this, "oki") { }
/* memory pointers */
UINT16 * sprite_extension;
@ -68,7 +68,7 @@ public:
/* devices */
running_device *maincpu;
running_device *audiocpu;
okim6295_device *oki;
required_device<okim6295_device> oki;
running_device *tc0100scn;
running_device *tc0100scn_1;
running_device *tc0100scn_2;