Converted sound modules to be osd_modules. Simplified code. (nw)

This commit is contained in:
couriersud 2015-01-24 02:20:18 +01:00
parent b828f37eef
commit 3818ac2be2
20 changed files with 365 additions and 551 deletions

View File

@ -6,10 +6,6 @@
#include "font_module.h"
#include "modules/osdmodule.h"
#include "astring.h"
#include "corealloc.h"
#include "fileio.h"
//-------------------------------------------------
// font_open - attempt to "open" a handle to the
// font with the given name

View File

@ -338,12 +338,14 @@ public:
return global_alloc(osd_font_sdl);
}
virtual void init()
int init()
{
if (TTF_Init() == -1)
{
osd_printf_error("SDL_ttf failed: %s\n", TTF_GetError());
return -1;
}
return 0;
}
virtual void exit()

View File

@ -11,7 +11,6 @@
#include "emu.h"
#include "osdepend.h"
#include "modules/sound/none.h"
#include "modules/debugger/none.h"
#include "modules/debugger/debugint.h"
#include "modules/lib/osdobj_common.h"
@ -119,6 +118,11 @@ void osd_common_t::register_options()
REGISTER_MODULE(m_mod_man, FONT_SDL);
REGISTER_MODULE(m_mod_man, FONT_NONE);
REGISTER_MODULE(m_mod_man, SOUND_DSOUND);
REGISTER_MODULE(m_mod_man, SOUND_JS);
REGISTER_MODULE(m_mod_man, SOUND_SDL);
REGISTER_MODULE(m_mod_man, SOUND_NONE);
// after initialization we know which modules are supported
const char *names[20];
@ -129,20 +133,17 @@ void osd_common_t::register_options()
dnames.append(names[i]);
update_option(OSD_FONT_PROVIDER, dnames);
m_mod_man.get_module_names(OSD_SOUND_PROVIDER, 20, &num, names);
dnames.reset();
for (int i = 0; i < num; i++)
dnames.append(names[i]);
update_option(OSD_SOUND_PROVIDER, dnames);
// Register video options and update options
video_options_add("none", NULL);
video_register();
update_option(OSDOPTION_VIDEO, m_video_names);
// Register sound options and update options
sound_options_add("none", OSD_SOUND_NONE);
sound_register();
update_option(OSDOPTION_SOUND, m_sound_names);
// Register debugger options and update options
debugger_options_add("none", OSD_DEBUGGER_NONE);
debugger_options_add("internal", OSD_DEBUGGER_INTERNAL);
@ -180,10 +181,6 @@ osd_common_t::~osd_common_t()
osd_free(const_cast<char*>(m_video_names[i]));
//m_video_options,reset();
for(int i= 0; i < m_sound_names.count(); ++i)
osd_free(const_cast<char*>(m_sound_names[i]));
m_sound_options.reset();
for(int i= 0; i < m_debugger_names.count(); ++i)
osd_free(const_cast<char*>(m_debugger_names[i]));
m_debugger_options.reset();
@ -233,11 +230,6 @@ void osd_common_t::init(running_machine &machine)
if (options.verbose())
g_print_verbose = true;
m_font_module = select_module_options<font_module *>(options, OSD_FONT_PROVIDER);
m_mod_man.init();
// ensure we get called on the way out
machine.add_notifier(MACHINE_NOTIFY_EXIT, machine_notify_delegate(FUNC(osd_common_t::osd_exit), this));
}
@ -327,8 +319,7 @@ void osd_common_t::update_audio_stream(const INT16 *buffer, int samples_this_fra
// It provides an array of stereo samples in L-R order which should be
// output at the configured sample_rate.
//
if (m_sound != NULL)
m_sound->update_audio_stream(buffer,samples_this_frame);
m_sound->update_audio_stream(m_machine->video().throttled(), buffer,samples_this_frame);
}
@ -449,7 +440,6 @@ void osd_common_t::init_subsystems()
exit(-1);
}
sound_init();
input_init();
// we need pause callbacks
machine().add_notifier(MACHINE_NOTIFY_PAUSE, machine_notify_delegate(FUNC(osd_common_t::input_pause), this));
@ -460,6 +450,15 @@ void osd_common_t::init_subsystems()
network_init();
#endif
midi_init();
m_font_module = select_module_options<font_module *>(options(), OSD_FONT_PROVIDER);
m_sound = select_module_options<sound_module *>(options(), OSD_SOUND_PROVIDER);
m_sound->m_sample_rate = options().sample_rate();
m_sound->m_audio_latency = options().audio_latency();
m_mod_man.init();
}
bool osd_common_t::video_init()
@ -472,21 +471,6 @@ bool osd_common_t::window_init()
return true;
}
bool osd_common_t::sound_init()
{
osd_sound_type sound = m_sound_options.find(options().sound());
if (sound==NULL)
{
osd_printf_warning("sound_init: option %s not found switching to auto\n",options().sound());
sound = m_sound_options.find("auto");
}
if (sound != NULL)
m_sound = (*sound)(*this, machine());
else
m_sound = NULL;
return true;
}
bool osd_common_t::no_sound()
{
return (strcmp(options().sound(),"none")==0) ? true : false;
@ -496,10 +480,6 @@ void osd_common_t::video_register()
{
}
void osd_common_t::sound_register()
{
}
void osd_common_t::debugger_register()
{
}
@ -530,7 +510,6 @@ bool osd_common_t::network_init()
void osd_common_t::exit_subsystems()
{
video_exit();
sound_exit();
input_exit();
output_exit();
#ifdef USE_NETWORK
@ -548,12 +527,6 @@ void osd_common_t::window_exit()
{
}
void osd_common_t::sound_exit()
{
if (m_sound != NULL)
global_free(m_sound);
}
void osd_common_t::input_exit()
{
}
@ -579,12 +552,6 @@ void osd_common_t::video_options_add(const char *name, void *type)
m_video_names.append(core_strdup(name));
}
void osd_common_t::sound_options_add(const char *name, osd_sound_type type)
{
m_sound_options.add(name, type, false);
m_sound_names.append(core_strdup(name));
}
void osd_common_t::debugger_options_add(const char *name, osd_debugger_type type)
{
m_debugger_options.add(name, type, false);
@ -602,23 +569,6 @@ void osd_common_t::midi_exit()
osd_midi_exit();
}
//-------------------------------------------------
// osd_sound_interface - constructor
//-------------------------------------------------
osd_sound_interface::osd_sound_interface(const osd_interface &osd, running_machine &machine)
: m_osd(osd), m_machine(machine)
{
}
//-------------------------------------------------
// osd_sound_interface - destructor
//-------------------------------------------------
osd_sound_interface::~osd_sound_interface()
{
}
//-------------------------------------------------
// osd_debugger_interface - constructor
//-------------------------------------------------

View File

@ -16,6 +16,7 @@
#include "osdepend.h"
#include "modules/osdmodule.h"
#include "modules/font/font_module.h"
#include "modules/sound/sound_module.h"
#include "cliopts.h"
//============================================================
@ -103,12 +104,8 @@ private:
static const options_entry s_option_entries[];
};
class osd_sound_interface;
class osd_debugger_interface;
// a osd_sound_type is simply a pointer to its alloc function
typedef osd_sound_interface *(*osd_sound_type)(const osd_interface &osd, running_machine &machine);
// a osd_sound_type is simply a pointer to its alloc function
typedef osd_debugger_interface *(*osd_debugger_type)(const osd_interface &osd);
@ -172,9 +169,6 @@ public:
virtual void video_register();
virtual bool window_init();
virtual bool sound_init();
virtual void sound_register();
virtual void input_resume();
virtual bool output_init();
virtual bool network_init();
@ -183,7 +177,6 @@ public:
virtual void exit_subsystems();
virtual void video_exit();
virtual void window_exit();
virtual void sound_exit();
virtual void input_exit();
virtual void output_exit();
virtual void network_exit();
@ -192,7 +185,6 @@ public:
virtual void osd_exit();
virtual void video_options_add(const char *name, void *type);
virtual void sound_options_add(const char *name, osd_sound_type type);
virtual void debugger_options_add(const char *name, osd_debugger_type type);
osd_options &options() { return m_options; }
@ -231,39 +223,16 @@ private:
}
protected:
osd_sound_interface* m_sound;
sound_module* m_sound;
osd_debugger_interface* m_debugger;
private:
//tagmap_t<osd_video_type> m_video_options;
dynamic_array<const char *> m_video_names;
tagmap_t<osd_sound_type> m_sound_options;
dynamic_array<const char *> m_sound_names;
tagmap_t<osd_debugger_type> m_debugger_options;
dynamic_array<const char *> m_debugger_names;
};
class osd_sound_interface
{
public:
// construction/destruction
osd_sound_interface(const osd_interface &osd, running_machine &machine);
virtual ~osd_sound_interface();
virtual void update_audio_stream(const INT16 *buffer, int samples_this_frame) = 0;
virtual void set_mastervolume(int attenuation) = 0;
protected:
const osd_interface& m_osd;
running_machine& m_machine;
};
// this template function creates a stub which constructs a sound subsystem
template<class _DeviceClass>
osd_sound_interface *osd_sound_creator(const osd_interface &osd, running_machine &machine)
{
return global_alloc(_DeviceClass(osd, machine));
}
class osd_debugger_interface
{
public:

View File

@ -36,8 +36,8 @@ public:
virtual bool probe() const { return true; }
virtual void init() { }
virtual void exit() { }
virtual int init() { return 0; }
virtual void exit() { }
private:
astring m_name;

View File

@ -6,6 +6,11 @@
//
//============================================================
#include "sound_module.h"
#include "modules/osdmodule.h"
#if defined(OSD_WINDOWS) || defined(SDLMAME_WIN32)
// standard windows headers
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
@ -21,9 +26,6 @@
#include "osdepend.h"
#include "emuopts.h"
// MAMEOS headers
#include "direct_sound.h"
#ifdef SDLMAME_WIN32
#include "../../sdl/osdsdl.h"
#if (SDLMAME_SDL2)
@ -45,6 +47,34 @@
#define LOG(x) do { if (LOG_SOUND) logerror x; } while(0)
class sound_direct_sound : public osd_module, public sound_module
{
public:
sound_direct_sound()
: osd_module(OSD_SOUND_PROVIDER, "dsound"), sound_module()
{
}
virtual ~sound_direct_sound() { }
virtual int init();
virtual void exit();
// sound_module
virtual void update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame);
virtual void set_mastervolume(int attenuation);
private:
HRESULT dsound_init();
void dsound_kill();
HRESULT dsound_create_buffers();
void dsound_destroy_buffers();
void copy_sample_data(const INT16 *data, int bytes_to_copy);
};
//============================================================
// LOCAL VARIABLES
@ -69,25 +99,25 @@ static WAVEFORMATEX stream_format;
// buffer over/underflow counts
static int buffer_underflows;
static int buffer_overflows;
//============================================================
// PROTOTYPES
//============================================================
const osd_sound_type OSD_SOUND_DIRECT_SOUND = &osd_sound_creator<sound_direct_sound>;
//-------------------------------------------------
// sound_direct_sound - constructor
//-------------------------------------------------
sound_direct_sound::sound_direct_sound(const osd_interface &osd, running_machine &machine)
: osd_sound_interface(osd, machine)
int sound_direct_sound::init()
{
// attempt to initialize directsound
// don't make it fatal if we can't -- we'll just run without sound
dsound_init();
return 0;
}
sound_direct_sound::~sound_direct_sound()
void sound_direct_sound::exit()
{
// kill the buffers and dsound
dsound_destroy_buffers();
@ -149,7 +179,7 @@ void sound_direct_sound::copy_sample_data(const INT16 *data, int bytes_to_copy)
// update_audio_stream
//============================================================
void sound_direct_sound::update_audio_stream(const INT16 *buffer, int samples_this_frame)
void sound_direct_sound::update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame)
{
int bytes_this_frame = samples_this_frame * stream_format.nBlockAlign;
DWORD play_position, write_position;
@ -268,18 +298,15 @@ HRESULT sound_direct_sound::dsound_init()
stream_format.wBitsPerSample = 16;
stream_format.wFormatTag = WAVE_FORMAT_PCM;
stream_format.nChannels = 2;
stream_format.nSamplesPerSec = m_machine.sample_rate();
stream_format.nSamplesPerSec = sample_rate();
stream_format.nBlockAlign = stream_format.wBitsPerSample * stream_format.nChannels / 8;
stream_format.nAvgBytesPerSec = stream_format.nSamplesPerSec * stream_format.nBlockAlign;
// compute the buffer size based on the output sample rate
int audio_latency;
#ifdef SDLMAME_WIN32
audio_latency = downcast<sdl_options &>(m_machine.options()).audio_latency();
#else
audio_latency = downcast<windows_options &>(m_machine.options()).audio_latency();
#endif
audio_latency = m_audio_latency;
stream_buffer_size = stream_format.nSamplesPerSec * stream_format.nBlockAlign * audio_latency / 10;
stream_buffer_size = (stream_buffer_size / 1024) * 1024;
if (stream_buffer_size < 1024)
@ -419,3 +446,9 @@ void sound_direct_sound::dsound_destroy_buffers(void)
IDirectSoundBuffer_Release(primary_buffer);
primary_buffer = NULL;
}
#else /* SDLMAME_UNIX */
MODULE_NOT_SUPPORTED(sound_direct_sound, OSD_SOUND_PROVIDER, "dsound")
#endif
MODULE_DEFINITION(SOUND_DSOUND, sound_direct_sound)

