Declared virtual functions in driver_data_t for:

machine_start
  machine_reset

  sound_start
  sound_reset

  palette_init
  video_start
  video_reset
  video_update
  video_eof

The default implementations of these call through the machine
configuration's functions as before. However, if a driver_data_t
overrides them, it will be called instead.

Also added virtual functions for pre_save() and post_load(),
which can be overridden to implement machine driver-specific
pre-save/post-load functionality instead of registering with
the save state system.

Updated beathead to use these new virtual functions instead of
specifying callbacks in the MACHINE_DRIVER.
This commit is contained in:
Aaron Giles 2010-08-21 23:13:26 +00:00
parent aa42ebcb51
commit d0cb76c6fe
6 changed files with 218 additions and 61 deletions

View File

@ -203,6 +203,8 @@ running_machine::running_machine(const game_driver &driver, const machine_config
// allocate the driver data (after devices)
if (m_config.m_driver_data_alloc != NULL)
m_driver_data = (*m_config.m_driver_data_alloc)(*this);
else
m_driver_data = auto_alloc(this, driver_data_t(*this));
// find devices
primary_screen = screen_first(*this);
@ -267,6 +269,8 @@ void running_machine::start()
output_init(this);
state_init(this);
state_save_allow_registration(this, true);
state_save_register_presave(this, pre_save_static, NULL);
state_save_register_postload(this, post_load_static, NULL);
palette_init(this);
render_init(this);
ui_init(this);
@ -338,12 +342,9 @@ void running_machine::start()
debugger_init(this);
// call the driver's _START callbacks
if (m_config.m_machine_start != NULL)
(*m_config.m_machine_start)(this);
if (m_config.m_sound_start != NULL)
(*m_config.m_sound_start)(this);
if (m_config.m_video_start != NULL)
(*m_config.m_video_start)(this);
m_driver_data->machine_start();
m_driver_data->sound_start();
m_driver_data->video_start();
// if we're coming in with a savegame request, process it now
const char *savegame = options_get_string(&m_options, OPTION_STATE);
@ -862,6 +863,28 @@ cancel:
}
//-------------------------------------------------
// pre_save_static - callback to prepare for
// state saving
//-------------------------------------------------
STATE_PRESAVE( running_machine::pre_save_static )
{
machine->m_driver_data->pre_save();
}
//-------------------------------------------------
// post_load_static - callback to update after
// static loading
//-------------------------------------------------
STATE_POSTLOAD( running_machine::post_load_static )
{
machine->m_driver_data->post_load();
}
//-------------------------------------------------
// soft_reset - actually perform a soft-reset
// of the system
@ -880,12 +903,9 @@ void running_machine::soft_reset()
call_notifiers(MACHINE_NOTIFY_RESET);
// run the driver's reset callbacks
if (m_config.m_machine_reset != NULL)
(*m_config.m_machine_reset)(this);
if (m_config.m_sound_reset != NULL)
(*m_config.m_sound_reset)(this);
if (m_config.m_video_reset != NULL)
(*m_config.m_video_reset)(this);
m_driver_data->machine_reset();
m_driver_data->sound_reset();
m_driver_data->video_reset();
// now we're running
m_current_phase = MACHINE_PHASE_RUNNING;
@ -988,6 +1008,135 @@ driver_data_t::~driver_data_t()
}
//-------------------------------------------------
// machine_start - default implementation which
// calls to the legacy machine_start function
//-------------------------------------------------
void driver_data_t::machine_start()
{
if (m_machine.m_config.m_machine_start != NULL)
(*m_machine.m_config.m_machine_start)(&m_machine);
}
//-------------------------------------------------
// machine_reset - default implementation which
// calls to the legacy machine_reset function
//-------------------------------------------------
void driver_data_t::machine_reset()
{
if (m_machine.m_config.m_machine_reset != NULL)
(*m_machine.m_config.m_machine_reset)(&m_machine);
}
//-------------------------------------------------
// sound_start - default implementation which
// calls to the legacy sound_start function
//-------------------------------------------------
void driver_data_t::sound_start()
{
if (m_machine.m_config.m_sound_start != NULL)
(*m_machine.m_config.m_sound_start)(&m_machine);
}
//-------------------------------------------------
// sound_reset - default implementation which
// calls to the legacy sound_reset function
//-------------------------------------------------
void driver_data_t::sound_reset()
{
if (m_machine.m_config.m_sound_reset != NULL)
(*m_machine.m_config.m_sound_reset)(&m_machine);
}
//-------------------------------------------------
// palette_init - default implementation which
// calls to the legacy palette_init function
//-------------------------------------------------
void driver_data_t::palette_init(const UINT8 *color_prom)
{
if (m_machine.m_config.m_init_palette != NULL)
(*m_machine.m_config.m_init_palette)(&m_machine, color_prom);
}
//-------------------------------------------------
// video_start - default implementation which
// calls to the legacy video_start function
//-------------------------------------------------
void driver_data_t::video_start()
{
if (m_machine.m_config.m_video_start != NULL)
(*m_machine.m_config.m_video_start)(&m_machine);
}
//-------------------------------------------------
// video_reset - default implementation which
// calls to the legacy video_reset function
//-------------------------------------------------
void driver_data_t::video_reset()
{
if (m_machine.m_config.m_video_reset != NULL)
(*m_machine.m_config.m_video_reset)(&m_machine);
}
//-------------------------------------------------
// video_update - default implementation which
// calls to the legacy video_update function
//-------------------------------------------------
bool driver_data_t::video_update(screen_device &screen, bitmap_t &bitmap, const rectangle &cliprect)
{
if (m_machine.m_config.m_video_update != NULL)
return (*m_machine.m_config.m_video_update)(&screen, &bitmap, &cliprect);
return 0;
}
//-------------------------------------------------
// video_eof - default implementation which
// calls to the legacy video_eof function
//-------------------------------------------------
void driver_data_t::video_eof()
{
if (m_machine.m_config.m_video_eof != NULL)
(*m_machine.m_config.m_video_eof)(&m_machine);
}
//-------------------------------------------------
// pre_save - default implementation which
// does nothing
//-------------------------------------------------
void driver_data_t::pre_save()
{
}
//-------------------------------------------------
// post_load - default implementation which
// does nothing
//-------------------------------------------------
void driver_data_t::post_load()
{
}
//**************************************************************************
// SYSTEM TIME

