summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGravatarGravatar Andrew Gardner <andrew-gardner@users.noreply.github.com>2013-02-05 16:17:15 +0000
committerGravatarGravatar Andrew Gardner <andrew-gardner@users.noreply.github.com>2013-02-05 16:17:15 +0000
commit3e7883e3fcf57399319157242ee4031b6323ca3b (patch)
treead1e311d5495a86415cb79dc5a223c52496969c4
parent96d5e7fea38a52481b800c60694aff7c34238a69 (diff)
downloadmame-3e7883e3fcf57399319157242ee4031b6323ca3b.tar.xz
mame-3e7883e3fcf57399319157242ee4031b6323ca3b.zip
Modernized iremga20 & k005289 sound devices. [Andrew Gardner]
-rw-r--r--src/emu/sound/iremga20.c250
-rw-r--r--src/emu/sound/iremga20.h55
-rw-r--r--src/emu/sound/k005289.c261
-rw-r--r--src/emu/sound/k005289.h73
-rw-r--r--src/mame/drivers/m107.c4
-rw-r--r--src/mame/drivers/m92.c4
-rw-r--r--src/mame/drivers/nemesis.c28
7 files changed, 339 insertions, 336 deletions
diff --git a/src/emu/sound/iremga20.c b/src/emu/sound/iremga20.c
index 2203aa0a6d4..c2e32675731 100644
--- a/src/emu/sound/iremga20.c
+++ b/src/emu/sound/iremga20.c
@@ -31,41 +31,80 @@ Revisions:
#define MAX_VOL 256
-struct IremGA20_channel_def
+
+// device type definition
+const device_type IREMGA20 = &device_creator<iremga20_device>;
+
+
+//**************************************************************************
+// LIVE DEVICE
+//**************************************************************************
+
+//-------------------------------------------------
+// iremga20_device - constructor
+//-------------------------------------------------
+
+iremga20_device::iremga20_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
+ : device_t(mconfig, IREMGA20, "Irem GA20", tag, owner, clock),
+ device_sound_interface(mconfig, *this),
+ m_rom(NULL),
+ m_rom_size(0),
+ m_stream(NULL)
{
- UINT32 rate;
- UINT32 size;
- UINT32 start;
- UINT32 pos;
- UINT32 frac;
- UINT32 end;
- UINT32 volume;
- UINT32 pan;
- UINT32 effect;
- UINT32 play;
-};
-
-struct ga20_state
+}
+
+
+//-------------------------------------------------
+// device_start - device-specific startup
+//-------------------------------------------------
+
+void iremga20_device::device_start()
{
- UINT8 *rom;
- INT32 rom_size;
- sound_stream * stream;
- UINT16 regs[0x40];
- struct IremGA20_channel_def channel[4];
-};
+ int i;
+
+ /* Initialize our chip structure */
+ m_rom = m_region->base();
+ m_rom_size = m_region->bytes();
+
+ iremga20_reset();
+
+ for ( i = 0; i < 0x40; i++ )
+ m_regs[i] = 0;
+ m_stream = stream_alloc(0, 2, clock()/4);
-INLINE ga20_state *get_safe_token(device_t *device)
+ save_item(NAME(m_regs));
+ for (i = 0; i < 4; i++)
+ {
+ save_item(NAME(m_channel[i].rate), i);
+ save_item(NAME(m_channel[i].size), i);
+ save_item(NAME(m_channel[i].start), i);
+ save_item(NAME(m_channel[i].pos), i);
+ save_item(NAME(m_channel[i].end), i);
+ save_item(NAME(m_channel[i].volume), i);
+ save_item(NAME(m_channel[i].pan), i);
+ save_item(NAME(m_channel[i].effect), i);
+ save_item(NAME(m_channel[i].play), i);
+ }
+}
+
+
+//-------------------------------------------------
+// device_reset - device-specific reset
+//-------------------------------------------------
+
+void iremga20_device::device_reset()
{
- assert(device != NULL);
- assert(device->type() == IREMGA20);
- return (ga20_state *)downcast<iremga20_device *>(device)->token();
+ iremga20_reset();
}
-static STREAM_UPDATE( IremGA20_update )
+//-------------------------------------------------
+// sound_stream_update - handle a stream update
+//-------------------------------------------------
+
+void iremga20_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
{
- ga20_state *chip = (ga20_state *)param;
UINT32 rate[4], pos[4], frac[4], end[4], vol[4], play[4];
UINT8 *pSamples;
stream_sample_t *outL, *outR;
@@ -74,16 +113,16 @@ static STREAM_UPDATE( IremGA20_update )
/* precache some values */
for (i=0; i < 4; i++)
{
- rate[i] = chip->channel[i].rate;
- pos[i] = chip->channel[i].pos;
- frac[i] = chip->channel[i].frac;
- end[i] = chip->channel[i].end - 0x20;
- vol[i] = chip->channel[i].volume;
- play[i] = chip->channel[i].play;
+ rate[i] = m_channel[i].rate;
+ pos[i] = m_channel[i].pos;
+ frac[i] = m_channel[i].frac;
+ end[i] = m_channel[i].end - 0x20;
+ vol[i] = m_channel[i].volume;
+ play[i] = m_channel[i].play;
}
i = samples;
- pSamples = chip->rom;
+ pSamples = m_rom;
outL = outputs[0];
outR = outputs[1];
@@ -133,72 +172,70 @@ static STREAM_UPDATE( IremGA20_update )
/* update the regs now */
for (i=0; i < 4; i++)
{
- chip->channel[i].pos = pos[i];
- chip->channel[i].frac = frac[i];
- chip->channel[i].play = play[i];
+ m_channel[i].pos = pos[i];
+ m_channel[i].frac = frac[i];
+ m_channel[i].play = play[i];
}
}
-WRITE8_DEVICE_HANDLER( irem_ga20_w )
+WRITE8_MEMBER( iremga20_device::irem_ga20_w )
{
- ga20_state *chip = get_safe_token(device);
int channel;
//logerror("GA20: Offset %02x, data %04x\n",offset,data);
- chip->stream->update();
+ m_stream->update();
channel = offset >> 3;
- chip->regs[offset] = data;
+ m_regs[offset] = data;
switch (offset & 0x7)
{
case 0: /* start address low */
- chip->channel[channel].start = ((chip->channel[channel].start)&0xff000) | (data<<4);
+ m_channel[channel].start = ((m_channel[channel].start)&0xff000) | (data<<4);
break;
case 1: /* start address high */
- chip->channel[channel].start = ((chip->channel[channel].start)&0x00ff0) | (data<<12);
+ m_channel[channel].start = ((m_channel[channel].start)&0x00ff0) | (data<<12);
break;
case 2: /* end address low */
- chip->channel[channel].end = ((chip->channel[channel].end)&0xff000) | (data<<4);
+ m_channel[channel].end = ((m_channel[channel].end)&0xff000) | (data<<4);
break;
case 3: /* end address high */
- chip->channel[channel].end = ((chip->channel[channel].end)&0x00ff0) | (data<<12);
+ m_channel[channel].end = ((m_channel[channel].end)&0x00ff0) | (data<<12);
break;
case 4:
- chip->channel[channel].rate = 0x1000000 / (256 - data);
+ m_channel[channel].rate = 0x1000000 / (256 - data);
break;
case 5: //AT: gain control
- chip->channel[channel].volume = (data * MAX_VOL) / (data + 10);
+ m_channel[channel].volume = (data * MAX_VOL) / (data + 10);
break;
case 6: //AT: this is always written 2(enabling both channels?)
- chip->channel[channel].play = data;
- chip->channel[channel].pos = chip->channel[channel].start;
- chip->channel[channel].frac = 0;
+ m_channel[channel].play = data;
+ m_channel[channel].pos = m_channel[channel].start;
+ m_channel[channel].frac = 0;
break;
}
}
-READ8_DEVICE_HANDLER( irem_ga20_r )
+READ8_MEMBER( iremga20_device::irem_ga20_r )
{
- ga20_state *chip = get_safe_token(device);
int channel;
- chip->stream->update();
+ m_stream->update();
channel = offset >> 3;
switch (offset & 0x7)
{
case 7: // voice status. bit 0 is 1 if active. (routine around 0xccc in rtypeleo)
- return chip->channel[channel].play ? 1 : 0;
+ return m_channel[channel].play ? 1 : 0;
default:
logerror("GA20: read unk. register %d, channel %d\n", offset & 0xf, channel);
@@ -208,104 +245,21 @@ READ8_DEVICE_HANDLER( irem_ga20_r )
return 0;
}
-static void iremga20_reset(ga20_state *chip)
-{
- int i;
-
- for( i = 0; i < 4; i++ ) {
- chip->channel[i].rate = 0;
- chip->channel[i].size = 0;
- chip->channel[i].start = 0;
- chip->channel[i].pos = 0;
- chip->channel[i].frac = 0;
- chip->channel[i].end = 0;
- chip->channel[i].volume = 0;
- chip->channel[i].pan = 0;
- chip->channel[i].effect = 0;
- chip->channel[i].play = 0;
- }
-}
-
-
-static DEVICE_RESET( iremga20 )
-{
- iremga20_reset(get_safe_token(device));
-}
-static DEVICE_START( iremga20 )
+void iremga20_device::iremga20_reset()
{
- ga20_state *chip = get_safe_token(device);
int i;
- /* Initialize our chip structure */
- chip->rom = *device->region();
- chip->rom_size = device->region()->bytes();
-
- iremga20_reset(chip);
-
- for ( i = 0; i < 0x40; i++ )
- chip->regs[i] = 0;
-
- chip->stream = device->machine().sound().stream_alloc( *device, 0, 2, device->clock()/4, chip, IremGA20_update );
-
- device->save_item(NAME(chip->regs));
- for (i = 0; i < 4; i++)
- {
- device->save_item(NAME(chip->channel[i].rate), i);
- device->save_item(NAME(chip->channel[i].size), i);
- device->save_item(NAME(chip->channel[i].start), i);
- device->save_item(NAME(chip->channel[i].pos), i);
- device->save_item(NAME(chip->channel[i].end), i);
- device->save_item(NAME(chip->channel[i].volume), i);
- device->save_item(NAME(chip->channel[i].pan), i);
- device->save_item(NAME(chip->channel[i].effect), i);
- device->save_item(NAME(chip->channel[i].play), i);
+ for( i = 0; i < 4; i++ ) {
+ m_channel[i].rate = 0;
+ m_channel[i].size = 0;
+ m_channel[i].start = 0;
+ m_channel[i].pos = 0;
+ m_channel[i].frac = 0;
+ m_channel[i].end = 0;
+ m_channel[i].volume = 0;
+ m_channel[i].pan = 0;
+ m_channel[i].effect = 0;
+ m_channel[i].play = 0;
}
}
-
-const device_type IREMGA20 = &device_creator<iremga20_device>;
-
-iremga20_device::iremga20_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
- : device_t(mconfig, IREMGA20, "Irem GA20", tag, owner, clock),
- device_sound_interface(mconfig, *this)
-{
- m_token = global_alloc_clear(ga20_state);
-}
-
-//-------------------------------------------------
-// device_config_complete - perform any
-// operations now that the configuration is
-// complete
-//-------------------------------------------------
-
-void iremga20_device::device_config_complete()
-{
-}
-
-//-------------------------------------------------
-// device_start - device-specific startup
-//-------------------------------------------------
-
-void iremga20_device::device_start()
-{
- DEVICE_START_NAME( iremga20 )(this);
-}
-
-//-------------------------------------------------
-// device_reset - device-specific reset
-//-------------------------------------------------
-
-void iremga20_device::device_reset()
-{
- DEVICE_RESET_NAME( iremga20 )(this);
-}
-
-//-------------------------------------------------
-// sound_stream_update - handle a stream update
-//-------------------------------------------------
-
-void iremga20_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");
-}
diff --git a/src/emu/sound/iremga20.h b/src/emu/sound/iremga20.h
index bd90e7082e3..02a70f5aaa4 100644
--- a/src/emu/sound/iremga20.h
+++ b/src/emu/sound/iremga20.h
@@ -8,31 +8,66 @@
#ifndef __IREMGA20_H__
#define __IREMGA20_H__
-#include "devlegcy.h"
-DECLARE_WRITE8_DEVICE_HANDLER( irem_ga20_w );
-DECLARE_READ8_DEVICE_HANDLER( irem_ga20_r );
+//**************************************************************************
+// INTERFACE CONFIGURATION MACROS
+//**************************************************************************
+
+#define MCFG_IREMGA20_ADD(_tag, _clock) \
+ MCFG_DEVICE_ADD(_tag, IREMGA20, _clock)
+#define MCFG_IREMGA20_REPLACE(_tag, _clock) \
+ MCFG_DEVICE_REPLACE(_tag, IREMGA20, _clock)
+
+
+//**************************************************************************
+// TYPE DEFINITIONS
+//**************************************************************************
+
+struct IremGA20_channel_def
+{
+ UINT32 rate;
+ UINT32 size;
+ UINT32 start;
+ UINT32 pos;
+ UINT32 frac;
+ UINT32 end;
+ UINT32 volume;
+ UINT32 pan;
+ UINT32 effect;
+ UINT32 play;
+};
+
+
+// ======================> iremga20_device
class iremga20_device : public device_t,
- public device_sound_interface
+ public device_sound_interface
{
public:
iremga20_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
- ~iremga20_device() { global_free(m_token); }
+ ~iremga20_device() { }
- // access to legacy token
- void *token() const { assert(m_token != NULL); return m_token; }
protected:
// device-level overrides
- virtual void device_config_complete();
virtual void device_start();
virtual void device_reset();
// sound stream update overrides
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples);
+
+public:
+ DECLARE_WRITE8_MEMBER( irem_ga20_w );
+ DECLARE_READ8_MEMBER( irem_ga20_r );
+
+private:
+ void iremga20_reset();
+
private:
- // internal state
- void *m_token;
+ UINT8 *m_rom;
+ INT32 m_rom_size;
+ sound_stream *m_stream;
+ UINT16 m_regs[0x40];
+ IremGA20_channel_def m_channel[4];
};
extern const device_type IREMGA20;
diff --git a/src/emu/sound/k005289.c b/src/emu/sound/k005289.c
index 243064ec4c5..c3f492e6df2 100644
--- a/src/emu/sound/k005289.c
+++ b/src/emu/sound/k005289.c
@@ -30,77 +30,89 @@
#define FREQBASEBITS 16
-/* this structure defines the parameters for a channel */
-struct k005289_sound_channel
-{
- int frequency;
- int counter;
- int volume;
- const unsigned char *wave;
-};
-struct k005289_state
-{
- k005289_sound_channel channel_list[2];
+// device type definition
+const device_type K005289 = &device_creator<k005289_device>;
- /* global sound parameters */
- const unsigned char *sound_prom;
- sound_stream * stream;
- int mclock,rate;
- /* mixer tables and internal buffers */
- INT16 *mixer_table;
- INT16 *mixer_lookup;
- short *mixer_buffer;
+//**************************************************************************
+// LIVE DEVICE
+//**************************************************************************
- int k005289_A_frequency,k005289_B_frequency;
- int k005289_A_volume,k005289_B_volume;
- int k005289_A_waveform,k005289_B_waveform;
- int k005289_A_latch,k005289_B_latch;
-};
+//-------------------------------------------------
+// k005289_device - constructor
+//-------------------------------------------------
-INLINE k005289_state *get_safe_token(device_t *device)
+k005289_device::k005289_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
+ : device_t(mconfig, K005289, "K005289", tag, owner, clock),
+ device_sound_interface(mconfig, *this),
+ m_sound_prom(NULL),
+ m_stream(NULL),
+ m_mclock(0),
+ m_rate(0),
+ m_mixer_table(NULL),
+ m_mixer_lookup(NULL),
+ m_mixer_buffer(NULL),
+ m_k005289_A_frequency(0),
+ m_k005289_B_frequency(0),
+ m_k005289_A_volume(0),
+ m_k005289_B_volume(0),
+ m_k005289_A_waveform(0),
+ m_k005289_B_waveform(0),
+ m_k005289_A_latch(0),
+ m_k005289_B_latch(0)
{
- assert(device != NULL);
- assert(device->type() == K005289);
- return (k005289_state *)downcast<k005289_device *>(device)->token();
}
-/* build a table to divide by the number of voices */
-static void make_mixer_table(running_machine &machine, k005289_state *info, int voices)
+
+//-------------------------------------------------
+// device_start - device-specific startup
+//-------------------------------------------------
+
+void k005289_device::device_start()
{
- int count = voices * 128;
- int i;
- int gain = 16;
+ k005289_sound_channel *voice;
- /* allocate memory */
- info->mixer_table = auto_alloc_array(machine, INT16, 256 * voices);
+ voice = m_channel_list;
- /* find the middle of the table */
- info->mixer_lookup = info->mixer_table + (128 * voices);
+ /* get stream channels */
+ m_rate = clock()/16;
+ m_stream = stream_alloc(0, 1, m_rate);
+ m_mclock = clock();
- /* fill in the table - 16 bit case */
- for (i = 0; i < count; i++)
- {
- int val = i * gain * 16 / voices;
- if (val > 32767) val = 32767;
- info->mixer_lookup[ i] = val;
- info->mixer_lookup[-i] = -val;
- }
+ /* allocate a pair of buffers to mix into - 1 second's worth should be more than enough */
+ m_mixer_buffer = auto_alloc_array(machine(), short, 2 * m_rate);
+
+ /* build the mixer table */
+ make_mixer_table(2);
+
+ m_sound_prom = m_region->base();
+
+ /* reset all the voices */
+ voice[0].frequency = 0;
+ voice[0].volume = 0;
+ voice[0].wave = &m_sound_prom[0];
+ voice[0].counter = 0;
+ voice[1].frequency = 0;
+ voice[1].volume = 0;
+ voice[1].wave = &m_sound_prom[0x100];
+ voice[1].counter = 0;
}
-/* generate sound to the mix buffer */
-static STREAM_UPDATE( K005289_update )
+//-------------------------------------------------
+// sound_stream_update - handle a stream update
+//-------------------------------------------------
+
+void k005289_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
{
- k005289_state *info = (k005289_state *)param;
- k005289_sound_channel *voice=info->channel_list;
+ k005289_sound_channel *voice=m_channel_list;
stream_sample_t *buffer = outputs[0];
short *mix;
int i,v,f;
/* zap the contents of the mixer buffer */
- memset(info->mixer_buffer, 0, samples * sizeof(INT16));
+ memset(m_mixer_buffer, 0, samples * sizeof(INT16));
v=voice[0].volume;
f=voice[0].frequency;
@@ -109,14 +121,14 @@ static STREAM_UPDATE( K005289_update )
const unsigned char *w = voice[0].wave;
int c = voice[0].counter;
- mix = info->mixer_buffer;
+ mix = m_mixer_buffer;
/* add our contribution */
for (i = 0; i < samples; i++)
{
int offs;
- c+=(long)((((float)info->mclock / (float)(f * 16))*(float)(1<<FREQBASEBITS)) / (float)(info->rate / 32));
+ c+=(long)((((float)m_mclock / (float)(f * 16))*(float)(1<<FREQBASEBITS)) / (float)(m_rate / 32));
offs = (c >> 16) & 0x1f;
*mix++ += ((w[offs] & 0x0f) - 8) * v;
}
@@ -132,14 +144,14 @@ static STREAM_UPDATE( K005289_update )
const unsigned char *w = voice[1].wave;
int c = voice[1].counter;
- mix = info->mixer_buffer;
+ mix = m_mixer_buffer;
/* add our contribution */
for (i = 0; i < samples; i++)
{
int offs;
- c+=(long)((((float)info->mclock / (float)(f * 16))*(float)(1<<FREQBASEBITS)) / (float)(info->rate / 32));
+ c+=(long)((((float)m_mclock / (float)(f * 16))*(float)(1<<FREQBASEBITS)) / (float)(m_rate / 32));
offs = (c >> 16) & 0x1f;
*mix++ += ((w[offs] & 0x0f) - 8) * v;
}
@@ -149,135 +161,92 @@ static STREAM_UPDATE( K005289_update )
}
/* mix it down */
- mix = info->mixer_buffer;
+ mix = m_mixer_buffer;
for (i = 0; i < samples; i++)
- *buffer++ = info->mixer_lookup[*mix++];
+ *buffer++ = m_mixer_lookup[*mix++];
}
-static DEVICE_START( k005289 )
-{
- k005289_sound_channel *voice;
- k005289_state *info = get_safe_token(device);
-
- voice = info->channel_list;
-
- /* get stream channels */
- info->rate = device->clock()/16;
- info->stream = device->machine().sound().stream_alloc(*device, 0, 1, info->rate, info, K005289_update);
- info->mclock = device->clock();
-
- /* allocate a pair of buffers to mix into - 1 second's worth should be more than enough */
- info->mixer_buffer = auto_alloc_array(device->machine(), short, 2 * info->rate);
-
- /* build the mixer table */
- make_mixer_table(device->machine(), info, 2);
-
- info->sound_prom = *device->region();
- /* reset all the voices */
- voice[0].frequency = 0;
- voice[0].volume = 0;
- voice[0].wave = &info->sound_prom[0];
- voice[0].counter = 0;
- voice[1].frequency = 0;
- voice[1].volume = 0;
- voice[1].wave = &info->sound_prom[0x100];
- voice[1].counter = 0;
-}
/********************************************************************************/
-static void k005289_recompute(k005289_state *info)
+/* build a table to divide by the number of voices */
+void k005289_device::make_mixer_table(int voices)
{
- k005289_sound_channel *voice = info->channel_list;
+ int count = voices * 128;
+ int i;
+ int gain = 16;
- info->stream->update(); /* update the streams */
+ /* allocate memory */
+ m_mixer_table = auto_alloc_array(machine(), INT16, 256 * voices);
- voice[0].frequency = info->k005289_A_frequency;
- voice[1].frequency = info->k005289_B_frequency;
- voice[0].volume = info->k005289_A_volume;
- voice[1].volume = info->k005289_B_volume;
- voice[0].wave = &info->sound_prom[32 * info->k005289_A_waveform];
- voice[1].wave = &info->sound_prom[32 * info->k005289_B_waveform + 0x100];
-}
+ /* find the middle of the table */
+ m_mixer_lookup = m_mixer_table + (128 * voices);
-WRITE8_DEVICE_HANDLER( k005289_control_A_w )
-{
- k005289_state *info = get_safe_token(device);
- info->k005289_A_volume=data&0xf;
- info->k005289_A_waveform=data>>5;
- k005289_recompute(info);
+ /* fill in the table - 16 bit case */
+ for (i = 0; i < count; i++)
+ {
+ int val = i * gain * 16 / voices;
+ if (val > 32767) val = 32767;
+ m_mixer_lookup[ i] = val;
+ m_mixer_lookup[-i] = -val;
+ }
}
-WRITE8_DEVICE_HANDLER( k005289_control_B_w )
-{
- k005289_state *info = get_safe_token(device);
- info->k005289_B_volume=data&0xf;
- info->k005289_B_waveform=data>>5;
- k005289_recompute(info);
-}
-WRITE8_DEVICE_HANDLER( k005289_pitch_A_w )
+void k005289_device::k005289_recompute()
{
- k005289_state *info = get_safe_token(device);
- info->k005289_A_latch = 0x1000 - offset;
-}
+ k005289_sound_channel *voice = m_channel_list;
-WRITE8_DEVICE_HANDLER( k005289_pitch_B_w )
-{
- k005289_state *info = get_safe_token(device);
- info->k005289_B_latch = 0x1000 - offset;
+ m_stream->update(); /* update the streams */
+
+ voice[0].frequency = m_k005289_A_frequency;
+ voice[1].frequency = m_k005289_B_frequency;
+ voice[0].volume = m_k005289_A_volume;
+ voice[1].volume = m_k005289_B_volume;
+ voice[0].wave = &m_sound_prom[32 * m_k005289_A_waveform];
+ voice[1].wave = &m_sound_prom[32 * m_k005289_B_waveform + 0x100];
}
-WRITE8_DEVICE_HANDLER( k005289_keylatch_A_w )
+
+WRITE8_MEMBER( k005289_device::k005289_control_A_w )
{
- k005289_state *info = get_safe_token(device);
- info->k005289_A_frequency = info->k005289_A_latch;
- k005289_recompute(info);
+ m_k005289_A_volume=data&0xf;
+ m_k005289_A_waveform=data>>5;
+ k005289_recompute();
}
-WRITE8_DEVICE_HANDLER( k005289_keylatch_B_w )
+
+WRITE8_MEMBER( k005289_device::k005289_control_B_w )
{
- k005289_state *info = get_safe_token(device);
- info->k005289_B_frequency = info->k005289_B_latch;
- k005289_recompute(info);
+ m_k005289_B_volume=data&0xf;
+ m_k005289_B_waveform=data>>5;
+ k005289_recompute();
}
-const device_type K005289 = &device_creator<k005289_device>;
-k005289_device::k005289_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock)
- : device_t(mconfig, K005289, "K005289", tag, owner, clock),
- device_sound_interface(mconfig, *this)
+WRITE8_MEMBER( k005289_device::k005289_pitch_A_w )
{
- m_token = global_alloc_clear(k005289_state);
+ m_k005289_A_latch = 0x1000 - offset;
}
-//-------------------------------------------------
-// device_config_complete - perform any
-// operations now that the configuration is
-// complete
-//-------------------------------------------------
-void k005289_device::device_config_complete()
+WRITE8_MEMBER( k005289_device::k005289_pitch_B_w )
{
+ m_k005289_B_latch = 0x1000 - offset;
}
-//-------------------------------------------------
-// device_start - device-specific startup
-//-------------------------------------------------
-void k005289_device::device_start()
+WRITE8_MEMBER( k005289_device::k005289_keylatch_A_w )
{
- DEVICE_START_NAME( k005289 )(this);
+ m_k005289_A_frequency = m_k005289_A_latch;
+ k005289_recompute();
}
-//-------------------------------------------------
-// sound_stream_update - handle a stream update
-//-------------------------------------------------
-void k005289_device::sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples)
+WRITE8_MEMBER( k005289_device::k005289_keylatch_B_w )
{
- // should never get here
- fatalerror("sound_stream_update called; not applicable to legacy sound devices\n");
+ m_k005289_B_frequency = m_k005289_B_latch;
+ k005289_recompute();
}
diff --git a/src/emu/sound/k005289.h b/src/emu/sound/k005289.h
index a593006813f..cef1781df7c 100644
--- a/src/emu/sound/k005289.h
+++ b/src/emu/sound/k005289.h
@@ -3,34 +3,79 @@
#ifndef __K005289_H__
#define __K005289_H__
-#include "devlegcy.h"
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_control_A_w );
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_control_B_w );
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_pitch_A_w );
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_pitch_B_w );
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_keylatch_A_w );
-DECLARE_WRITE8_DEVICE_HANDLER( k005289_keylatch_B_w );
+//**************************************************************************
+// INTERFACE CONFIGURATION MACROS
+//**************************************************************************
+
+#define MCFG_K005289_ADD(_tag, _clock) \
+ MCFG_DEVICE_ADD(_tag, K005289, _clock)
+#define MCFG_K005289_REPLACE(_tag, _clock) \
+ MCFG_DEVICE_REPLACE(_tag, K005289, _clock)
+
+
+//**************************************************************************
+// TYPE DEFINITIONS
+//**************************************************************************
+
+struct k005289_sound_channel
+{
+ int frequency;
+ int counter;
+ int volume;
+ const unsigned char *wave;
+};
+
+
+// ======================> k005289_device
class k005289_device : public device_t,
- public device_sound_interface
+ public device_sound_interface
{
public:
k005289_device(const machine_config &mconfig, const char *tag, device_t *owner, UINT32 clock);
- ~k005289_device() { global_free(m_token); }
+ ~k005289_device() { }
- // access to legacy token
- void *token() const { assert(m_token != NULL); return m_token; }
protected:
// device-level overrides
- virtual void device_config_complete();
virtual void device_start();
// sound stream update overrides
virtual void sound_stream_update(sound_stream &stream, stream_sample_t **inputs, stream_sample_t **outputs, int samples);
+
+public:
+ DECLARE_WRITE8_MEMBER( k005289_control_A_w );
+ DECLARE_WRITE8_MEMBER( k005289_control_B_w );
+ DECLARE_WRITE8_MEMBER( k005289_pitch_A_w );
+ DECLARE_WRITE8_MEMBER( k005289_pitch_B_w );
+ DECLARE_WRITE8_MEMBER( k005289_keylatch_A_w );
+ DECLARE_WRITE8_MEMBER( k005289_keylatch_B_w );
+
+private:
+ void make_mixer_table(int voices);
+ void k005289_recompute();
+
private:
- // internal state
- void *m_token;
+ k005289_sound_channel m_channel_list[2];
+
+ const unsigned char *m_sound_prom;
+ sound_stream *m_stream;
+ int m_mclock;
+ int m_rate;
+
+ /* mixer tables and internal buffers */
+ INT16 *m_mixer_table;
+ INT16 *m_mixer_lookup;
+ short *m_mixer_buffer;
+
+ int m_k005289_A_frequency;
+ int m_k005289_B_frequency;
+ int m_k005289_A_volume;
+ int m_k005289_B_volume;
+ int m_k005289_A_waveform;
+ int m_k005289_B_waveform;
+ int m_k005289_A_latch;
+ int m_k005289_B_latch;
};
extern const device_type K005289;
diff --git a/src/mame/drivers/m107.c b/src/mame/drivers/m107.c
index be3129ae458..0693ee272e9 100644
--- a/src/mame/drivers/m107.c
+++ b/src/mame/drivers/m107.c
@@ -180,7 +180,7 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START( sound_map, AS_PROGRAM, 16, m107_state )
AM_RANGE(0x00000, 0x1ffff) AM_ROM
AM_RANGE(0xa0000, 0xa3fff) AM_RAM
- AM_RANGE(0xa8000, 0xa803f) AM_DEVREADWRITE8_LEGACY("irem", irem_ga20_r, irem_ga20_w, 0x00ff)
+ AM_RANGE(0xa8000, 0xa803f) AM_DEVREADWRITE8("irem", iremga20_device, irem_ga20_r, irem_ga20_w, 0x00ff)
AM_RANGE(0xa8040, 0xa8043) AM_DEVREADWRITE8("ymsnd", ym2151_device, read, write, 0x00ff)
AM_RANGE(0xa8044, 0xa8045) AM_READWRITE(m107_soundlatch_r, m107_sound_irq_ack_w)
AM_RANGE(0xa8046, 0xa8047) AM_WRITE(m107_sound_status_w)
@@ -789,7 +789,7 @@ static MACHINE_CONFIG_START( firebarr, m107_state )
MCFG_SOUND_ROUTE(0, "lspeaker", 0.40)
MCFG_SOUND_ROUTE(1, "rspeaker", 0.40)
- MCFG_SOUND_ADD("irem", IREMGA20, 14318180/4)
+ MCFG_IREMGA20_ADD("irem", 14318180/4)
MCFG_SOUND_ROUTE(0, "lspeaker", 1.0)
MCFG_SOUND_ROUTE(1, "rspeaker", 1.0)
MACHINE_CONFIG_END
diff --git a/src/mame/drivers/m92.c b/src/mame/drivers/m92.c
index eb51a005964..0be3bbd847a 100644
--- a/src/mame/drivers/m92.c
+++ b/src/mame/drivers/m92.c
@@ -402,7 +402,7 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START( sound_map, AS_PROGRAM, 16, m92_state )
AM_RANGE(0x00000, 0x1ffff) AM_ROM
AM_RANGE(0xa0000, 0xa3fff) AM_RAM
- AM_RANGE(0xa8000, 0xa803f) AM_DEVREADWRITE8_LEGACY("irem", irem_ga20_r, irem_ga20_w, 0x00ff)
+ AM_RANGE(0xa8000, 0xa803f) AM_DEVREADWRITE8("irem", iremga20_device, irem_ga20_r, irem_ga20_w, 0x00ff)
AM_RANGE(0xa8040, 0xa8043) AM_DEVREADWRITE8("ymsnd", ym2151_device, read, write, 0x00ff)
AM_RANGE(0xa8044, 0xa8045) AM_READWRITE(m92_soundlatch_r, m92_sound_irq_ack_w)
AM_RANGE(0xa8046, 0xa8047) AM_WRITE(m92_sound_status_w)
@@ -953,7 +953,7 @@ static MACHINE_CONFIG_START( m92, m92_state )
MCFG_SOUND_ROUTE(0, "mono", 0.40)
MCFG_SOUND_ROUTE(1, "mono", 0.40)
- MCFG_SOUND_ADD("irem", IREMGA20, XTAL_14_31818MHz/4)
+ MCFG_IREMGA20_ADD("irem", XTAL_14_31818MHz/4)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0)
MACHINE_CONFIG_END
diff --git a/src/mame/drivers/nemesis.c b/src/mame/drivers/nemesis.c
index c2d92fe09bd..8a3ff560aa1 100644
--- a/src/mame/drivers/nemesis.c
+++ b/src/mame/drivers/nemesis.c
@@ -392,11 +392,11 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START( sound_map, AS_PROGRAM, 8, nemesis_state )
AM_RANGE(0x0000, 0x3fff) AM_ROM
AM_RANGE(0x4000, 0x47ff) AM_RAM
- AM_RANGE(0xa000, 0xafff) AM_DEVWRITE_LEGACY("k007232", k005289_pitch_A_w)
- AM_RANGE(0xc000, 0xcfff) AM_DEVWRITE_LEGACY("k007232", k005289_pitch_B_w)
+ AM_RANGE(0xa000, 0xafff) AM_DEVWRITE("k007232", k005289_device, k005289_pitch_A_w)
+ AM_RANGE(0xc000, 0xcfff) AM_DEVWRITE("k007232", k005289_device, k005289_pitch_B_w)
AM_RANGE(0xe001, 0xe001) AM_READ(soundlatch_byte_r)
- AM_RANGE(0xe003, 0xe003) AM_DEVWRITE_LEGACY("k007232", k005289_keylatch_A_w)
- AM_RANGE(0xe004, 0xe004) AM_DEVWRITE_LEGACY("k007232", k005289_keylatch_B_w)
+ AM_RANGE(0xe003, 0xe003) AM_DEVWRITE("k007232", k005289_device, k005289_keylatch_A_w)
+ AM_RANGE(0xe004, 0xe004) AM_DEVWRITE("k007232", k005289_device, k005289_keylatch_B_w)
AM_RANGE(0xe005, 0xe005) AM_DEVWRITE_LEGACY("ay2", ay8910_address_w)
AM_RANGE(0xe006, 0xe006) AM_DEVWRITE_LEGACY("ay1", ay8910_address_w)
AM_RANGE(0xe086, 0xe086) AM_DEVREAD_LEGACY("ay1", ay8910_r)
@@ -408,12 +408,12 @@ ADDRESS_MAP_END
static ADDRESS_MAP_START( gx400_sound_map, AS_PROGRAM, 8, nemesis_state )
AM_RANGE(0x0000, 0x1fff) AM_ROM
AM_RANGE(0x4000, 0x87ff) AM_RAM AM_SHARE("gx400_shared")
- AM_RANGE(0xa000, 0xafff) AM_DEVWRITE_LEGACY("k007232", k005289_pitch_A_w)
- AM_RANGE(0xc000, 0xcfff) AM_DEVWRITE_LEGACY("k007232", k005289_pitch_B_w)
+ AM_RANGE(0xa000, 0xafff) AM_DEVWRITE("k007232", k005289_device, k005289_pitch_A_w)
+ AM_RANGE(0xc000, 0xcfff) AM_DEVWRITE("k007232", k005289_device, k005289_pitch_B_w)
AM_RANGE(0xe000, 0xe000) AM_DEVWRITE_LEGACY("vlm", vlm5030_data_w)
AM_RANGE(0xe001, 0xe001) AM_READ(soundlatch_byte_r)
- AM_RANGE(0xe003, 0xe003) AM_DEVWRITE_LEGACY("k007232", k005289_keylatch_A_w)
- AM_RANGE(0xe004, 0xe004) AM_DEVWRITE_LEGACY("k007232", k005289_keylatch_B_w)
+ AM_RANGE(0xe003, 0xe003) AM_DEVWRITE("k007232", k005289_device, k005289_keylatch_A_w)
+ AM_RANGE(0xe004, 0xe004) AM_DEVWRITE("k007232", k005289_device, k005289_keylatch_B_w)
AM_RANGE(0xe005, 0xe005) AM_DEVWRITE_LEGACY("ay2", ay8910_address_w)
AM_RANGE(0xe006, 0xe006) AM_DEVWRITE_LEGACY("ay1", ay8910_address_w)
AM_RANGE(0xe030, 0xe030) AM_WRITE(gx400_speech_start_w)
@@ -1476,8 +1476,8 @@ static const ay8910_interface ay8910_interface_2 =
AY8910_DEFAULT_LOADS,
DEVCB_NULL,
DEVCB_NULL,
- DEVCB_DEVICE_HANDLER("k007232", k005289_control_A_w),
- DEVCB_DEVICE_HANDLER("k007232", k005289_control_B_w)
+ DEVCB_DEVICE_MEMBER("k007232", k005289_device, k005289_control_A_w),
+ DEVCB_DEVICE_MEMBER("k007232", k005289_device, k005289_control_B_w)
};
static void sound_irq(device_t *device, int state)
@@ -1574,7 +1574,7 @@ static MACHINE_CONFIG_START( nemesis, nemesis_state )
MCFG_SOUND_CONFIG(ay8910_interface_2) /* fixed */
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.00) /* verified with OST */
- MCFG_SOUND_ADD("k007232", K005289, 3579545/2)
+ MCFG_K005289_ADD("k007232", 3579545/2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.35) /* verified with OST */
MCFG_SOUND_ADD("vlm", VLM5030, 3579545)
@@ -1617,7 +1617,7 @@ static MACHINE_CONFIG_START( gx400, nemesis_state )
MCFG_SOUND_CONFIG(ay8910_interface_2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.00) /* verified with OST */
- MCFG_SOUND_ADD("k007232", K005289, 3579545/2)
+ MCFG_K005289_ADD("k007232", 3579545/2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.35) /* verified with OST */
MCFG_SOUND_ADD("vlm", VLM5030, 3579545)
@@ -1659,7 +1659,7 @@ static MACHINE_CONFIG_START( konamigt, nemesis_state )
MCFG_SOUND_CONFIG(ay8910_interface_2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.80)
- MCFG_SOUND_ADD("k007232", K005289, 3579545/2)
+ MCFG_K005289_ADD("k007232", 3579545/2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.60)
MACHINE_CONFIG_END
@@ -1699,7 +1699,7 @@ static MACHINE_CONFIG_START( rf2_gx400, nemesis_state )
MCFG_SOUND_CONFIG(ay8910_interface_2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.80)
- MCFG_SOUND_ADD("k007232", K005289, 3579545/2)
+ MCFG_K005289_ADD("k007232", 3579545/2)
MCFG_SOUND_ROUTE(ALL_OUTPUTS, "mono", 0.60)
MCFG_SOUND_ADD("vlm", VLM5030, 3579545)