View File

@ -1,46 +0,0 @@
// license:BSD-3-Clause
// copyright-holders:Aaron Giles
//============================================================
//
// sound.c - Win32 implementation of MAME sound routines
//
//============================================================
#pragma once
#ifndef __SOUND_DSOUND_H__
#define __SOUND_DSOUND_H__
// standard windows headers
#define WIN32_LEAN_AND_MEAN
#include <windows.h>
#include <mmsystem.h>
// undef WINNT for dsound.h to prevent duplicate definition
#undef WINNT
#include <dsound.h>
#undef interface
#include "osdepend.h"
#include "modules/lib/osdobj_common.h"
class sound_direct_sound : public osd_sound_interface
{
public:
// construction/destruction
sound_direct_sound(const osd_interface &osd, running_machine &machine);
virtual ~sound_direct_sound();
virtual void update_audio_stream(const INT16 *buffer, int samples_this_frame);
virtual void set_mastervolume(int attenuation);
HRESULT dsound_init();
void dsound_kill();
HRESULT dsound_create_buffers();
void dsound_destroy_buffers();
void copy_sample_data(const INT16 *data, int bytes_to_copy);
private:
};
extern const osd_sound_type OSD_SOUND_DIRECT_SOUND;
#endif /* __SOUND_DSOUND_H__ */