View File

@ -160,10 +160,27 @@ typedef tagged_list<region_info> region_list;
// base class for all driver data structures
class driver_data_t : public bindable_object
{
friend class running_machine;
public:
driver_data_t(running_machine &machine);
virtual ~driver_data_t();
virtual void machine_start();
virtual void machine_reset();
virtual void sound_start();
virtual void sound_reset();
virtual void palette_init(const UINT8 *color_prom);
virtual void video_start();
virtual void video_reset();
virtual bool video_update(screen_device &screen, bitmap_t &bitmap, const rectangle &cliprect);
virtual void video_eof();
virtual void pre_save();
virtual void post_load();
running_machine & m_machine;
};
@ -406,6 +423,8 @@ private:
void set_saveload_filename(const char *filename);
void fill_systime(system_time &systime, time_t t);
void handle_saveload();
static STATE_PRESAVE( pre_save_static );
static STATE_POSTLOAD( post_load_static );
static TIMER_CALLBACK( static_soft_reset );
void soft_reset();

View File

@ -297,8 +297,7 @@ void video_init(running_machine *machine)
init_buffered_spriteram(machine);
/* call the PALETTE_INIT function */
if (machine->config->m_init_palette != NULL)
(*machine->config->m_init_palette)(machine, memory_region(machine, "proms"));
machine->driver_data<driver_data_t>()->palette_init(memory_region(machine, "proms"));
/* create a render target for snapshots */
viewname = options_get_string(machine->options(), OPTION_SNAPVIEW);
@ -485,10 +484,10 @@ void video_frame_update(running_machine *machine, int debug)
machine->primary_screen->scanline0_callback();
/* otherwise, call the video EOF callback */
else if (machine->config->m_video_eof != NULL)
else
{
g_profiler.start(PROFILER_VIDEO);
(*machine->config->m_video_eof)(machine);
machine->driver_data<driver_data_t>()->video_eof();
g_profiler.stop();
}
}
@ -2121,8 +2120,7 @@ bool screen_device::update_partial(int scanline)
g_profiler.start(PROFILER_VIDEO);
LOG_PARTIAL_UPDATES(("updating %d-%d\n", clip.min_y, clip.max_y));
if (machine->config->m_video_update != NULL)
flags = (*machine->config->m_video_update)(this, m_bitmap[m_curbitmap], &clip);
flags = machine->driver_data<driver_data_t>()->video_update(*this, *m_bitmap[m_curbitmap], clip);
global.partial_updates_this_frame++;
g_profiler.stop();

