modernised CDDA & discard buffered samples when starting to play to avoid audio glitches and timing issues. [smf]

This commit is contained in:
smf- 2013-05-13 23:35:54 +00:00
parent 2541335959
commit 8dba8bdf40
14 changed files with 276 additions and 431 deletions

View File

@ -51,7 +51,7 @@ struct matsucd
void (*stch_cb)( running_machine &machine, int level ); /* Status changed callback */
void (*scor_cb)( running_machine &machine, int level ); /* Subcode ready callback */
cdrom_file *cdrom;
device_t *cdda;
cdda_device *cdda;
emu_timer *frame_timer;
};
@ -67,7 +67,7 @@ void matsucd_init( cdrom_image_device *cdrom_device, const char *cdda_tag )
memset(&cd, 0, sizeof( matsucd ) );
cd.cdrom = cdrom_device->get_cdrom_file();
cd.cdda = cdrom_device->machine().device(cdda_tag);
cd.cdda = cdrom_device->machine().device<cdda_device>(cdda_tag);
cd.frame_timer = cdrom_device->machine().scheduler().timer_alloc(FUNC(matsu_subcode_proc));
@ -137,31 +137,27 @@ int matsucd_get_next_byte( UINT8 *data )
static void matsucd_cdda_stop( running_machine &machine )
{
device_t *cdda = cdda_from_cdrom(machine, cd.cdrom);
if (cdda != NULL)
if (cd.cdda != NULL)
{
cdda_stop_audio(cdda);
cd.cdda->stop_audio();
cd.frame_timer->reset( );
}
}
static void matsucd_cdda_play( running_machine &machine, UINT32 lba, UINT32 num_blocks )
{
device_t *cdda = cdda_from_cdrom(machine, cd.cdrom);
if (cdda != NULL)
if (cd.cdda != NULL)
{
cdda_start_audio(cdda, lba, num_blocks);
cd.cdda->start_audio(lba, num_blocks);
cd.frame_timer->adjust(attotime::from_hz( 75 ));
}
}
static void matsucd_cdda_pause( running_machine &machine, int pause )
{
device_t *cdda = cdda_from_cdrom(machine, cd.cdrom);
if (cdda != NULL)
if (cd.cdda != NULL)
{
cdda_pause_audio(cdda, pause);
cd.cdda->pause_audio(pause);
if ( pause )
{
@ -176,17 +172,15 @@ static void matsucd_cdda_pause( running_machine &machine, int pause )
static UINT8 matsucd_cdda_getstatus( running_machine &machine, UINT32 *lba )
{
device_t *cdda = cdda_from_cdrom(machine, cd.cdrom);
if ( lba ) *lba = 0;
if (cdda != NULL)
if (cd.cdda != NULL)
{
if (cdda_audio_active(cdda))
if (cd.cdda->audio_active())
{
if ( lba ) *lba = cdda_get_audio_lba(cdda);
if ( lba ) *lba = cd.cdda->get_audio_lba();
if (cdda_audio_paused(cdda))
if (cd.cdda->audio_paused())
{
return 0x12; /* audio paused */
}
@ -195,7 +189,7 @@ static UINT8 matsucd_cdda_getstatus( running_machine &machine, UINT32 *lba )
return 0x11; /* audio in progress */
}
}
else if (cdda_audio_ended(cdda))
else if (cd.cdda->audio_ended())
{
return 0x13; /* audio ended */
}
@ -280,11 +274,9 @@ static void matsucd_set_status( running_machine &machine, UINT8 status )
static TIMER_CALLBACK(matsu_subcode_proc)
{
device_t *cdda = cdda_from_cdrom(machine, cd.cdrom);
(void)param;
if (cdda != NULL)
if (cd.cdda != NULL)
{
UINT8 s = matsucd_cdda_getstatus(machine, NULL);
UINT8 newstatus = cd.status;
@ -364,11 +356,8 @@ void matsucd_command_w( running_machine &machine, UINT8 data )
if ( cd.cdda_set == 0 )
{
// 2009-10, FP: for some reason, cdda_from_cdrom was not returning the correct
// CDDA device. Hence, as a temp workaround, I added the cdda to the struct
// and its tag is configured in matsucd_init
if ( cd.cdrom )
cdda_set_cdrom( cd.cdda, cd.cdrom);
cd.cdda->set_cdrom(cd.cdrom);
cd.cdda_set = 1;
}

View File

@ -7,7 +7,6 @@
#include "emu.h"
#include "machine/scsihle.h"
#include "cdrom.h"
#include "sound/cdda.h"
#include "imagedev/chd_cd.h"
#include "scsicd.h"
@ -23,12 +22,14 @@ static void phys_frame_to_msf(int phys_frame, int *m, int *s, int *f)
const device_type SCSICD = &device_creator<scsicd_device>;
scsicd_device::scsicd_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
: scsihle_device(mconfig, SCSICD, "SCSICD", tag, owner, clock, "scsicd", __FILE__)
: scsihle_device(mconfig, SCSICD, "SCSICD", tag, owner, clock, "scsicd", __FILE__),
m_cdda(*this, "cdda")
{
}
scsicd_device::scsicd_device(const machine_config &mconfig, device_type type, const char *name, const char *tag, device_t *owner, UINT32 clock, const char *shortname, const char *source) :
scsihle_device(mconfig, type, name, tag, owner, clock, shortname, source)
scsihle_device(mconfig, type, name, tag, owner, clock, shortname, source),
m_cdda(*this, "cdda")
{
}
@ -82,7 +83,6 @@ machine_config_constructor scsicd_device::device_mconfig_additions() const
void scsicd_device::ExecCommand( int *transferLength )
{
device_t *cdda;
int trk;
switch ( command[0] )
@ -110,11 +110,7 @@ void scsicd_device::ExecCommand( int *transferLength )
break;
case 0x1b: // START STOP UNIT
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
{
cdda_stop_audio(cdda);
}
m_cdda->stop_audio();
SetPhase( SCSI_PHASE_STATUS );
*transferLength = 0;
break;
@ -146,11 +142,7 @@ void scsicd_device::ExecCommand( int *transferLength )
cur_subblock = 0;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
{
cdda_stop_audio(cdda);
}
m_cdda->stop_audio();
SetPhase( SCSI_PHASE_DATAIN );
*transferLength = blocks * bytes_per_sector;
@ -188,11 +180,7 @@ void scsicd_device::ExecCommand( int *transferLength )
length = 4;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
{
cdda_stop_audio(cdda);
}
m_cdda->stop_audio();
SetPhase( SCSI_PHASE_DATAIN );
*transferLength = length;
@ -219,9 +207,7 @@ void scsicd_device::ExecCommand( int *transferLength )
if (cdrom_get_track_type(cdrom, trk) == CD_TRACK_AUDIO)
{
play_err_flag = 0;
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
m_cdda->start_audio(lba, blocks);
}
else
{
@ -250,9 +236,7 @@ void scsicd_device::ExecCommand( int *transferLength )
if (blocks && cdrom)
{
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
m_cdda->start_audio(lba, blocks);
}
logerror("SCSICD: PLAY AUDIO T/I: strk %d idx %d etrk %d idx %d frames %d\n", command[4], command[5], command[7], command[8], blocks);
@ -263,9 +247,7 @@ void scsicd_device::ExecCommand( int *transferLength )
case 0x4b: // PAUSE/RESUME
if (cdrom)
{
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_pause_audio(cdda, (command[8] & 0x01) ^ 0x01);
m_cdda->pause_audio((command[8] & 0x01) ^ 0x01);
}
logerror("SCSICD: PAUSE/RESUME: %s\n", command[8]&1 ? "RESUME" : "PAUSE");
@ -276,9 +258,7 @@ void scsicd_device::ExecCommand( int *transferLength )
case 0x4e: // STOP
if (cdrom)
{
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
logerror("SCSICD: STOP_PLAY_SCAN\n");
@ -318,9 +298,7 @@ void scsicd_device::ExecCommand( int *transferLength )
if (cdrom_get_track_type(cdrom, trk) == CD_TRACK_AUDIO)
{
play_err_flag = 0;
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
m_cdda->start_audio(lba, blocks);
}
else
{
@ -347,11 +325,7 @@ void scsicd_device::ExecCommand( int *transferLength )
cur_subblock = 0;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
{
cdda_stop_audio(cdda);
}
m_cdda->stop_audio();
SetPhase( SCSI_PHASE_DATAIN );
*transferLength = blocks * bytes_per_sector;
@ -378,7 +352,6 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
UINT32 last_phys_frame;
UINT32 temp;
UINT8 tmp_buffer[2048];
device_t *cdda;
switch ( command[0] )
{
@ -389,8 +362,7 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
data[0] = 0x71; // deferred error
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL && cdda_audio_active(cdda))
if (m_cdda->audio_active())
{
data[12] = 0x00;
data[13] = 0x11; // AUDIO PLAY OPERATION IN PROGRESS
@ -470,7 +442,6 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
{
case 1: // return current position
{
int audio_active;
int msf;
if (!cdrom)
@ -482,11 +453,12 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
msf = command[1] & 0x2;
cdda = cdda_from_cdrom(machine(), cdrom);
audio_active = cdda != NULL && cdda_audio_active(cdda);
int audio_active = m_cdda->audio_active();
if (audio_active)
{
if (cdda_audio_paused(cdda))
// if audio is playing, get the latest LBA from the CDROM layer
last_lba = m_cdda->get_audio_lba();
if (m_cdda->audio_paused())
{
data[1] = 0x12; // audio is paused
}
@ -497,7 +469,8 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
}
else
{
if (cdda != NULL && cdda_audio_ended(cdda))
last_lba = 0;
if (m_cdda->audio_ended())
{
data[1] = 0x13; // ended successfully
}
@ -508,16 +481,6 @@ void scsicd_device::ReadData( UINT8 *data, int dataLength )
}
}
// if audio is playing, get the latest LBA from the CDROM layer
if (audio_active)
{
last_lba = cdda_get_audio_lba(cdda);
}
else
{
last_lba = 0;
}
data[2] = 0;
data[3] = 12; // data length
data[4] = 0x01; // sub-channel format code
@ -752,7 +715,7 @@ void scsicd_device::GetDevice( void **_cdrom )
void scsicd_device::SetDevice( void *_cdrom )
{
cdrom = (cdrom_file *)_cdrom;
cdda_set_cdrom(subdevice("cdda"), cdrom);
m_cdda->set_cdrom(cdrom);
}
int scsicd_device::GetSectorBytes()

View File

@ -8,6 +8,7 @@
#define _SCSICD_H_
#include "machine/scsihle.h"
#include "sound/cdda.h"
#include "cdrom.h"
class scsicd_device : public scsihle_device
@ -33,6 +34,7 @@ protected:
virtual void device_reset();
private:
required_device<cdda_device> m_cdda;
UINT32 lba;
UINT32 blocks;
UINT32 last_lba;

View File

@ -364,7 +364,7 @@ void saturn_state::cd_exec_command( void )
cur_track = (start_pos)>>8;
cd_fad_seek = cdrom_get_track_start(cdrom, cur_track-1);
cd_stat = CD_STAT_SEEK;
cdda_pause_audio( machine().device( "cdda" ), 0 );
machine().device<cdda_device>("cdda")->pause_audio(0);
}
else
{
@ -437,8 +437,8 @@ void saturn_state::cd_exec_command( void )
// cdda
if(cdrom_get_track_type(cdrom, cdrom_get_track(cdrom, cd_curfad)) == CD_TRACK_AUDIO)
{
cdda_pause_audio( machine().device( "cdda" ), 0 );
//cdda_start_audio( machine.device( "cdda" ), cd_curfad, fadstoplay );
machine().device<cdda_device>("cdda")->pause_audio(0);
//machine().device<cdda_device>("cdda")->start_audio(cd_curfad, fadstoplay);
//cdda_repeat_count = 0;
}
@ -464,7 +464,7 @@ void saturn_state::cd_exec_command( void )
if (temp == 0xffffff)
{
cd_stat = CD_STAT_PAUSE;
cdda_pause_audio( machine().device( "cdda" ), 1 );
machine().device<cdda_device>("cdda")->pause_audio(1);
}
else
{
@ -480,7 +480,7 @@ void saturn_state::cd_exec_command( void )
cd_stat = CD_STAT_PAUSE;
cur_track = cr2>>8;;
cd_curfad = cdrom_get_track_start(cdrom, cur_track-1);
cdda_pause_audio( machine().device( "cdda" ), 1 );
machine().device<cdda_device>("cdda")->pause_audio(1);
// (index is cr2 low byte)
}
else // error!
@ -488,7 +488,7 @@ void saturn_state::cd_exec_command( void )
cd_stat = CD_STAT_STANDBY;
cd_curfad = 0xffffffff;
cur_track = 0xff;
cdda_stop_audio( machine().device( "cdda" ) ); //stop any pending CD-DA
machine().device<cdda_device>("cdda")->stop_audio(); //stop any pending CD-DA
}
}
@ -1477,7 +1477,7 @@ void saturn_state::stvcd_reset( void )
cdrom = cdrom_open(get_disk_handle(machine(), "cdrom"));
}
cdda_set_cdrom( machine().device("cdda"), cdrom );
machine().device<cdda_device>("cdda")->set_cdrom(cdrom);
if (cdrom)
{
@ -2593,12 +2593,12 @@ void saturn_state::cd_playdata( void )
if(cdrom_get_track_type(cdrom, cdrom_get_track(cdrom, cd_curfad)) != CD_TRACK_AUDIO)
{
cd_read_filtered_sector(cd_curfad,&p_ok);
cdda_stop_audio( machine().device( "cdda" ) ); //stop any pending CD-DA
machine().device<cdda_device>("cdda")->stop_audio(); //stop any pending CD-DA
}
else
{
p_ok = 1; // TODO
cdda_start_audio( machine().device( "cdda" ), cd_curfad, 1 );
machine().device<cdda_device>("cdda")->start_audio(cd_curfad, 1);
}
if(p_ok)
@ -2681,7 +2681,7 @@ void saturn_state::stvcd_set_tray_close( void )
cdrom = cdrom_open(get_disk_handle(machine(), "cdrom"));
}
cdda_set_cdrom( machine().device("cdda"), cdrom );
machine().device<cdda_device>("cdda")->set_cdrom(cdrom);
if (cdrom)
{

View File

@ -4,72 +4,49 @@
*/
#include "emu.h"
#include "cdrom.h"
#include "cdda.h"
struct cdda_info
{
sound_stream * stream;
cdrom_file * disc;
INT8 audio_playing, audio_pause, audio_ended_normally;
UINT32 audio_lba, audio_length;
UINT8 * audio_cache;
UINT32 audio_samples;
UINT32 audio_bptr;
INT16 audio_volume[2];
};
INLINE cdda_info *get_safe_token(device_t *device)
{
assert(device != NULL);
assert(device->type() == CDDA);
return (cdda_info *)downcast<cdda_device *>(device)->token();
}
#define MAX_SECTORS ( 4 )
static void get_audio_data(cdda_info *info, stream_sample_t *bufL, stream_sample_t *bufR, UINT32 samples_wanted);
//-------------------------------------------------
// sound_stream_update - handle a stream update
//-------------------------------------------------
/*-------------------------------------------------
cdda_update - stream update callback
-------------------------------------------------*/
static STREAM_UPDATE( cdda_update )
void cdda_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
{
cdda_info *info = (cdda_info *)param;
get_audio_data(info, &outputs[0][0], &outputs[1][0], samples);
info->audio_volume[0] = (INT16)outputs[0][0];
info->audio_volume[1] = (INT16)outputs[1][0];
get_audio_data(&outputs[0][0], &outputs[1][0], samples);
m_audio_volume[0] = (INT16)outputs[0][0];
m_audio_volume[1] = (INT16)outputs[1][0];
}
//-------------------------------------------------
// device_start - device-specific startup
//-------------------------------------------------
/*-------------------------------------------------
DEVICE_START( cdda ) - audio start callback
-------------------------------------------------*/
static DEVICE_START( cdda )
void cdda_device::device_start()
{
//const struct CDDAinterface *intf;
cdda_info *info = get_safe_token(device);
/* allocate an audio cache */
info->audio_cache = auto_alloc_array( device->machine(), UINT8, CD_MAX_SECTOR_DATA * MAX_SECTORS );
m_audio_cache = auto_alloc_array( machine(), UINT8, CD_MAX_SECTOR_DATA * MAX_SECTORS );
//intf = (const struct CDDAinterface *)device->static_config();
m_stream = machine().sound().stream_alloc(*this, 0, 2, 44100);
info->stream = device->machine().sound().stream_alloc(*device, 0, 2, 44100, info, cdda_update);
m_audio_playing = 0;
m_audio_pause = 0;
m_audio_ended_normally = 0;
m_audio_lba = 0;
m_audio_length = 0;
m_audio_samples = 0;
m_audio_bptr = 0;
device->save_item( NAME(info->audio_playing) );
device->save_item( NAME(info->audio_pause) );
device->save_item( NAME(info->audio_ended_normally) );
device->save_item( NAME(info->audio_lba) );
device->save_item( NAME(info->audio_length) );
device->save_pointer( NAME(info->audio_cache), CD_MAX_SECTOR_DATA * MAX_SECTORS );
device->save_item( NAME(info->audio_samples) );
device->save_item( NAME(info->audio_bptr) );
save_item( NAME(m_audio_playing) );
save_item( NAME(m_audio_pause) );
save_item( NAME(m_audio_ended_normally) );
save_item( NAME(m_audio_lba) );
save_item( NAME(m_audio_length) );
save_pointer( NAME(m_audio_cache), CD_MAX_SECTOR_DATA * MAX_SECTORS );
save_item( NAME(m_audio_samples) );
save_item( NAME(m_audio_bptr) );
}
@ -78,30 +55,9 @@ static DEVICE_START( cdda )
given CDDA stream
-------------------------------------------------*/
void cdda_set_cdrom(device_t *device, void *file)
void cdda_device::set_cdrom(void *file)
{
cdda_info *info = get_safe_token(device);
info->disc = (cdrom_file *)file;
}
/*-------------------------------------------------
cdda_from_cdrom - find the CDDA stream
that references the given CD-ROM file
-------------------------------------------------*/
device_t *cdda_from_cdrom(running_machine &machine, void *file)
{
sound_interface_iterator iter(machine.root_device());
for (device_sound_interface *sound = iter.first(); sound != NULL; sound = iter.next())
if (sound->device().type() == CDDA)
{
cdda_info *info = get_safe_token(*sound);
if (info->disc == file)
return *sound;
}
return NULL;
m_disc = (cdrom_file *)file;
}
@ -110,16 +66,15 @@ device_t *cdda_from_cdrom(running_machine &machine, void *file)
Book audio track
-------------------------------------------------*/
void cdda_start_audio(device_t *device, UINT32 startlba, UINT32 numblocks)
void cdda_device::start_audio(UINT32 startlba, UINT32 numblocks)
{
cdda_info *info = get_safe_token(device);
info->stream->update();
info->audio_playing = TRUE;
info->audio_pause = FALSE;
info->audio_ended_normally = FALSE;
info->audio_lba = startlba;
info->audio_length = numblocks;
m_stream->update();
m_audio_playing = TRUE;
m_audio_pause = FALSE;
m_audio_ended_normally = FALSE;
m_audio_lba = startlba;
m_audio_length = numblocks;
m_audio_samples = 0;
}
@ -128,13 +83,11 @@ void cdda_start_audio(device_t *device, UINT32 startlba, UINT32 numblocks)
audio track
-------------------------------------------------*/
void cdda_stop_audio(device_t *device)
void cdda_device::stop_audio()
{
cdda_info *info = get_safe_token(device);
info->stream->update();
info->audio_playing = FALSE;
info->audio_ended_normally = TRUE;
m_stream->update();
m_audio_playing = FALSE;
m_audio_ended_normally = TRUE;
}
@ -143,12 +96,10 @@ void cdda_stop_audio(device_t *device)
a Red Book audio track
-------------------------------------------------*/
void cdda_pause_audio(device_t *device, int pause)
void cdda_device::pause_audio(int pause)
{
cdda_info *info = get_safe_token(device);
info->stream->update();
info->audio_pause = pause;
m_stream->update();
m_audio_pause = pause;
}
@ -157,12 +108,10 @@ void cdda_pause_audio(device_t *device, int pause)
(physical sector) during Red Book playback
-------------------------------------------------*/
UINT32 cdda_get_audio_lba(device_t *device)
UINT32 cdda_device::get_audio_lba()
{
cdda_info *info = get_safe_token(device);
info->stream->update();
return info->audio_lba;
m_stream->update();
return m_audio_lba;
}
@ -171,12 +120,10 @@ UINT32 cdda_get_audio_lba(device_t *device)
playback status
-------------------------------------------------*/
int cdda_audio_active(device_t *device)
int cdda_device::audio_active()
{
cdda_info *info = get_safe_token(device);
info->stream->update();
return info->audio_playing;
m_stream->update();
return m_audio_playing;
}
@ -185,10 +132,9 @@ int cdda_audio_active(device_t *device)
playback is paused
-------------------------------------------------*/
int cdda_audio_paused(device_t *device)
int cdda_device::audio_paused()
{
cdda_info *info = get_safe_token(device);
return info->audio_pause;
return m_audio_pause;
}
@ -197,10 +143,9 @@ int cdda_audio_paused(device_t *device)
track reached it's natural end
-------------------------------------------------*/
int cdda_audio_ended(device_t *device)
int cdda_device::audio_ended()
{
cdda_info *info = get_safe_token(device);
return info->audio_ended_normally;
return m_audio_ended_normally;
}
@ -210,84 +155,66 @@ int cdda_audio_ended(device_t *device)
converts it to 2 16-bit 44.1 kHz streams
-------------------------------------------------*/
static void get_audio_data(cdda_info *info, stream_sample_t *bufL, stream_sample_t *bufR, UINT32 samples_wanted)
void cdda_device::get_audio_data(stream_sample_t *bufL, stream_sample_t *bufR, UINT32 samples_wanted)
{
int i, sectoread, remaining;
INT16 *audio_cache = (INT16 *) info->audio_cache;
int i;
INT16 *audio_cache = (INT16 *) m_audio_cache;
/* if no file, audio not playing, audio paused, or out of disc data,
just zero fill */
if (!info->disc || !info->audio_playing || info->audio_pause || (!info->audio_length && !info->audio_samples))
while (samples_wanted > 0)
{
if( info->disc && info->audio_playing && !info->audio_pause && !info->audio_length )
/* if no file, audio not playing, audio paused, or out of disc data,
just zero fill */
if (!m_disc || !m_audio_playing || m_audio_pause || (!m_audio_length && !m_audio_samples))
{
info->audio_playing = FALSE;
info->audio_ended_normally = TRUE;
if( m_disc && m_audio_playing && !m_audio_pause && !m_audio_length )
{
m_audio_playing = FALSE;
m_audio_ended_normally = TRUE;
}
memset(bufL, 0, sizeof(stream_sample_t)*samples_wanted);
memset(bufR, 0, sizeof(stream_sample_t)*samples_wanted);
return;
}
memset(bufL, 0, sizeof(stream_sample_t)*samples_wanted);
memset(bufR, 0, sizeof(stream_sample_t)*samples_wanted);
return;
}
/* if we've got enough samples, just feed 'em out */
if (samples_wanted <= info->audio_samples)
{
for (i = 0; i < samples_wanted; i++)
int samples = samples_wanted;
if (samples > m_audio_samples)
{
*bufL++ = audio_cache[ info->audio_bptr++ ];
*bufR++ = audio_cache[ info->audio_bptr++ ];
samples = m_audio_samples;
}
info->audio_samples -= samples_wanted;
return;
}
/* we don't have enough, so first feed what we've got */
for (i = 0; i < info->audio_samples; i++)
{
*bufL++ = audio_cache[ info->audio_bptr++ ];
*bufR++ = audio_cache[ info->audio_bptr++ ];
}
/* remember how much left for later */
remaining = samples_wanted - info->audio_samples;
/* reset the buffer and get what we can from the disc */
info->audio_samples = 0;
if (info->audio_length >= MAX_SECTORS)
{
sectoread = MAX_SECTORS;
}
else
{
sectoread = info->audio_length;
}
for (i = 0; i < sectoread; i++)
{
cdrom_read_data(info->disc, info->audio_lba, &info->audio_cache[CD_MAX_SECTOR_DATA*i], CD_TRACK_AUDIO);
info->audio_lba++;
}
info->audio_samples = (CD_MAX_SECTOR_DATA*sectoread)/4;
info->audio_length -= sectoread;
/* CD-DA data on the disc is big-endian, flip if we're not */
if (ENDIANNESS_NATIVE == ENDIANNESS_LITTLE)
{
for( i = 0; i < info->audio_samples * 2; i++ )
for (i = 0; i < samples; i++)
{
audio_cache[ i ] = BIG_ENDIANIZE_INT16( audio_cache[ i ] );
/* CD-DA data on the disc is big-endian */
*bufL++ = (INT16) BIG_ENDIANIZE_INT16( audio_cache[ m_audio_bptr ] ); m_audio_bptr++;
*bufR++ = (INT16) BIG_ENDIANIZE_INT16( audio_cache[ m_audio_bptr ] ); m_audio_bptr++;
}
samples_wanted -= samples;
m_audio_samples -= samples;
if (m_audio_samples == 0)
{
int sectors = m_audio_length;
if (sectors > MAX_SECTORS)
{
sectors = MAX_SECTORS;
}
for (i = 0; i < sectors; i++)
{
cdrom_read_data(m_disc, m_audio_lba, &m_audio_cache[CD_MAX_SECTOR_DATA*i], CD_TRACK_AUDIO);
m_audio_lba++;
}
m_audio_samples = (CD_MAX_SECTOR_DATA*sectors)/4;
m_audio_length -= sectors;
/* reset feedout ptr */
m_audio_bptr = 0;
}
}
/* reset feedout ptr */
info->audio_bptr = 0;
/* we've got data, feed it out by calling ourselves recursively */
get_audio_data(info, bufL, bufR, remaining);
}
/*-------------------------------------------------
@ -295,12 +222,10 @@ static void get_audio_data(cdda_info *info, stream_sample_t *bufL, stream_sample
for both speakers, used for fade in/out effects
-------------------------------------------------*/
void cdda_set_volume(device_t *device,int volume)
void cdda_device::set_volume(int volume)
{
cdda_info *cdda = get_safe_token(device);
cdda->stream->set_output_gain(0,volume / 100.0);
cdda->stream->set_output_gain(1,volume / 100.0);
m_stream->set_output_gain(0,volume / 100.0);
m_stream->set_output_gain(1,volume / 100.0);
}
/*-------------------------------------------------
@ -308,11 +233,9 @@ void cdda_set_volume(device_t *device,int volume)
for either speaker, used for fade in/out effects
-------------------------------------------------*/
void cdda_set_channel_volume(device_t *device, int channel, int volume)
void cdda_device::set_channel_volume(int channel, int volume)
{
cdda_info *cdda = get_safe_token(device);
cdda->stream->set_output_gain(channel,volume / 100.0);
m_stream->set_output_gain(channel,volume / 100.0);
}
@ -321,11 +244,9 @@ void cdda_set_channel_volume(device_t *device, int channel, int volume)
for either speaker, used for volume control display
-------------------------------------------------*/
INT16 cdda_get_channel_volume(device_t *device, int channel)
INT16 cdda_device::get_channel_volume(int channel)
{
cdda_info *cdda = get_safe_token(device);
return cdda->audio_volume[channel];
return m_audio_volume[channel];
}
const device_type CDDA = &device_creator<cdda_device>;
@ -334,7 +255,6 @@ cdda_device::cdda_device(const machine_config &mconfig, const char *tag, device_
: device_t(mconfig, CDDA, "CD/DA", tag, owner, clock),
device_sound_interface(mconfig, *this)
{
m_token = global_alloc_clear(cdda_info);
}
//-------------------------------------------------
@ -346,22 +266,3 @@ cdda_device::cdda_device(const machine_config &mconfig, const char *tag, device_
void cdda_device::device_config_complete()
{
}
//-------------------------------------------------
// device_start - device-specific startup
//-------------------------------------------------
void cdda_device::device_start()
{
DEVICE_START_NAME( cdda )(this);
}
//-------------------------------------------------
// sound_stream_update - handle a stream update
//-------------------------------------------------
void cdda_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
{
// should never get here
fatalerror("sound_stream_update called; not applicable to legacy sound devices\n");
}

View File

@ -3,32 +3,30 @@
#ifndef __CDDA_H__
#define __CDDA_H__
#include "devlegcy.h"
void cdda_set_cdrom(device_t *device, void *file);
device_t *cdda_from_cdrom(running_machine &machine, void *file);
void cdda_start_audio(device_t *device, UINT32 startlba, UINT32 numblocks);
void cdda_stop_audio(device_t *device);
void cdda_pause_audio(device_t *device, int pause);
void cdda_set_volume(device_t *device, int volume);
void cdda_set_channel_volume(device_t *device, int channel, int volume);
INT16 cdda_get_channel_volume(device_t *device, int channel);
UINT32 cdda_get_audio_lba(device_t *device);
int cdda_audio_active(device_t *device);
int cdda_audio_paused(device_t *device);
int cdda_audio_ended(device_t *device);
#include "cdrom.h"
class cdda_device : public device_t,
public device_sound_interface
{
public:
cdda_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
~cdda_device() { global_free(m_token); }
// access to legacy token
void *token() const { assert(m_token != NULL); return m_token; }
void set_cdrom(void *file);
void start_audio(UINT32 startlba, UINT32 numblocks);
void stop_audio();
void pause_audio(int pause);
void set_volume(int volume);
void set_channel_volume(int channel, int volume);
INT16 get_channel_volume(int channel);
UINT32 get_audio_lba();
int audio_active();
int audio_paused();
int audio_ended();
cdrom_file * m_disc;
protected:
// device-level overrides
virtual void device_config_complete();
@ -36,9 +34,20 @@ protected:
// sound stream update overrides
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples);
private:
void get_audio_data(stream_sample_t *bufL, stream_sample_t *bufR, UINT32 samples_wanted);
// internal state
void *m_token;
sound_stream * m_stream;
INT8 m_audio_playing, m_audio_pause, m_audio_ended_normally;
UINT32 m_audio_lba, m_audio_length;
UINT8 * m_audio_cache;
UINT32 m_audio_samples;
UINT32 m_audio_bptr;
INT16 m_audio_volume[2];
};
extern const device_type CDDA;

View File

@ -61,6 +61,7 @@ public:
UINT8 m_cdrom_cmd_start;
UINT8 m_cdrom_cmd_end;
UINT8 m_cdrom_cmd_resp;
cdda_device *m_cdda;
cdrom_file *m_cdrom;
UINT8 * m_cdrom_toc;
emu_timer *m_dma_timer;
@ -203,8 +204,7 @@ static DEVICE_START( akiko )
state->m_dma_timer = machine.scheduler().timer_alloc(FUNC(akiko_dma_proc), state);
state->m_frame_timer = machine.scheduler().timer_alloc(FUNC(akiko_frame_proc), state);
state->m_i2cmem = machine.device("i2cmem");
state->m_cdda = machine.device<cdda_device>("cdda");
}
static void akiko_nvram_write(akiko_state *state, UINT32 data)
@ -323,33 +323,29 @@ static const char* get_akiko_reg_name(int reg)
static void akiko_cdda_stop(akiko_state *state)
{
device_t *cdda = cdda_from_cdrom(state->machine(), state->m_cdrom);
if (cdda != NULL)
if (state->m_cdda != NULL)
{
cdda_stop_audio(cdda);
state->m_cdda->stop_audio();
state->m_frame_timer->reset( );
}
}
static void akiko_cdda_play(akiko_state *state, UINT32 lba, UINT32 num_blocks)
{
device_t *cdda = cdda_from_cdrom(state->machine(), state->m_cdrom);
if (cdda != NULL)
if (state->m_cdda != NULL)
{
cdda_start_audio(cdda, lba, num_blocks);
state->m_cdda->start_audio(lba, num_blocks);
state->m_frame_timer->adjust( attotime::from_hz( 75 ) );
}
}
static void akiko_cdda_pause(akiko_state *state, int pause)
{
device_t *cdda = cdda_from_cdrom(state->machine(), state->m_cdrom);
if (cdda != NULL)
if (state->m_cdda != NULL)
{
if (cdda_audio_active(cdda) && cdda_audio_paused(cdda) != pause )
if (state->m_cdda->audio_active() && state->m_cdda->audio_paused() != pause )
{
cdda_pause_audio(cdda, pause);
state->m_cdda->pause_audio(pause);
if ( pause )
{
@ -365,17 +361,15 @@ static void akiko_cdda_pause(akiko_state *state, int pause)
static UINT8 akiko_cdda_getstatus(akiko_state *state, UINT32 *lba)
{
device_t *cdda = cdda_from_cdrom(state->machine(), state->m_cdrom);
if ( lba ) *lba = 0;
if (cdda != NULL)
if (state->m_cdda != NULL)
{
if (cdda_audio_active(cdda))
if (state->m_cdda->audio_active())
{
if ( lba ) *lba = cdda_get_audio_lba(cdda);
if ( lba ) *lba = state->m_cdda->get_audio_lba();
if (cdda_audio_paused(cdda))
if (state->m_cdda->audio_paused())
{
return 0x12; /* audio paused */
}
@ -384,7 +378,7 @@ static UINT8 akiko_cdda_getstatus(akiko_state *state, UINT32 *lba)
return 0x11; /* audio in progress */
}
}
else if (cdda_audio_ended(cdda))
else if (state->m_cdda->audio_ended())
{
return 0x13; /* audio ended */
}
@ -409,11 +403,10 @@ static void akiko_set_cd_status(akiko_state *state, UINT32 status)
static TIMER_CALLBACK(akiko_frame_proc)
{
akiko_state *state = (akiko_state *)ptr;
device_t *cdda = cdda_from_cdrom(machine, state->m_cdrom);
(void)param;
if (cdda != NULL)
if (state->m_cdda != NULL)
{
UINT8 s = akiko_cdda_getstatus(state, NULL);
@ -787,7 +780,7 @@ READ32_DEVICE_HANDLER( amiga_akiko32_r )
switch( offset )
{
case 0x00/4: /* ID */
if ( state->m_cdrom != NULL ) cdda_set_cdrom(state->m_space->machine().device("cdda"), state->m_cdrom);
if ( state->m_cdrom != NULL ) state->m_cdda->set_cdrom(state->m_cdrom);
return 0x0000cafe;
case 0x04/4: /* CDROM STATUS 1 */

View File

@ -813,7 +813,7 @@ void cdicdic_device::process_delayed_command()
// next_lba = next_nybbles[0] + next_nybbles[1]*10 + ((next_nybbles[2] + next_nybbles[3]*10)*75) + ((next_nybbles[4] + next_nybbles[5]*10)*75*60);
verboselog(machine(), 0, "Playing CDDA sector from MSF location %06x\n", m_time | 2 );
cdda_start_audio(state->m_cdda, lba, rounded_next_msf);
state->m_cdda->start_audio(lba, rounded_next_msf);
}
m_ram[(m_data_buffer & 5) * (0xa00/2) + 0x924/2] = 0x0001; // CTRL
@ -1115,7 +1115,7 @@ WRITE16_MEMBER( cdicdic_device::regs_w )
break;
}
case 0x2b: // Stop CDDA
cdda_stop_audio(state->m_cdda);
state->m_cdda->stop_audio();
m_interrupt_timer->adjust(attotime::never);
break;
case 0x23: // Reset Mode 1
@ -1226,13 +1226,13 @@ void cdicdic_device::device_reset()
{
// MESS case (has CDROM device)
m_cd = cdrom_dev->get_cdrom_file();
cdda_set_cdrom(state->m_cdda, m_cd);
state->m_cdda->set_cdrom(m_cd);
}
else
{
// MAME case
m_cd = cdrom_open(get_disk_handle(machine(), ":cdrom"));
cdda_set_cdrom(state->m_cdda, m_cd);
state->m_cdda->set_cdrom(m_cd);
}
}

View File

@ -7,7 +7,6 @@
#include "emu.h"
#include "machine/scsihle.h"
#include "cdrom.h"
#include "sound/cdda.h"
#include "imagedev/chd_cd.h"
#include "gdrom.h"
@ -29,7 +28,8 @@ static void phys_frame_to_msf(int phys_frame, int *m, int *s, int *f)
const device_type GDROM = &device_creator<gdrom_device>;
gdrom_device::gdrom_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
: scsihle_device(mconfig, GDROM, "GDROM", tag, owner, clock, "gdrom", __FILE__)
: scsihle_device(mconfig, GDROM, "GDROM", tag, owner, clock, "gdrom", __FILE__),
m_cdda(*this, "cdda")
{
}
@ -103,7 +103,6 @@ machine_config_constructor gdrom_device::device_mconfig_additions() const
void gdrom_device::ExecCommand( int *transferLength )
{
device_t *cdda;
int trk;
switch ( command[0] )
@ -141,10 +140,9 @@ void gdrom_device::ExecCommand( int *transferLength )
break;
case 0x1b: // START STOP UNIT
cdda = cdda_from_cdrom( machine(), cdrom);
if (cdda != NULL)
if (m_cdda != NULL)
{
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
SetPhase( SCSI_PHASE_STATUS );
*transferLength = 0;
@ -177,10 +175,9 @@ void gdrom_device::ExecCommand( int *transferLength )
cur_subblock = 0;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
if (m_cdda != NULL)
{
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
SetPhase( SCSI_PHASE_DATAIN );
@ -223,10 +220,9 @@ void gdrom_device::ExecCommand( int *transferLength )
cur_subblock = 0;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
if (m_cdda != NULL)
{
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
SetPhase( SCSI_PHASE_DATAIN );
@ -266,10 +262,9 @@ void gdrom_device::ExecCommand( int *transferLength )
length = 4;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
if (m_cdda != NULL)
{
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
SetPhase( SCSI_PHASE_DATAIN );
@ -297,9 +292,8 @@ void gdrom_device::ExecCommand( int *transferLength )
if (cdrom_get_track_type(cdrom, trk) == CD_TRACK_AUDIO)
{
play_err_flag = 0;
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
if (m_cdda != NULL)
m_cdda->start_audio(lba, blocks);
}
else
{
@ -328,9 +322,8 @@ void gdrom_device::ExecCommand( int *transferLength )
if (blocks && cdrom)
{
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
if (m_cdda != NULL)
m_cdda->start_audio(lba, blocks);
}
logerror("GDROM: PLAY AUDIO T/I: strk %d idx %d etrk %d idx %d frames %d\n", command[4], command[5], command[7], command[8], blocks);
@ -341,9 +334,8 @@ void gdrom_device::ExecCommand( int *transferLength )
case 0x4b: // PAUSE/RESUME
if (cdrom)
{
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_pause_audio(cdda, (command[8] & 0x01) ^ 0x01);
if (m_cdda != NULL)
m_cdda->pause_audio((command[8] & 0x01) ^ 0x01);
}
logerror("GDROM: PAUSE/RESUME: %s\n", command[8]&1 ? "RESUME" : "PAUSE");
@ -383,9 +375,8 @@ void gdrom_device::ExecCommand( int *transferLength )
if (cdrom_get_track_type(cdrom, trk) == CD_TRACK_AUDIO)
{
play_err_flag = 0;
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
cdda_start_audio(cdda, lba, blocks);
if (m_cdda != NULL)
m_cdda->start_audio(lba, blocks);
}
else
{
@ -412,10 +403,9 @@ void gdrom_device::ExecCommand( int *transferLength )
cur_subblock = 0;
}
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL)
if (m_cdda != NULL)
{
cdda_stop_audio(cdda);
m_cdda->stop_audio();
}
SetPhase( SCSI_PHASE_DATAIN );
@ -444,7 +434,6 @@ void gdrom_device::ReadData( UINT8 *data, int dataLength )
UINT32 last_phys_frame;
UINT32 temp;
UINT8 tmp_buffer[2048];
device_t *cdda;
switch ( command[0] )
{
@ -455,8 +444,7 @@ void gdrom_device::ReadData( UINT8 *data, int dataLength )
data[0] = 0x71; // deferred error
cdda = cdda_from_cdrom(machine(), cdrom);
if (cdda != NULL && cdda_audio_active(cdda))
if (m_cdda != NULL && m_cdda->audio_active())
{
data[12] = 0x00;
data[13] = 0x11; // AUDIO PLAY OPERATION IN PROGRESS
@ -583,11 +571,10 @@ void gdrom_device::ReadData( UINT8 *data, int dataLength )
msf = command[1] & 0x2;
cdda = cdda_from_cdrom(machine(), cdrom);
audio_active = cdda != NULL && cdda_audio_active(cdda);
audio_active = m_cdda != NULL && m_cdda->audio_active();
if (audio_active)
{
if (cdda_audio_paused(cdda))
if (m_cdda->audio_paused())
{
data[1] = 0x12; // audio is paused
}
@ -598,7 +585,7 @@ void gdrom_device::ReadData( UINT8 *data, int dataLength )
}
else
{
if (cdda != NULL && cdda_audio_ended(cdda))
if (m_cdda != NULL && m_cdda->audio_ended())
{
data[1] = 0x13; // ended successfully
}
@ -612,7 +599,7 @@ void gdrom_device::ReadData( UINT8 *data, int dataLength )
// if audio is playing, get the latest LBA from the CDROM layer
if (audio_active)
{
last_lba = cdda_get_audio_lba(cdda);
last_lba = m_cdda->get_audio_lba();
}
else
{

View File

@ -8,6 +8,7 @@
#define _GDROM_H_
#include "machine/scsihle.h"
#include "sound/cdda.h"
// Sega GD-ROM handler
class gdrom_device : public scsihle_device
@ -43,6 +44,7 @@ private:
UINT32 read_type; // for command 0x30 only
UINT32 data_select; // for command 0x30 only
cdrom_file *cdrom;
optional_device<cdda_device> m_cdda;
bool is_file;
};

View File

@ -201,7 +201,7 @@ void lc89510_temp_device::CDD_Stop(running_machine &machine)
SCD_STATUS = CDD_STOPPED;
CDD_STATUS = 0x0000;
SET_CDD_DATA_MODE
cdda_stop_audio( m_cdda ); //stop any pending CD-DA
m_cdda->stop_audio(); //stop any pending CD-DA
//neocd
NeoCD_StatusHack = 0x0E;
@ -366,7 +366,7 @@ void lc89510_temp_device::CDD_Play(running_machine &machine)
printf("%d Track played\n",SCD_CURTRK);
CDD_MIN = to_bcd(SCD_CURTRK, false);
if(!(CURRENT_TRACK_IS_DATA))
cdda_start_audio( m_cdda, SCD_CURLBA, end_msf - SCD_CURLBA );
m_cdda->start_audio(SCD_CURLBA, end_msf - SCD_CURLBA);
SET_CDC_READ
@ -399,7 +399,7 @@ void lc89510_temp_device::CDD_Pause(running_machine &machine)
//segacd.current_frame = cdda_get_audio_lba( machine.device( "cdda" ) );
//if(!(CURRENT_TRACK_IS_DATA))
cdda_pause_audio( m_cdda, 1 );
m_cdda->pause_audio(1);
NeoCD_StatusHack = 4;
@ -418,7 +418,7 @@ void lc89510_temp_device::CDD_Resume(running_machine &machine)
CDD_MIN = to_bcd (SCD_CURTRK, false);
SET_CDC_READ
//if(!(CURRENT_TRACK_IS_DATA))
cdda_pause_audio( m_cdda, 0 );
m_cdda->pause_audio(0);
NeoCD_StatusHack = 1;
}
@ -993,7 +993,7 @@ WRITE16_MEMBER( lc89510_temp_device::segacd_cdfader_w )
//printf("%f\n",cdfader_vol);
cdda_set_volume( m_cdda, cdfader_vol);
m_cdda->set_volume(cdfader_vol);
}
void lc89510_temp_device::reset_cd(void)
@ -1010,8 +1010,8 @@ void lc89510_temp_device::reset_cd(void)
if ( segacd.cd )
{
segacd.toc = cdrom_get_toc( segacd.cd );
cdda_set_cdrom( m_cdda, segacd.cd );
cdda_stop_audio(m_cdda ); //stop any pending CD-DA
m_cdda->set_cdrom(segacd.cd);
m_cdda->stop_audio(); //stop any pending CD-DA
}
}
}

View File

@ -1381,8 +1381,7 @@ void towns_state::towns_cd_set_status(UINT8 st0, UINT8 st1, UINT8 st2, UINT8 st3
UINT8 towns_state::towns_cd_get_track()
{
cdrom_image_device* cdrom = m_cdrom;
device_t* cdda = m_cdda;
UINT32 lba = cdda_get_audio_lba(cdda);
UINT32 lba = m_cdda->get_audio_lba();
UINT8 track;
for(track=1;track<99;track++)
@ -1566,8 +1565,8 @@ void towns_state::towns_cdrom_play_cdda(cdrom_image_device* device)
m_towns_cd.cdda_current = msf_to_lbafm(lba1);
m_towns_cd.cdda_length = msf_to_lbafm(lba2) - m_towns_cd.cdda_current;
cdda_set_cdrom(m_cdda,device->get_cdrom_file());
cdda_start_audio(m_cdda,m_towns_cd.cdda_current,m_towns_cd.cdda_length);
m_cdda->set_cdrom(device->get_cdrom_file());
m_cdda->start_audio(m_towns_cd.cdda_current,m_towns_cd.cdda_length);
logerror("CD: CD-DA start from LBA:%i length:%i\n",m_towns_cd.cdda_current,m_towns_cd.cdda_length);
if(m_towns_cd.command & 0x20)
{
@ -1636,7 +1635,7 @@ void towns_state::towns_cdrom_execute_command(cdrom_image_device* device)
if(m_towns_cd.command & 0x20)
{
m_towns_cd.extra_status = 0;
if(cdda_audio_active(m_cdda) && !cdda_audio_paused(m_cdda))
if(m_cdda->audio_active() && !m_cdda->audio_paused())
towns_cd_set_status(0x00,0x03,0x00,0x00);
else
towns_cd_set_status(0x00,0x01,0x00,0x00);
@ -1657,7 +1656,7 @@ void towns_state::towns_cdrom_execute_command(cdrom_image_device* device)
m_towns_cd.extra_status = 1;
towns_cd_set_status(0x00,0x00,0x00,0x00);
}
cdda_pause_audio(m_cdda,1);
m_cdda->pause_audio(1);
logerror("CD: Command 0x84: STOP CD-DA\n");
break;
case 0x85: // Stop CD audio track (difference from 0x84?)
@ -1666,7 +1665,7 @@ void towns_state::towns_cdrom_execute_command(cdrom_image_device* device)
m_towns_cd.extra_status = 1;
towns_cd_set_status(0x00,0x00,0x00,0x00);
}
cdda_pause_audio(m_cdda,1);
m_cdda->pause_audio(1);
logerror("CD: Command 0x85: STOP CD-DA\n");
break;
case 0x87: // Resume CD-DA playback
@ -1675,7 +1674,7 @@ void towns_state::towns_cdrom_execute_command(cdrom_image_device* device)
m_towns_cd.extra_status = 1;
towns_cd_set_status(0x00,0x03,0x00,0x00);
}
cdda_pause_audio(m_cdda,0);
m_cdda->pause_audio(0);
logerror("CD: Command 0x87: RESUME CD-DA\n");
break;
default:
@ -1792,21 +1791,21 @@ READ8_MEMBER(towns_state::towns_cdrom_r)
m_towns_cd.extra_status++;
break;
case 2: // st0/1/2 = MSF from beginning of current track
addr = cdda_get_audio_lba(m_cdda);
addr = m_cdda->get_audio_lba();
addr = lba_to_msf(addr - m_towns_cd.cdda_current);
towns_cd_set_status(0x19,
(addr & 0xff0000) >> 16,(addr & 0x00ff00) >> 8,addr & 0x0000ff);
m_towns_cd.extra_status++;
break;
case 3: // st1/2 = current MSF
addr = cdda_get_audio_lba(m_cdda);
addr = m_cdda->get_audio_lba();
addr = lba_to_msf(addr); // this data is incorrect, but will do until exact meaning is found
towns_cd_set_status(0x19,
0x00,(addr & 0xff0000) >> 16,(addr & 0x00ff00) >> 8);
m_towns_cd.extra_status++;
break;
case 4:
addr = cdda_get_audio_lba(m_cdda);
addr = m_cdda->get_audio_lba();
addr = lba_to_msf(addr); // this data is incorrect, but will do until exact meaning is found
towns_cd_set_status(0x20,
addr & 0x0000ff,0x00,0x00);
@ -2030,9 +2029,9 @@ WRITE8_MEMBER(towns_state::towns_volume_w)
case 2:
m_towns_volume[m_towns_volume_select] = data;
if(m_towns_volume_select == 4)
cdda_set_channel_volume(m_cdda,0,100.0 * (data / 64.0f));
m_cdda->set_channel_volume(0,100.0 * (data / 64.0f));
if(m_towns_volume_select == 5)
cdda_set_channel_volume(m_cdda,1,100.0 * (data / 64.0f));
m_cdda->set_channel_volume(1,100.0 * (data / 64.0f));
break;
case 3: // select channel
if(data < 8)
@ -2616,7 +2615,7 @@ void towns_state::machine_reset()
m_pit = machine().device("pit");
m_messram = m_ram;
m_cdrom = machine().device<cdrom_image_device>("cdrom");
m_cdda = machine().device("cdda");
m_cdda = machine().device<cdda_device>("cdda");
m_scsi = machine().device<fmscsi_device>("scsi:fm");
m_ftimer = 0x00;
m_freerun_timer = 0x00;

View File

@ -95,7 +95,7 @@ class towns_state : public driver_device
device_t* m_pit;
ram_device* m_messram;
cdrom_image_device* m_cdrom;
device_t* m_cdda;
cdda_device* m_cdda;
required_device<speaker_sound_device> m_speaker;
class fmscsi_device* m_scsi;
required_device<ram_device> m_ram;

View File

@ -519,7 +519,7 @@ static void pce_cd_read_6( running_machine &machine )
if ( pce_cd.cdda_status != PCE_CD_CDDA_OFF )
{
pce_cd.cdda_status = PCE_CD_CDDA_OFF;
cdda_stop_audio( machine.device( "cdda" ) );
machine.device<cdda_device>("cdda")->stop_audio();
pce_cd.end_mark = 0;
}
@ -589,7 +589,7 @@ static void pce_cd_nec_set_audio_start_position( running_machine &machine )
if ( pce_cd.cdda_status == PCE_CD_CDDA_PAUSED )
{
pce_cd.cdda_status = PCE_CD_CDDA_OFF;
cdda_stop_audio( machine.device( "cdda" ) );
machine.device<cdda_device>("cdda")->stop_audio();
pce_cd.end_frame = pce_cd.last_frame;
pce_cd.end_mark = 0;
}
@ -599,7 +599,7 @@ static void pce_cd_nec_set_audio_start_position( running_machine &machine )
{
pce_cd.cdda_status = PCE_CD_CDDA_PLAYING;
pce_cd.end_frame = pce_cd.last_frame; //get the end of the CD
cdda_start_audio( machine.device( "cdda" ), pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
machine.device<cdda_device>("cdda")->start_audio( pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
pce_cd.cdda_play_mode = (pce_cd.command_buffer[1] & 0x02) ? 2 : 3; // mode 2 sets IRQ at end
pce_cd.end_mark = (pce_cd.command_buffer[1] & 0x02) ? 1 : 0;
}
@ -607,7 +607,7 @@ static void pce_cd_nec_set_audio_start_position( running_machine &machine )
{
pce_cd.cdda_status = PCE_CD_CDDA_PLAYING;
pce_cd.end_frame = pce_cd.toc->tracks[ cdrom_get_track(pce_cd.cd, pce_cd.current_frame) + 1 ].logframeofs; //get the end of THIS track
cdda_start_audio( machine.device( "cdda" ), pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
machine.device<cdda_device>("cdda")->start_audio( pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
pce_cd.end_mark = 0;
pce_cd.cdda_play_mode = 3;
}
@ -666,12 +666,12 @@ static void pce_cd_nec_set_audio_stop_position( running_machine &machine )
{
if ( pce_cd.cdda_status == PCE_CD_CDDA_PAUSED )
{
cdda_pause_audio( machine.device( "cdda" ), 0 );
machine.device<cdda_device>("cdda")->pause_audio( 0 );
}
else
{
//printf("%08x %08x\n",pce_cd.current_frame,pce_cd.end_frame - pce_cd.current_frame);
cdda_start_audio( machine.device( "cdda" ), pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
machine.device<cdda_device>("cdda")->start_audio( pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame );
pce_cd.end_mark = 1;
}
pce_cd.cdda_status = PCE_CD_CDDA_PLAYING;
@ -679,7 +679,7 @@ static void pce_cd_nec_set_audio_stop_position( running_machine &machine )
else
{
pce_cd.cdda_status = PCE_CD_CDDA_OFF;
cdda_stop_audio( machine.device( "cdda" ) );
machine.device<cdda_device>("cdda")->stop_audio();
pce_cd.end_frame = pce_cd.last_frame;
pce_cd.end_mark = 0;
// assert( NULL == pce_cd_nec_set_audio_stop_position );
@ -710,8 +710,8 @@ static void pce_cd_nec_pause( running_machine &machine )
}
pce_cd.cdda_status = PCE_CD_CDDA_PAUSED;
pce_cd.current_frame = cdda_get_audio_lba( machine.device( "cdda" ) );
cdda_pause_audio( machine.device( "cdda" ), 1 );
pce_cd.current_frame = machine.device<cdda_device>("cdda")->get_audio_lba();
machine.device<cdda_device>("cdda")->pause_audio( 1 );
pce_cd_reply_status_byte( state, SCSI_STATUS_OK );
}
@ -736,11 +736,11 @@ static void pce_cd_nec_get_subq( running_machine &machine )
{
case PCE_CD_CDDA_PAUSED:
pce_cd.data_buffer[0] = 2;
frame = cdda_get_audio_lba( machine.device( "cdda" ) );
frame = machine.device<cdda_device>("cdda")->get_audio_lba();
break;
case PCE_CD_CDDA_PLAYING:
pce_cd.data_buffer[0] = 0;
frame = cdda_get_audio_lba( machine.device( "cdda" ) );
frame = machine.device<cdda_device>("cdda")->get_audio_lba();
break;
default:
pce_cd.data_buffer[0] = 3;
@ -999,7 +999,7 @@ static void pce_cd_update( running_machine &machine )
pce_cd.cd_motor_on = 0;
pce_cd.selected = 0;
pce_cd.cdda_status = PCE_CD_CDDA_OFF;
cdda_stop_audio( machine.device( "cdda" ) );
machine.device<cdda_device>("cdda")->stop_audio();
pce_cd.adpcm_dma_timer->adjust(attotime::never); // stop ADPCM DMA here
}
pce_cd.scsi_last_RST = pce_cd.scsi_RST;
@ -1064,11 +1064,11 @@ static void pce_cd_update( running_machine &machine )
}
/* FIXME: presumably CD-DA needs an irq interface for this */
if(cdda_audio_ended(machine.device("cdda")) && pce_cd.end_mark == 1)
if(machine.device<cdda_device>("cdda")->audio_ended() && pce_cd.end_mark == 1)
{
switch(pce_cd.cdda_play_mode & 3)
{
case 1: cdda_start_audio( machine.device( "cdda" ), pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame ); pce_cd.end_mark = 1; break; //play with repeat
case 1: machine.device<cdda_device>("cdda")->start_audio( pce_cd.current_frame, pce_cd.end_frame - pce_cd.current_frame ); pce_cd.end_mark = 1; break; //play with repeat
case 2: pce_cd_set_irq_line( machine, PCE_CD_IRQ_TRANSFER_DONE, ASSERT_LINE ); pce_cd.end_mark = 0; break; //irq when finished
case 3: pce_cd.end_mark = 0; break; //play without repeat
}
@ -1178,7 +1178,7 @@ static void pce_cd_init( running_machine &machine )
if ( pce_cd.cd )
{
pce_cd.toc = cdrom_get_toc( pce_cd.cd );
cdda_set_cdrom( machine.device("cdda"), pce_cd.cd );
machine.device<cdda_device>("cdda")->set_cdrom( pce_cd.cd );
pce_cd.last_frame = cdrom_get_track_start( pce_cd.cd, cdrom_get_last_track( pce_cd.cd ) - 1 );
pce_cd.last_frame += pce_cd.toc->tracks[ cdrom_get_last_track( pce_cd.cd ) - 1 ].frames;
pce_cd.end_frame = pce_cd.last_frame;
@ -1234,12 +1234,12 @@ TIMER_CALLBACK_MEMBER(pce_state::pce_cd_cdda_fadeout_callback)
if(pce_cd.cdda_volume <= 0)
{
pce_cd.cdda_volume = 0.0;
cdda_set_volume(machine().device("cdda"), 0.0);
machine().device<cdda_device>("cdda")->set_volume(0.0);
pce_cd.cdda_fadeout_timer->adjust(attotime::never);
}
else
{
cdda_set_volume(machine().device("cdda"), pce_cd.cdda_volume);
machine().device<cdda_device>("cdda")->set_volume(pce_cd.cdda_volume);
pce_cd.cdda_fadeout_timer->adjust(attotime::from_usec(param), param);
}
}
@ -1252,12 +1252,12 @@ TIMER_CALLBACK_MEMBER(pce_state::pce_cd_cdda_fadein_callback)
if(pce_cd.cdda_volume >= 100.0)
{
pce_cd.cdda_volume = 100.0;
cdda_set_volume(machine().device("cdda"), 100.0);
machine().device<cdda_device>("cdda")->set_volume(100.0);
pce_cd.cdda_fadein_timer->adjust(attotime::never);
}
else
{
cdda_set_volume(machine().device("cdda"), pce_cd.cdda_volume);
machine().device<cdda_device>("cdda")->set_volume(pce_cd.cdda_volume);
pce_cd.cdda_fadein_timer->adjust(attotime::from_usec(param), param);
}
}
@ -1599,10 +1599,10 @@ READ8_MEMBER(pce_state::pce_cd_intf_r)
case 0x04: /* CD reset */
break;
case 0x05: /* Convert PCM data / PCM data */
data = cdda_get_channel_volume(machine().device( "cdda" ),(pce_cd.regs[0x03] & 2) ? 0 : 1) & 0xff;
data = machine().device<cdda_device>("cdda")->get_channel_volume((pce_cd.regs[0x03] & 2) ? 0 : 1) & 0xff;
break;
case 0x06: /* PCM data */
data = cdda_get_channel_volume(machine().device( "cdda" ),(pce_cd.regs[0x03] & 2) ? 0 : 1) >> 8;
data = machine().device<cdda_device>("cdda")->get_channel_volume((pce_cd.regs[0x03] & 2) ? 0 : 1) >> 8;
break;
case 0x07: /* BRAM unlock / CD status */
data = ( pce_cd.bram_locked ? ( data & 0x7F ) : ( data | 0x80 ) );