View File

@ -8,32 +8,48 @@
*******************************************************************c********/
#include "sound_module.h"
#include "modules/osdmodule.h"
#if (defined(SDLMAME_EMSCRIPTEN))
#include "js_sound.h"
#include "emscripten.h"
//-------------------------------------------------
// sound_js - constructor
//-------------------------------------------------
sound_js::sound_js(const osd_interface &osd)
: osd_sound_interface(osd)
class sound_js : public osd_module, public sound_module
{
}
public:
void sound_js::update_audio_stream(const INT16 *buffer, int samples_this_frame)
{
EM_ASM_ARGS({
// Forward audio stream update on to JS backend implementation.
jsmess_update_audio_stream($0, $1);
}, (unsigned int)buffer, samples_this_frame);
}
sound_js()
: osd_module(OSD_SOUND_PROVIDER, "js"), sound_module()
{
}
virtual ~sound_js() { }
void sound_js::set_mastervolume(int attenuation)
{
EM_ASM_ARGS({
// Forward volume update on to JS backend implementation.
jsmess_set_mastervolume($0);
}, attenuation);
}
virtual int init();
virtual void exit();
const osd_sound_type OSD_SOUND_JS = &osd_sound_creator<sound_js>;
// sound_module
virtual void update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame)
{
EM_ASM_ARGS({
// Forward audio stream update on to JS backend implementation.
jsmess_update_audio_stream($1, $2);
}, (unsigned int)buffer, samples_this_frame);
}
virtual void set_mastervolume(int attenuation)
{
EM_ASM_ARGS({
// Forward volume update on to JS backend implementation.
jsmess_set_mastervolume($0);
}, attenuation);
}
};
#else /* SDLMAME_UNIX */
MODULE_NOT_SUPPORTED(sound_js, OSD_SOUND_PROVIDER, "js")
#endif
MODULE_DEFINITION(SOUND_JS, sound_js)

View File

@ -1,31 +0,0 @@
// license:BSD-3-Clause
// copyright-holders:Miodrag Milanovic, Katelyn Gadd
/***************************************************************************
js_sound.h
Shim for native JavaScript sound interface implementations (Emscripten only).
*******************************************************************c********/
#pragma once
#ifndef __SOUND_JS_H__
#define __SOUND_JS_H__
#include "osdepend.h"
class sound_js : public osd_sound_interface
{
public:
// construction/destruction
sound_js(const osd_interface &osd);
virtual ~sound_js() { }
virtual void update_audio_stream(const INT16 *buffer, int samples_this_frame);
virtual void set_mastervolume(int attenuation);
};
extern const osd_sound_type OSD_SOUND_JS;
#endif /* __SOUND_JS_H__ */