View File

@ -138,35 +138,33 @@ static TIMER_DEVICE_CALLBACK( scanline_callback )
}
static MACHINE_START( beathead )
void beathead_state::machine_start()
{
atarigen_init(machine);
atarigen_init(&m_machine);
}
static void update_interrupts(running_machine *machine) { machine->driver_data<beathead_state>()->update_interrupts(); }
static MACHINE_RESET( beathead )
void beathead_state::machine_reset()
{
beathead_state *state = machine->driver_data<beathead_state>();
/* reset the common subsystems */
atarigen_eeprom_reset(state);
atarigen_interrupt_reset(state, update_interrupts);
atarigen_eeprom_reset(this);
atarigen_interrupt_reset(this, ::update_interrupts);
atarijsa_reset();
/* the code is temporarily mapped at 0 at startup */
/* just copying the first 0x40 bytes is sufficient */
memcpy(state->m_ram_base, state->m_rom_base, 0x40);
memcpy(m_ram_base, m_rom_base, 0x40);
/* compute the timing of the HBLANK interrupt and set the first timer */
state->m_hblank_offset = attotime_to_double(machine->primary_screen->scan_period()) * ((455. - 336. - 25.) / 455.);
timer_device *scanline_timer = machine->device<timer_device>("scan_timer");
scanline_timer->adjust(double_to_attotime(attotime_to_double(machine->primary_screen->time_until_pos(0)) - state->m_hblank_offset));
m_hblank_offset = attotime_to_double(m_machine.primary_screen->scan_period()) * ((455. - 336. - 25.) / 455.);
timer_device *scanline_timer = m_machine.device<timer_device>("scan_timer");
scanline_timer->adjust(double_to_attotime(attotime_to_double(m_machine.primary_screen->time_until_pos(0)) - m_hblank_offset));
/* reset IRQs */
state->m_irq_line_state = CLEAR_LINE;
state->m_irq_state[0] = state->m_irq_state[1] = state->m_irq_state[2] = 0;
state->m_irq_enable[0] = state->m_irq_enable[1] = state->m_irq_enable[2] = 0;
m_irq_line_state = CLEAR_LINE;
m_irq_state[0] = m_irq_state[1] = m_irq_state[2] = 0;
m_irq_enable[0] = m_irq_enable[1] = m_irq_enable[2] = 0;
}
@ -401,8 +399,6 @@ static MACHINE_DRIVER_START( beathead )
MDRV_CPU_ADD("maincpu", ASAP, ATARI_CLOCK_14MHz)
MDRV_CPU_PROGRAM_MAP(main_map)
MDRV_MACHINE_START(beathead)
MDRV_MACHINE_RESET(beathead)
MDRV_NVRAM_HANDLER(generic_1fill)
MDRV_TIMER_ADD("scan_timer", scanline_callback)
@ -417,9 +413,6 @@ static MACHINE_DRIVER_START( beathead )
MDRV_SCREEN_VISIBLE_AREA(0*8, 42*8-1, 0*8, 30*8-1)
MDRV_PALETTE_LENGTH(32768)
MDRV_VIDEO_START(beathead)
MDRV_VIDEO_UPDATE(beathead)
/* sound hardware */
MDRV_IMPORT_FROM(jsa_iii_mono)
MACHINE_DRIVER_END