View File

@ -8,16 +8,26 @@
*******************************************************************c********/
#include "sound_module.h"
#include "modules/osdmodule.h"
#include "none.h"
//-------------------------------------------------
// sound_none - constructor
//-------------------------------------------------
sound_none::sound_none(const osd_interface &osd, running_machine &machine)
: osd_sound_interface(osd, machine)
class sound_none : public osd_module, public sound_module
{
}
public:
sound_none()
: osd_module(OSD_SOUND_PROVIDER, "none"), sound_module()
{
}
virtual ~sound_none() { }
virtual int init() { return 0; }
virtual void exit() { }
const osd_sound_type OSD_SOUND_NONE = &osd_sound_creator<sound_none>;
// sound_module
virtual void update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame) { }
virtual void set_mastervolume(int attenuation) { }
};
MODULE_DEFINITION(SOUND_NONE, sound_none)

View File

@ -1,32 +0,0 @@
// license:BSD-3-Clause
// copyright-holders:Miodrag Milanovic
/***************************************************************************
none.h
Dummy sound interface.
*******************************************************************c********/
#pragma once
#ifndef __SOUND_NONE_H__
#define __SOUND_NONE_H__
#include "osdepend.h"
#include "modules/lib/osdobj_common.h"
class sound_none : public osd_sound_interface
{
public:
// construction/destruction
sound_none(const osd_interface &osd, running_machine &machine);
virtual ~sound_none() { }
virtual void update_audio_stream(const INT16 *buffer, int samples_this_frame) { }
virtual void set_mastervolume(int attenuation) { }
};
extern const osd_sound_type OSD_SOUND_NONE;
#endif /* __SOUND_NONE_H__ */

View File

@ -9,6 +9,11 @@
//
//============================================================
#include "sound_module.h"
#include "modules/osdmodule.h"
#if (!defined(SDLMAME_EMSCRIPTEN)) && (!defined(OSD_WINDOWS))
// standard sdl header
#include "../../sdl/sdlinc.h"
@ -16,7 +21,6 @@
#include "emu.h"
#include "emuopts.h"
#include "sdl_sound.h"
#include "../../sdl/osdsdl.h"
//============================================================
@ -26,15 +30,74 @@
#define LOG_SOUND 0
//============================================================
// PARAMETERS
// PROTOTYPES
//============================================================
// number of samples per SDL callback
#define SDL_XFER_SAMPLES (512)
static void sdl_callback(void *userdata, Uint8 *stream, int len);
static int sdl_xfer_samples = SDL_XFER_SAMPLES;
static int stream_in_initialized = 0;
static int stream_loop = 0;
//============================================================
// CLASS
//============================================================
class sound_sdl : public osd_module, public sound_module
{
public:
friend void sdl_callback(void *userdata, Uint8 *stream, int len);
// number of samples per SDL callback
static const int SDL_XFER_SAMPLES = 512;
sound_sdl()
: osd_module(OSD_SOUND_PROVIDER, "sdl"), sound_module(),
stream_in_initialized(0),
stream_loop(0),
attenuation(0)
{
sdl_xfer_samples = SDL_XFER_SAMPLES;
}
virtual ~sound_sdl() { }
virtual int init();
virtual void exit();
// sound_module
virtual void update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame);
virtual void set_mastervolume(int attenuation);
private:
int lock_buffer(bool is_throttled, long offset, long size, void **buffer1, long *length1, void **buffer2, long *length2);
void unlock_buffer(void);
void att_memcpy(void *dest, const INT16 *data, int bytes_to_copy);
void copy_sample_data(bool is_throttled, const INT16 *data, int bytes_to_copy);
int sdl_create_buffers(void);
void sdl_destroy_buffers(void);
int sdl_xfer_samples;
int stream_in_initialized;
int stream_loop;
int attenuation;
int buf_locked;
INT8 *stream_buffer;
volatile INT32 stream_playpos;
UINT32 stream_buffer_size;
UINT32 stream_buffer_in;
// buffer over/underflow counts
int buffer_underflows;
int buffer_overflows;
};
//============================================================
// PARAMETERS
//============================================================
// maximum audio latency
#define MAX_AUDIO_LATENCY 5
@ -43,103 +106,23 @@ static int stream_loop = 0;
// LOCAL VARIABLES
//============================================================
static int attenuation = 0;
static int initialized_audio = 0;
static int buf_locked;
static INT8 *stream_buffer;
static volatile INT32 stream_playpos;
static UINT32 stream_buffer_size;
static UINT32 stream_buffer_in;
// buffer over/underflow counts
static int buffer_underflows;
static int buffer_overflows;
// debugging
static FILE *sound_log;
// sound enable
static int snd_enabled;
//============================================================
// PROTOTYPES
//============================================================
static int sdl_init(running_machine &machine);
static void sdl_kill(running_machine &machine);
static int sdl_create_buffers(void);
static void sdl_destroy_buffers(void);
static void SDLCALL sdl_callback(void *userdata, Uint8 *stream, int len);
const osd_sound_type OSD_SOUND_SDL = &osd_sound_creator<sound_sdl>;
//-------------------------------------------------
// sound_sdl - constructor
//-------------------------------------------------
sound_sdl::sound_sdl(const osd_interface &osd, running_machine &machine)
: osd_sound_interface(osd, machine)
{
if (LOG_SOUND)
sound_log = fopen(SDLMAME_SOUND_LOG, "w");
// skip if sound disabled
if (m_machine.sample_rate() != 0)
{
if (initialized_audio)
{
//sound_exit();
}
// attempt to initialize SDL
if (sdl_init(m_machine))
return;
// set the startup volume
set_mastervolume(attenuation);
}
}
//============================================================
// sound_sdl - destructor
//============================================================
sound_sdl::~sound_sdl()
{
// if nothing to do, don't do it
if (m_machine.sample_rate() == 0)
return;
// kill the buffers and dsound
sdl_kill(m_machine);
sdl_destroy_buffers();
// print out over/underflow stats
if (buffer_overflows || buffer_underflows)
osd_printf_verbose("Sound buffer: overflows=%d underflows=%d\n", buffer_overflows, buffer_underflows);
if (LOG_SOUND)
{
fprintf(sound_log, "Sound buffer: overflows=%d underflows=%d\n", buffer_overflows, buffer_underflows);
fclose(sound_log);
}
}
//============================================================
// lock_buffer
//============================================================
static int lock_buffer(running_machine &machine, long offset, long size, void **buffer1, long *length1, void **buffer2, long *length2)
int sound_sdl::lock_buffer(bool is_throttled, long offset, long size, void **buffer1, long *length1, void **buffer2, long *length2)
{
volatile long pstart, pend, lstart, lend;
if (!buf_locked)
{
if (machine.video().throttled())
if (is_throttled)
{
pstart = stream_playpos;
pend = (pstart + sdl_xfer_samples);
@ -185,7 +168,7 @@ static int lock_buffer(running_machine &machine, long offset, long size, void **
//============================================================
// unlock_buffer
//============================================================
static void unlock_buffer(void)
void sound_sdl::unlock_buffer(void)
{
buf_locked--;
if (!buf_locked)
@ -200,7 +183,7 @@ static void unlock_buffer(void)
// Apply attenuation
//============================================================
static void att_memcpy(void *dest, const INT16 *data, int bytes_to_copy)
void sound_sdl::att_memcpy(void *dest, const INT16 *data, int bytes_to_copy)
{
int level= (int) (pow(10.0, (float) attenuation / 20.0) * 128.0);
INT16 *d = (INT16 *) dest;
@ -216,14 +199,14 @@ static void att_memcpy(void *dest, const INT16 *data, int bytes_to_copy)
// copy_sample_data
//============================================================
static void copy_sample_data(running_machine &machine, const INT16 *data, int bytes_to_copy)
void sound_sdl::copy_sample_data(bool is_throttled, const INT16 *data, int bytes_to_copy)
{
void *buffer1, *buffer2 = (void *)NULL;
long length1, length2;
int cur_bytes;
// attempt to lock the stream buffer
if (lock_buffer(machine, stream_buffer_in, bytes_to_copy, &buffer1, &length1, &buffer2, &length2) < 0)
if (lock_buffer(is_throttled, stream_buffer_in, bytes_to_copy, &buffer1, &length1, &buffer2, &length2) < 0)
{
buffer_underflows++;
return;
@ -264,10 +247,10 @@ static void copy_sample_data(running_machine &machine, const INT16 *data, int by
// update_audio_stream
//============================================================
void sound_sdl::update_audio_stream(const INT16 *buffer, int samples_this_frame)
void sound_sdl::update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame)
{
// if nothing to do, don't do it
if (m_machine.sample_rate() != 0 && stream_buffer)
if (sample_rate() != 0 && stream_buffer)
{
int bytes_this_frame = samples_this_frame * sizeof(INT16) * 2;
int play_position, write_position, stream_in;
@ -275,7 +258,7 @@ void sound_sdl::update_audio_stream(const INT16 *buffer, int samples_this_frame)
play_position = stream_playpos;
write_position = stream_playpos + ((m_machine.sample_rate() / 50) * sizeof(INT16) * 2);
write_position = stream_playpos + ((sample_rate() / 50) * sizeof(INT16) * 2);
orig_write = write_position;
if (!stream_in_initialized)
@ -336,7 +319,7 @@ void sound_sdl::update_audio_stream(const INT16 *buffer, int samples_this_frame)
// now we know where to copy; let's do it
stream_buffer_in = stream_in;
copy_sample_data(m_machine, buffer, bytes_this_frame);
copy_sample_data(is_throttled, buffer, bytes_this_frame);
}
}
@ -371,22 +354,23 @@ void sound_sdl::set_mastervolume(int _attenuation)
//============================================================
static void sdl_callback(void *userdata, Uint8 *stream, int len)
{
sound_sdl *thiz = (sound_sdl *) userdata;
int len1, len2, sb_in;
sb_in = stream_buffer_in;
if (stream_loop)
sb_in += stream_buffer_size;
sb_in = thiz->stream_buffer_in;
if (thiz->stream_loop)
sb_in += thiz->stream_buffer_size;
if (sb_in < (stream_playpos+len))
if (sb_in < (thiz->stream_playpos+len))
{
if (LOG_SOUND)
fprintf(sound_log, "Underflow at sdl_callback: SPP=%d SBI=%d(%d) Len=%d\n", (int)stream_playpos, (int)sb_in, (int)stream_buffer_in, (int)len);
fprintf(sound_log, "Underflow at sdl_callback: SPP=%d SBI=%d(%d) Len=%d\n", (int)thiz->stream_playpos, (int)sb_in, (int)thiz->stream_buffer_in, (int)len);
return;
}
else if ((stream_playpos+len) > stream_buffer_size)
else if ((thiz->stream_playpos+len) > thiz->stream_buffer_size)
{
len1 = stream_buffer_size - stream_playpos;
len1 = thiz->stream_buffer_size - thiz->stream_playpos;
len2 = len - len1;
}
else
@ -395,28 +379,21 @@ static void sdl_callback(void *userdata, Uint8 *stream, int len)
len2 = 0;
}
if (snd_enabled)
{
memcpy(stream, stream_buffer + stream_playpos, len1);
memset(stream_buffer + stream_playpos, 0, len1); // no longer needed
if (len2)
{
memcpy(stream+len1, stream_buffer, len2);
memset(stream_buffer, 0, len2); // no longer needed
}
memcpy(stream, thiz->stream_buffer + thiz->stream_playpos, len1);
memset(thiz->stream_buffer + thiz->stream_playpos, 0, len1); // no longer needed
if (len2)
{
memcpy(stream+len1, thiz->stream_buffer, len2);
memset(thiz->stream_buffer, 0, len2); // no longer needed
}
}
else
{
memset(stream, 0, len);
}
// move the play cursor
stream_playpos += len1 + len2;
if (stream_playpos >= stream_buffer_size)
thiz->stream_playpos += len1 + len2;
if (thiz->stream_playpos >= thiz->stream_buffer_size)
{
stream_playpos -= stream_buffer_size;
stream_loop = 0;
thiz->stream_playpos -= thiz->stream_buffer_size;
thiz->stream_loop = 0;
if (LOG_SOUND)
fprintf(sound_log, "stream_loop set to 0 (stream_playpos looped)\n");
@ -424,89 +401,96 @@ static void sdl_callback(void *userdata, Uint8 *stream, int len)
if (LOG_SOUND)
fprintf(sound_log, "callback: xfer len1 %d len2 %d, playpos %d\n",
len1, len2, stream_playpos);
len1, len2, thiz->stream_playpos);
}
//============================================================
// sdl_init
// sound_sdl::init
//============================================================
static int sdl_init(running_machine &machine)
int sound_sdl::init()
{
int n_channels = 2;
int audio_latency;
SDL_AudioSpec aspec, obtained;
char audio_driver[16] = "";
if (SDL_InitSubSystem(SDL_INIT_AUDIO)) {
osd_printf_error("Could not initialize SDL %s\n", SDL_GetError());
exit(-1);
}
if (LOG_SOUND)
sound_log = fopen(SDLMAME_SOUND_LOG, "w");
osd_printf_verbose("Audio: Start initialization\n");
#if (SDLMAME_SDL2)
strncpy(audio_driver, SDL_GetCurrentAudioDriver(), sizeof(audio_driver));
#else
SDL_AudioDriverName(audio_driver, sizeof(audio_driver));
#endif
osd_printf_verbose("Audio: Driver is %s\n", audio_driver);
// skip if sound disabled
if (sample_rate() != 0)
{
if (SDL_InitSubSystem(SDL_INIT_AUDIO)) {
osd_printf_error("Could not initialize SDL %s\n", SDL_GetError());
return -1;
}
initialized_audio = 0;
osd_printf_verbose("Audio: Start initialization\n");
#if (SDLMAME_SDL2)
strncpy(audio_driver, SDL_GetCurrentAudioDriver(), sizeof(audio_driver));
#else
SDL_AudioDriverName(audio_driver, sizeof(audio_driver));
#endif
osd_printf_verbose("Audio: Driver is %s\n", audio_driver);
sdl_xfer_samples = SDL_XFER_SAMPLES;
stream_in_initialized = 0;
stream_loop = 0;
sdl_xfer_samples = SDL_XFER_SAMPLES;
stream_in_initialized = 0;
stream_loop = 0;
// set up the audio specs
aspec.freq = machine.sample_rate();
aspec.format = AUDIO_S16SYS; // keep endian independent
aspec.channels = n_channels;
aspec.samples = sdl_xfer_samples;
aspec.callback = sdl_callback;
aspec.userdata = 0;
// set up the audio specs
aspec.freq = sample_rate();
aspec.format = AUDIO_S16SYS; // keep endian independent
aspec.channels = n_channels;
aspec.samples = sdl_xfer_samples;
aspec.callback = sdl_callback;
aspec.userdata = this;
if (SDL_OpenAudio(&aspec, &obtained) < 0)
goto cant_start_audio;
if (SDL_OpenAudio(&aspec, &obtained) < 0)
goto cant_start_audio;
initialized_audio = 1;
snd_enabled = 1;
osd_printf_verbose("Audio: frequency: %d, channels: %d, samples: %d\n",
obtained.freq, obtained.channels, obtained.samples);
osd_printf_verbose("Audio: frequency: %d, channels: %d, samples: %d\n",
obtained.freq, obtained.channels, obtained.samples);
sdl_xfer_samples = obtained.samples;
sdl_xfer_samples = obtained.samples;
audio_latency = m_audio_latency;
audio_latency = downcast<sdl_options &>(machine.options()).audio_latency();
// pin audio latency
if (audio_latency > MAX_AUDIO_LATENCY)
{
audio_latency = MAX_AUDIO_LATENCY;
}
else if (audio_latency < 1)
{
audio_latency = 1;
}
// pin audio latency
if (audio_latency > MAX_AUDIO_LATENCY)
{
audio_latency = MAX_AUDIO_LATENCY;
}
else if (audio_latency < 1)
{
audio_latency = 1;
}
// compute the buffer sizes
stream_buffer_size = (sample_rate() * 2 * sizeof(INT16) * (2 + audio_latency)) / 30;
stream_buffer_size = (stream_buffer_size / 1024) * 1024;
if (stream_buffer_size < 1024)
stream_buffer_size = 1024;
// compute the buffer sizes
stream_buffer_size = (machine.sample_rate() * 2 * sizeof(INT16) * (2 + audio_latency)) / 30;
stream_buffer_size = (stream_buffer_size / 1024) * 1024;
if (stream_buffer_size < 1024)
stream_buffer_size = 1024;
// create the buffers
if (sdl_create_buffers())
goto cant_create_buffers;
// create the buffers
if (sdl_create_buffers())
goto cant_create_buffers;
// set the startup volume
set_mastervolume(attenuation);
osd_printf_verbose("Audio: End initialization\n");
return 0;
osd_printf_verbose("Audio: End initialization\n");
return 0;
// error handling
cant_create_buffers:
cant_start_audio:
osd_printf_verbose("Audio: Initialization failed. SDL error: %s\n", SDL_GetError());
// error handling
cant_create_buffers:
cant_start_audio:
osd_printf_verbose("Audio: Initialization failed. SDL error: %s\n", SDL_GetError());
return -1;
}
return 0;
return 0;
}
@ -515,15 +499,29 @@ cant_start_audio:
// sdl_kill
//============================================================
static void sdl_kill(running_machine &machine)
void sound_sdl::exit()
{
if (initialized_audio)
{
osd_printf_verbose("sdl_kill: closing audio\n");
// if nothing to do, don't do it
if (sample_rate() == 0)
return;
osd_printf_verbose("sdl_kill: closing audio\n");
SDL_CloseAudio();
SDL_CloseAudio();
}
SDL_QuitSubSystem(SDL_INIT_AUDIO);
// kill the buffers
sdl_destroy_buffers();
// print out over/underflow stats
if (buffer_overflows || buffer_underflows)
osd_printf_verbose("Sound buffer: overflows=%d underflows=%d\n", buffer_overflows, buffer_underflows);
if (LOG_SOUND)
{
fprintf(sound_log, "Sound buffer: overflows=%d underflows=%d\n", buffer_overflows, buffer_underflows);
fclose(sound_log);
}
}
@ -532,7 +530,7 @@ static void sdl_kill(running_machine &machine)
// dsound_create_buffers
//============================================================
static int sdl_create_buffers(void)
int sound_sdl::sdl_create_buffers(void)
{
osd_printf_verbose("sdl_create_buffers: creating stream buffer of %u bytes\n", stream_buffer_size);
@ -542,16 +540,22 @@ static int sdl_create_buffers(void)
return 0;
}
//============================================================
// sdl_destroy_buffers
//============================================================
static void sdl_destroy_buffers(void)
void sound_sdl::sdl_destroy_buffers(void)
{
// release the buffer
if (stream_buffer)
global_free_array(stream_buffer);
stream_buffer = NULL;
}
#else /* SDLMAME_UNIX */
MODULE_NOT_SUPPORTED(sound_sdl, OSD_SOUND_PROVIDER, "sdl")
#endif
MODULE_DEFINITION(SOUND_SDL, sound_sdl)

View File

@ -1,32 +0,0 @@
//============================================================
//
// sound.c - SDL implementation of MAME sound routines
//
// Copyright (c) 1996-2010, Nicola Salmoria and the MAME Team.
// Visit http://mamedev.org for licensing and usage restrictions.
//
// SDLMAME by Olivier Galibert and R. Belmont
//
//============================================================
#pragma once
#ifndef __SOUND_SDL_H__
#define __SOUND_SDL_H__
#include "osdepend.h"
#include "modules/lib/osdobj_common.h"
class sound_sdl : public osd_sound_interface
{
public:
// construction/destruction
sound_sdl(const osd_interface &osd, running_machine &machine);
virtual ~sound_sdl();
virtual void update_audio_stream(const INT16 *buffer, int samples_this_frame);
virtual void set_mastervolume(int attenuation);
};
extern const osd_sound_type OSD_SOUND_SDL;
#endif /* __SOUND_SDL_H__ */

View File

@ -0,0 +1,34 @@
/*
* sound_module.h
*
*/
#ifndef SOUND_MODULE_H_
#define SOUND_MODULE_H_
#include "osdepend.h"
#include "modules/osdmodule.h"
//============================================================
// CONSTANTS
//============================================================
#define OSD_SOUND_PROVIDER "sound"
class sound_module
{
public:
sound_module() : m_sample_rate(0), m_audio_latency(1) { }
virtual ~sound_module() { }
virtual void update_audio_stream(bool is_throttled, const INT16 *buffer, int samples_this_frame) = 0;
virtual void set_mastervolume(int attenuation) = 0;
int sample_rate() { return m_sample_rate; }
int m_sample_rate;
int m_audio_latency;
};
#endif /* FONT_MODULE_H_ */

View File

@ -189,7 +189,6 @@ public:
virtual void customize_input_type_list(simple_list<input_type_entry> &typelist);
virtual void video_register();
virtual void sound_register();
virtual void debugger_register();
virtual bool video_init();

View File

@ -204,14 +204,12 @@ endif
ifeq ($(TARGETOS),unix)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = tc
FONT_IMPLEMENTATION = sdl
endif
ifeq ($(TARGETOS),linux)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = tc
SDL_NETWORK = taptun
FONT_IMPLEMENTATION = sdl
ifndef NO_USE_MIDI
INCPATH += `pkg-config --cflags alsa`
@ -223,7 +221,6 @@ endif
ifeq ($(TARGETOS),freebsd)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = tc
FONT_IMPLEMENTATION = sdl
DEFS += -DNO_AFFINITY_NP
LIBS += -lutil
# /usr/local/include is not considered a system include directory
@ -235,7 +232,6 @@ endif
ifeq ($(TARGETOS),openbsd)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = ntc
FONT_IMPLEMENTATION = sdl
LIBS += -lutil
NO_USE_MIDI = 1
endif
@ -243,7 +239,6 @@ endif
ifeq ($(TARGETOS),netbsd)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = ntc
FONT_IMPLEMENTATION = sdl
LIBS += -lutil
NO_USE_MIDI = 1
endif
@ -252,14 +247,12 @@ ifeq ($(TARGETOS),solaris)
BASE_TARGETOS = unix
DEFS += -DNO_AFFINITY_NP -UHAVE_VSNPRINTF -DNO_vsnprintf
SYNC_IMPLEMENTATION = tc
FONT_IMPLEMENTATION = sdl
NO_USE_MIDI = 1
endif
ifeq ($(TARGETOS),haiku)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = ntc
FONT_IMPLEMENTATION = sdl
NO_X11 = 1
NO_USE_XINPUT = 1
NO_USE_MIDI = 1
@ -270,7 +263,6 @@ endif
ifeq ($(TARGETOS),emscripten)
BASE_TARGETOS = unix
SYNC_IMPLEMENTATION = mini
FONT_IMPLEMENTATION = none
NO_DEBUGGER = 1
NO_X11 = 1
NO_USE_XINPUT = 1
@ -282,7 +274,6 @@ endif
ifeq ($(TARGETOS),macosx)
NO_USE_QTDEBUG = 1
BASE_TARGETOS = unix
FONT_IMPLEMENTATION = osx
DEFS += -DSDLMAME_UNIX -DSDLMAME_MACOSX -DSDLMAME_DARWIN
ifndef NO_USE_MIDI
@ -335,7 +326,6 @@ endif
ifeq ($(TARGETOS),win32)
BASE_TARGETOS = win32
SYNC_IMPLEMENTATION = windows
FONT_IMPLEMENTATION = windows
NO_X11 = 1
NO_USE_XINPUT = 1
DEFS += -DSDLMAME_WIN32 -DX64_WINDOWS_ABI
@ -373,7 +363,6 @@ ifeq ($(TARGETOS),os2)
BASE_TARGETOS = os2
DEFS += -DSDLMAME_OS2
SYNC_IMPLEMENTATION = os2
FONT_IMPLEMENTATION = none
NO_DEBUGGER = 1
NO_X11 = 1
NO_USE_XINPUT = 1
@ -398,11 +387,6 @@ NO_DEBUGGER = 1
endif
endif
ifndef FONT_IMPLEMENTATION
$(error Please define FONT_IMPLEMENTATION !)
endif
#-------------------------------------------------
# object and source roots
#-------------------------------------------------
@ -444,7 +428,10 @@ OSDOBJS = \
$(SDLMAIN) \
$(SDLOBJ)/sdlmain.o \
$(SDLOBJ)/input.o \
$(OSDOBJ)/modules/sound/js_sound.o \
$(OSDOBJ)/modules/sound/direct_sound.o \
$(OSDOBJ)/modules/sound/sdl_sound.o \
$(OSDOBJ)/modules/sound/none.o \
$(SDLOBJ)/video.o \
$(SDLOBJ)/drawsdl.o \
$(SDLOBJ)/window.o \

View File

@ -57,14 +57,6 @@
#include "osdsdl.h"
#include "modules/lib/osdlib.h"
#include "modules/sound/sdl_sound.h"
#if defined(SDLMAME_EMSCRIPTEN)
#include "modules/sound/js_sound.h"
#endif
#if defined(SDLMAME_WIN32)
#include "modules/sound/direct_sound.h"
#endif
#if !defined(NO_DEBUGGER)
#include "modules/debugger/debugqt.h"
#endif
@ -538,25 +530,6 @@ void sdl_osd_interface::video_register()
//video_options_add("auto", NULL); // making d3d video default one
}
//============================================================
// sound_register
//============================================================
void sdl_osd_interface::sound_register()
{
sound_options_add("sdl", OSD_SOUND_SDL);
#if defined(SDLMAME_WIN32)
sound_options_add("dsound", OSD_SOUND_DIRECT_SOUND);
#endif
#if defined(SDLMAME_EMSCRIPTEN)
sound_options_add("js", OSD_SOUND_JS);
sound_options_add("auto", OSD_SOUND_JS); // making JS audio default one
#else
sound_options_add("auto", OSD_SOUND_SDL); // making SDL audio default one
#endif
}
//============================================================
// debugger_register
//============================================================

View File

@ -357,7 +357,6 @@ OSDCOREOBJS = \
$(WINOBJ)/winsocket.o \
$(OSDOBJ)/modules/sync/work_osd.o \
$(OSDOBJ)/modules/lib/osdlib_win32.o \
$(OSDOBJ)/modules/font/font_windows.o \
$(OSDOBJ)/modules/osdmodule.o \
$(WINOBJ)/winptty.o \
@ -375,7 +374,10 @@ OSDOBJS = \
$(WINOBJ)/drawnone.o \
$(WINOBJ)/input.o \
$(WINOBJ)/output.o \
$(OSDOBJ)/modules/sound/direct_sound.o \
$(OSDOBJ)/modules/sound/js_sound.o \
$(OSDOBJ)/modules/sound/direct_sound.o \
$(OSDOBJ)/modules/sound/sdl_sound.o \
$(OSDOBJ)/modules/sound/none.o \
$(WINOBJ)/video.o \
$(WINOBJ)/window.o \
$(WINOBJ)/winmenu.o \

View File

@ -39,11 +39,6 @@
#include "debugger.h"
#include "winfile.h"
#include "modules/sound/direct_sound.h"
#if (USE_SDL)
#include "modules/sound/sdl_sound.h"
#endif
#include "modules/debugger/debugwin.h"
#if (USE_QTDEBUG)
@ -540,20 +535,6 @@ void windows_osd_interface::video_register()
//video_options_add("auto", NULL); // making d3d video default one
}
//============================================================
// sound_register
//============================================================
void windows_osd_interface::sound_register()
{
sound_options_add("dsound", OSD_SOUND_DIRECT_SOUND);
#if (USE_SDL)
sound_options_add("sdl", OSD_SOUND_SDL);
#endif
sound_options_add("auto", OSD_SOUND_DIRECT_SOUND); // making Direct Sound audio default one
}
//============================================================
// debugger_register
//============================================================

View File

@ -253,7 +253,6 @@ public:
virtual void customize_input_type_list(simple_list<input_type_entry> &typelist);
virtual void video_register();
virtual void sound_register();
virtual void debugger_register();
virtual bool video_init();