View File

@ -17,6 +17,12 @@ public:
: atarigen_state(machine),
m_maincpu(*machine.device<asap_device>("maincpu")) { }
virtual void machine_start();
virtual void machine_reset();
virtual void video_start();
virtual bool video_update(screen_device &screen, bitmap_t &bitmap, const rectangle &cliprect);
asap_device & m_maincpu;
UINT32 * m_videoram;
@ -70,9 +76,3 @@ public:
DECLARE_READ32_MEMBER( hsync_ram_r );
DECLARE_WRITE32_MEMBER( hsync_ram_w );
};
/*----------- defined in video/beathead.c -----------*/
VIDEO_START( beathead );
VIDEO_UPDATE( beathead );

View File

@ -15,14 +15,13 @@
*
*************************************/
VIDEO_START( beathead )
void beathead_state::video_start()
{
beathead_state *state = machine->driver_data<beathead_state>();
state_save_register_global(machine, state->m_finescroll);
state_save_register_global(machine, state->m_vram_latch_offset);
state_save_register_global(machine, state->m_hsyncram_offset);
state_save_register_global(machine, state->m_hsyncram_start);
state_save_register_global_array(machine, state->m_hsyncram);
state_save_register_global(&m_machine, m_finescroll);
state_save_register_global(&m_machine, m_vram_latch_offset);
state_save_register_global(&m_machine, m_hsyncram_offset);
state_save_register_global(&m_machine, m_hsyncram_start);
state_save_register_global_array(&m_machine, m_hsyncram);
}
@ -155,36 +154,35 @@ WRITE32_MEMBER( beathead_state::hsync_ram_w )
*
*************************************/
VIDEO_UPDATE( beathead )
bool beathead_state::video_update(screen_device &screen, bitmap_t &bitmap, const rectangle &cliprect)
{
beathead_state *state = screen->machine->driver_data<beathead_state>();
UINT8 *videoram = reinterpret_cast<UINT8 *>(state->m_videoram);
UINT8 *videoram = reinterpret_cast<UINT8 *>(m_videoram);
int x, y;
/* generate the final screen */
for (y = cliprect->min_y; y <= cliprect->max_y; y++)
for (y = cliprect.min_y; y <= cliprect.max_y; y++)
{
pen_t pen_base = (*state->m_palette_select & 0x7f) * 256;
pen_t pen_base = (*m_palette_select & 0x7f) * 256;
UINT16 scanline[336];
/* blanking */
if (state->m_finescroll & 8)
for (x = cliprect->min_x; x <= cliprect->max_x; x++)
if (m_finescroll & 8)
for (x = cliprect.min_x; x <= cliprect.max_x; x++)
scanline[x] = pen_base;
/* non-blanking */
else
{
offs_t scanline_offset = state->m_vram_latch_offset + (state->m_finescroll & 3);
offs_t src = scanline_offset + cliprect->min_x;
offs_t scanline_offset = m_vram_latch_offset + (m_finescroll & 3);
offs_t src = scanline_offset + cliprect.min_x;
/* unswizzle the scanline first */
for (x = cliprect->min_x; x <= cliprect->max_x; x++)
for (x = cliprect.min_x; x <= cliprect.max_x; x++)
scanline[x] = pen_base | videoram[BYTE4_XOR_LE(src++)];
}
/* then draw it */
draw_scanline16(bitmap, cliprect->min_x, y, cliprect->max_x - cliprect->min_x + 1, &scanline[cliprect->min_x], NULL);
draw_scanline16(&bitmap, cliprect.min_x, y, cliprect.max_x - cliprect.min_x + 1, &scanline[cliprect.min_x], NULL);
}
return 0;
}