From bb4a4dfa8dfbb17f827ce16a432ad4b68c76759c Mon Sep 17 00:00:00 2001 From: Couriersud Date: Fri, 14 Aug 2009 21:33:55 +0000 Subject: [PATCH] Galaxian sound updates - Moon Cresta and Galaxian now have their respective schematics emulated, i.e. Moon Cresta has a slightly different mixing stage. - Cleaned up driver, added some section titles and comments, removed old code. --- src/mame/audio/galaxian.c | 682 +++++------------------------------ src/mame/drivers/galaxian.c | 5 +- src/mame/includes/galaxian.h | 20 +- 3 files changed, 99 insertions(+), 608 deletions(-) diff --git a/src/mame/audio/galaxian.c b/src/mame/audio/galaxian.c index a7aa3295708..140dd7467c4 100644 --- a/src/mame/audio/galaxian.c +++ b/src/mame/audio/galaxian.c @@ -1,582 +1,34 @@ +/*************************************************************************** + + Galaxian-derived sound hardware + +**************************************************************************** + +Notes: +----- + +- There is currently no way to exactly reproduce the CD4066 switch control + mixing. This is changing impedance of the input resistor for e.g. + following filters to >> 10M Ohm. These resistors are static values in + the discrete core. + + +TODO: +---- + +- Check more schematics for differences. + +***************************************************************************/ #include "driver.h" #include "streams.h" #include "includes/galaxian.h" -#if !GALAXIAN_USE_DISCRETE -#include "sound/samples.h" - -#define VERBOSE 0 - -#define NEW_LFO 1 - -#define XTAL 18432000 - -#define SOUND_CLOCK (XTAL/6/2) /* 1.536 MHz */ - -#define RNG_RATE (XTAL/3) /* RNG clock is XTAL/3 */ -#define NOISE_RATE (XTAL/3/192/2/2) /* 2V = 8kHz */ -#define NOISE_LENGTH (NOISE_RATE*4) /* four seconds of noise */ - -#define SHOOT_RATE 2672 -#define SHOOT_LENGTH 13000 - -#define TOOTHSAW_LENGTH 16 -#define TOOTHSAW_VOLUME 0.36f -#define STEPS 16 -#define LFO_VOLUME 0.06f -#define SHOOT_VOLUME 0.50f -#define NOISE_VOLUME 0.50f -#define NOISE_AMPLITUDE (70*256) -#define TOOTHSAW_AMPLITUDE (64*256) - -/* see comments in galaxian_sh_update() */ -#define MINFREQ (139-139/3) -#define MAXFREQ (139+139/3) - -#define LOG(x) do { if (VERBOSE) logerror x; } while (0) - -static emu_timer *lfotimer = NULL; -static INT32 freq; - -#define STEP 1 - -static INT32 noise_enable; -static INT32 noisevolume; -static INT16 *noisewave; -static INT16 *shootwave; -static INT32 shoot_length; -static INT32 shoot_rate; - -static UINT8 last_port2=0; - -static INT16 tonewave[4][TOOTHSAW_LENGTH]; -static INT32 pitch,vol; - -static INT32 counter, countdown; -static INT32 lfobit[4]; - -static const INT16 backgroundwave[32] = -{ - 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, - 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, 0x4000, - -0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000, - -0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000,-0x4000, -}; - -#define CHANNEL_NOISE 0 -#define CHANNEL_SHOOT 1 -#define CHANNEL_LFO 2 -static sound_stream * tone_stream; -static emu_timer *noisetimer; - -static TIMER_CALLBACK( lfo_timer_cb ); -static TIMER_CALLBACK( galaxian_sh_update ); - -static STREAM_UPDATE( tone_update ) -{ - stream_sample_t *buffer = outputs[0]; - int i,j; - INT16 *w = tonewave[vol]; - - /* only update if we have non-zero volume and frequency */ - if( pitch != 0xff ) - { - for (i = 0; i < samples; i++) - { - int mix = 0; - - for (j = 0;j < STEPS;j++) - { - if (countdown >= 256) - { - counter = (counter + 1) % TOOTHSAW_LENGTH; - countdown = pitch; - } - countdown++; - - mix += w[counter]; - } - *buffer++ = mix / STEPS; - } - } - else - { - for( i = 0; i < samples; i++ ) - *buffer++ = 0; - } -} - -WRITE8_DEVICE_HANDLER( galaxian_sound_w ) -{ - data &= 0x01; - switch (offset & 7) - { - case 0: /* FS1 (controls 555 timer at 8R) */ - case 1: /* FS2 (controls 555 timer at 8S) */ - case 2: /* FS3 (controls 555 timer at 8T) */ - galaxian_background_enable_w(device, offset, data); - break; - - case 3: /* HIT */ - galaxian_noise_enable_w(device, 0, data); - break; - - case 4: /* n/c */ - break; - - case 5: /* FIRE */ - galaxian_shoot_enable_w(device, 0, data); - break; - - case 6: /* VOL1 */ - case 7: /* VOL2 */ - galaxian_vol_w(device, offset & 1, data); - break; - } -} - - -WRITE8_DEVICE_HANDLER( galaxian_pitch_w ) -{ - stream_update(tone_stream); - - pitch = data; -} - -WRITE8_DEVICE_HANDLER( galaxian_vol_w ) -{ - stream_update(tone_stream); - - /* offset 0 = bit 0, offset 1 = bit 1 */ - vol = (vol & ~(1 << offset)) | ((data & 1) << offset); -} - - -static TIMER_CALLBACK( noise_timer_cb ) -{ - if( !noise_enable && noisevolume > 0 ) - { - const device_config *samples = devtag_get_device(machine, GAL_AUDIO); - noisevolume -= (noisevolume / 10) + 1; - sample_set_volume(samples, CHANNEL_NOISE,noisevolume / 100.0); - } -} - -WRITE8_DEVICE_HANDLER( galaxian_noise_enable_w ) -{ - noise_enable = data & 1; - - if( noise_enable ) - { - noisevolume = 100; - sample_set_volume(device, CHANNEL_NOISE,noisevolume / 100.0); - } -} - -WRITE8_DEVICE_HANDLER( galaxian_shoot_enable_w ) -{ - if( data & 1 && !(last_port2 & 1) ) - { - sample_start_raw(device, CHANNEL_SHOOT, shootwave, shoot_length, shoot_rate, 0); - sample_set_volume(device, CHANNEL_SHOOT,SHOOT_VOLUME); - } - last_port2=data; -} - - -static SAMPLES_START( galaxian_sh_start ) -{ - running_machine *machine = device->machine; - int i, j, sweep, charge, countdown, generator, bit1, bit2; - - freq = MAXFREQ; - - sample_set_volume(device, CHANNEL_NOISE, NOISE_VOLUME); - sample_set_volume(device, CHANNEL_SHOOT, SHOOT_VOLUME); - sample_set_volume(device, CHANNEL_LFO+0, LFO_VOLUME); - sample_set_volume(device, CHANNEL_LFO+1, LFO_VOLUME); - sample_set_volume(device, CHANNEL_LFO+2, LFO_VOLUME); - - noisewave = auto_alloc_array(machine, INT16, NOISE_LENGTH); - -#define SHOOT_SEC 2 - shoot_rate = machine->sample_rate; - shoot_length = SHOOT_SEC * shoot_rate; - shootwave = auto_alloc_array(machine, INT16, shoot_length); - - /* - * The RNG shifter is clocked with RNG_RATE, bit 17 is - * latched every 2V cycles (every 2nd scanline). - * This signal is used as a noise source. - */ - generator = 0; - countdown = NOISE_RATE / 2; - for( i = 0; i < NOISE_LENGTH; i++ ) - { - countdown -= RNG_RATE; - while( countdown < 0 ) - { - generator <<= 1; - bit1 = (~generator >> 17) & 1; - bit2 = (generator >> 5) & 1; - if (bit1 ^ bit2) generator |= 1; - countdown += NOISE_RATE; - } - noisewave[i] = ((generator >> 17) & 1) ? NOISE_AMPLITUDE : -NOISE_AMPLITUDE; - } - - /* dummy */ - sweep = 100; - charge = +2; - j=0; - { -#define R41__ 100000 -#define R44__ 10000 -#define R45__ 22000 -#define R46__ 10000 -#define R47__ 2200 -#define R48__ 2200 -#define C25__ 0.000001 -#define C27__ 0.00000001 -#define C28__ 0.000047 -#define C29__ 0.00000001 -#define IC8L3_L 0.2 /* 7400 L level */ -#define IC8L3_H 4.5 /* 7400 H level */ -#define NOISE_L 0.2 /* 7474 L level */ -#define NOISE_H 4.5 /* 7474 H level */ -/* - key on/off time is programmable - Therefore, it is necessary to make separate sample with key on/off. - And, calculate the playback point according to the voltage of c28. -*/ -#define SHOOT_KEYON_TIME 0.1 /* second */ -/* - NE555-FM input calculation is wrong. - The frequency is not proportional to the voltage of FM input. - And, duty will be changed,too. -*/ -#define NE555_FM_ADJUST_RATE 0.80 - /* discharge : 100K * 1uF */ - double v = 5.0; - double vK = (shoot_rate) ? exp(-1 / (R41__*C25__) / shoot_rate) : 0; - /* -- SHOOT KEY port -- */ - double IC8L3 = IC8L3_L; /* key on */ - int IC8Lcnt = SHOOT_KEYON_TIME * shoot_rate; /* count for key off */ - /* C28 : KEY port capacity */ - /* connection : 8L-3 - R47(2.2K) - C28(47u) - R48(2.2K) - C29 */ - double c28v = IC8L3_H - (IC8L3_H-(NOISE_H+NOISE_L)/2)/(R46__+R47__+R48__)*R47__; - double c28K = (shoot_rate) ? exp(-1 / (22000 * 0.000047 ) / shoot_rate) : 0; - /* C29 : NOISE capacity */ - /* connection : NOISE - R46(10K) - C29(0.1u) - R48(2.2K) - C28 */ - double c29v = IC8L3_H - (IC8L3_H-(NOISE_H+NOISE_L)/2)/(R46__+R47__+R48__)*(R47__+R48__); - double c29K1 = (shoot_rate) ? exp(-1 / (22000 * 0.00000001 ) / shoot_rate) : 0; /* form C28 */ - double c29K2 = (shoot_rate) ? exp(-1 / (100000 * 0.00000001 ) / shoot_rate) : 0; /* from noise */ - /* NE555 timer */ - /* RA = 10K , RB = 22K , C=.01u ,FM = C29 */ - double ne555cnt = 0; - double ne555step = (shoot_rate) ? ((1.44/((R44__+R45__*2)*C27__)) / shoot_rate) : 0; - double ne555duty = (double)(R44__+R45__)/(R44__+R45__*2); /* t1 duty */ - double ne555sr; /* threshold (FM) rate */ - /* NOISE source */ - double ncnt = 0.0; - double nstep = (shoot_rate) ? ((double)NOISE_RATE / shoot_rate) : 0; - double noise_sh2; /* voltage level */ - - for( i = 0; i < shoot_length; i++ ) - { - /* noise port */ - noise_sh2 = noisewave[(int)ncnt % NOISE_LENGTH] == NOISE_AMPLITUDE ? NOISE_H : NOISE_L; - ncnt+=nstep; - /* calculate NE555 threshold level by FM input */ - ne555sr = c29v*NE555_FM_ADJUST_RATE / (5.0*2/3); - /* calc output */ - ne555cnt += ne555step; - if( ne555cnt >= ne555sr) ne555cnt -= ne555sr; - if( ne555cnt < ne555sr*ne555duty ) - { - /* t1 time */ - shootwave[i] = v/5*0x7fff; - /* discharge output level */ - if(IC8L3==IC8L3_H) - v *= vK; - } - else - shootwave[i] = 0; - /* C28 charge/discharge */ - c28v += (IC8L3-c28v) - (IC8L3-c28v)*c28K; /* from R47 */ - c28v += (c29v-c28v) - (c29v-c28v)*c28K; /* from R48 */ - /* C29 charge/discharge */ - c29v += (c28v-c29v) - (c28v-c29v)*c29K1; /* from R48 */ - c29v += (noise_sh2-c29v) - (noise_sh2-c29v)*c29K2; /* from R46 */ - /* key off */ - if(IC8L3==IC8L3_L && --IC8Lcnt==0) - IC8L3=IC8L3_H; - } - } - - memset(tonewave, 0, sizeof(tonewave)); - - for( i = 0; i < TOOTHSAW_LENGTH; i++ ) - { - #define V(r0,r1) 2*TOOTHSAW_AMPLITUDE*(r0)/(r0+r1)-TOOTHSAW_AMPLITUDE - double r0a = 1.0/1e12, r1a = 1.0/1e12; - double r0b = 1.0/1e12, r1b = 1.0/1e12; - - /* #0: VOL1=0 and VOL2=0 - * only the 33k and the 22k resistors R51 and R50 - */ - if( i & 1 ) - { - r1a += 1.0/33000; - r1b += 1.0/33000; - } - else - { - r0a += 1.0/33000; - r0b += 1.0/33000; - } - if( i & 4 ) - { - r1a += 1.0/22000; - r1b += 1.0/22000; - } - else - { - r0a += 1.0/22000; - r0b += 1.0/22000; - } - tonewave[0][i] = V(1.0/r0a, 1.0/r1a); - - /* #1: VOL1=1 and VOL2=0 - * add the 10k resistor R49 for bit QC - */ - if( i & 4 ) - r1a += 1.0/10000; - else - r0a += 1.0/10000; - tonewave[1][i] = V(1.0/r0a, 1.0/r1a); - - /* #2: VOL1=0 and VOL2=1 - * add the 15k resistor R52 for bit QD - */ - if( i & 8 ) - r1b += 1.0/15000; - else - r0b += 1.0/15000; - tonewave[2][i] = V(1.0/r0b, 1.0/r1b); - - /* #3: VOL1=1 and VOL2=1 - * add the 10k resistor R49 for QC - */ - if( i & 4 ) - r0b += 1.0/10000; - else - r1b += 1.0/10000; - tonewave[3][i] = V(1.0/r0b, 1.0/r1b); - LOG(("tone[%2d]: $%02x $%02x $%02x $%02x\n", i, tonewave[0][i], tonewave[1][i], tonewave[2][i], tonewave[3][i])); - } - - pitch = 0xff; - vol = 0; - - tone_stream = stream_create(device,0,1,SOUND_CLOCK/STEPS,NULL,tone_update); - stream_set_output_gain(tone_stream, 0, TOOTHSAW_VOLUME); - - sample_set_volume(device, CHANNEL_NOISE,0); - sample_start_raw(device, CHANNEL_NOISE,noisewave,NOISE_LENGTH,NOISE_RATE,1); - - sample_set_volume(device, CHANNEL_SHOOT,0); - sample_start_raw(device, CHANNEL_SHOOT,shootwave,SHOOT_LENGTH,SHOOT_RATE,1); - - sample_set_volume(device, CHANNEL_LFO+0,0); - sample_start_raw(device, CHANNEL_LFO+0,backgroundwave,ARRAY_LENGTH(backgroundwave),1000,1); - sample_set_volume(device, CHANNEL_LFO+1,0); - sample_start_raw(device, CHANNEL_LFO+1,backgroundwave,ARRAY_LENGTH(backgroundwave),1000,1); - sample_set_volume(device, CHANNEL_LFO+2,0); - sample_start_raw(device, CHANNEL_LFO+2,backgroundwave,ARRAY_LENGTH(backgroundwave),1000,1); - - noisetimer = timer_alloc(machine, noise_timer_cb, NULL); - timer_adjust_periodic(noisetimer, ATTOTIME_IN_NSEC((155000+22000)/100*693*22), 0, ATTOTIME_IN_NSEC((155000+22000)/100*693*22)); - - lfotimer = timer_alloc(machine, lfo_timer_cb, NULL); - - timer_pulse(machine, video_screen_get_frame_period(machine->primary_screen), NULL, 0, galaxian_sh_update); - - state_save_register_global(machine, freq); - state_save_register_global(machine, noise_enable); - state_save_register_global(machine, noisevolume); - state_save_register_global(machine, last_port2); - state_save_register_global(machine, pitch); - state_save_register_global(machine, vol); - state_save_register_global(machine, counter); - state_save_register_global(machine, countdown); - state_save_register_global_array(machine, lfobit); -} - - - -WRITE8_DEVICE_HANDLER( galaxian_background_enable_w ) -{ - sample_set_volume(device, CHANNEL_LFO+offset,(data & 1) ? LFO_VOLUME : 0); -} - -static TIMER_CALLBACK( lfo_timer_cb ) -{ - if( freq > MINFREQ ) - freq--; - else - freq = MAXFREQ; -} - -WRITE8_DEVICE_HANDLER( galaxian_lfo_freq_w ) -{ -#if NEW_LFO - /* R18 1M,R17 470K,R16 220K,R15 100K */ - static const int rv[4] = { 1000000,470000,220000,100000}; - double r1,r2,Re,td; - int i; - - if( (data & 1) == lfobit[offset] ) - return; - - /* - * NE555 9R is setup as astable multivibrator - * - this circuit looks LINEAR RAMP V-F converter - I = 1/Re * ( R1/(R1+R2)-Vbe) - td = (2/3VCC*Re*(R1+R2)*C) / (R1*VCC-Vbe*(R1+R2)) - parts assign - R1 : (R15* L1)|(R16* L2)|(R17* L3)|(R18* L1) - R2 : (R15*~L1)|(R16*~L2)|(R17*~L3)|(R18*~L4)|R??(330K) - Re : R21(100K) - Vbe : Q2(2SA1015)-Vbe - * - R20(15K) and Q1 is unknown,maybe current booster. - */ - - lfobit[offset] = data & 1; - - /* R20 15K */ - r1 = 1e12; - /* R19? 330k to gnd */ - r2 = 330000; - //r1 = 15000; - /* R21 100K */ - Re = 100000; - /* register calculation */ - for(i=0;i<4;i++) - { - if(lfobit[i]) - r1 = (r1*rv[i])/(r1+rv[i]); /* Hi */ - else - r2 = (r2*rv[i])/(r2+rv[i]); /* Low */ - } - -#define Vcc 5.0 -#define Vbe 0.65 /* 2SA1015 */ -#define Cap 0.000001 /* C15 1uF */ - td = (Vcc*2/3*Re*(r1+r2)*Cap) / (r1*Vcc - Vbe*(r1+r2) ); -#undef Cap -#undef Vbe -#undef Vcc - LOG(("lfo timer bits:%d%d%d%d r1:%d, r2:%d, re: %d, td: %9.2fsec\n", lfobit[0], lfobit[1], lfobit[2], lfobit[3], (int)r1, (int)r2, (int)Re, td)); - timer_adjust_periodic(lfotimer, attotime_make(0, ATTOSECONDS_PER_SECOND / (MAXFREQ-MINFREQ) * td), 0, attotime_make(0, ATTOSECONDS_PER_SECOND / (MAXFREQ-MINFREQ) * td)); -#else - double r0, r1, rx = 100000.0; - - if( (data & 1) == lfobit[offset] ) - return; - - /* - * NE555 9R is setup as astable multivibrator - * - Ra is between 100k and ??? (open?) - * - Rb is zero here (bridge between pins 6 and 7) - * - C is 1uF - * charge time t1 = 0.693 * (Ra + Rb) * C - * discharge time t2 = 0.693 * (Rb) * C - * period T = t1 + t2 = 0.693 * (Ra + 2 * Rb) * C - * -> min period: 0.693 * 100 kOhm * 1uF -> 69300 us = 14.4Hz - * -> max period: no idea, since I don't know the max. value for Ra :( - */ - - lfobit[offset] = data & 1; - - /* R?? 330k to gnd */ - r0 = 1.0/330000; - /* open is a very high value really ;-) */ - r1 = 1.0/1e12; - - /* R18 1M */ - if( lfobit[0] ) - r1 += 1.0/1000000; - else - r0 += 1.0/1000000; - - /* R17 470k */ - if( lfobit[1] ) - r1 += 1.0/470000; - else - r0 += 1.0/470000; - - /* R16 220k */ - if( lfobit[2] ) - r1 += 1.0/220000; - else - r0 += 1.0/220000; - - /* R15 100k */ - if( lfobit[3] ) - r1 += 1.0/100000; - else - r0 += 1.0/100000; - - r0 = 1.0/r0; - r1 = 1.0/r1; - - /* I used an arbitrary value for max. Ra of 2M */ - rx = rx + 2000000.0 * r0 / (r0+r1); - - LOG(("lfotimer bits:%d%d%d%d r0:%d, r1:%d, rx: %d, time: %9.2fus\n", lfobit[3], lfobit[2], lfobit[1], lfobit[0], (int)r0, (int)r1, (int)rx, 0.639 * rx)); - timer_adjust_periodic(lfotimer, attotime_make(0, ATTOSECONDS_PER_SECOND / 1000000000 / (MAXFREQ-MINFREQ) * 639 * rx), 0, attotime_make(0, ATTOSECONDS_PER_SECOND / 1000000000 / (MAXFREQ-MINFREQ) * 639 * rx)); -#endif -} - -static TIMER_CALLBACK( galaxian_sh_update ) -{ - const device_config *samples = devtag_get_device(machine, GAL_AUDIO); - - /* - * NE555 8R, 8S and 8T are used as pulse position modulators - * FS1 Ra=100k, Rb=470k and C=0.01uF - * -> 0.693 * 1040k * 0.01uF -> 7207.2us = 139Hz - * FS2 Ra=100k, Rb=330k and C=0.01uF - * -> 0.693 * 760k * 0.01uF -> 5266.8us = 190Hz - * FS2 Ra=100k, Rb=220k and C=0.01uF - * -> 0.693 * 540k * 0.01uF -> 3742.2us = 267Hz - */ - - sample_set_freq(samples, CHANNEL_LFO+0, sizeof(backgroundwave)*freq*(100+2*470)/(100+2*470) ); - sample_set_freq(samples, CHANNEL_LFO+1, sizeof(backgroundwave)*freq*(100+2*330)/(100+2*470) ); - sample_set_freq(samples, CHANNEL_LFO+2, sizeof(backgroundwave)*freq*(100+2*220)/(100+2*470) ); -} - - -static const samples_interface galaxian_custom_interface = -{ - 5, - NULL, - galaxian_sh_start -}; - -MACHINE_DRIVER_START( galaxian_audio ) - - /* sound hardware */ - - MDRV_SOUND_ADD(GAL_AUDIO, SAMPLES, 0) - MDRV_SOUND_CONFIG(galaxian_custom_interface) - MDRV_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0) -MACHINE_DRIVER_END - -#else +/************************************* + * + * Defines + * + *************************************/ #define XTAL 18432000 @@ -626,11 +78,9 @@ MACHINE_DRIVER_END * R34 is given twice on galaxian board and both times as 5.1k. On moon cresta * it is only listed once and given as 15k. This is more in line with recordings */ -#if HARDWARE == HARDWARE_GALAXIAN -#define GAL_R34 RES_K(5.1) /* val from mcresta galaxian : RES_K(5.1) */ -#else -#define GAL_R34 RES_K(15) /* val from mcresta galaxian : RES_K(5.1) */ -#endif +#define GAL_R34 RES_K(5.1) +#define MCRST_R34 RES_K(15) + #define GAL_R35 RES_K(150) #define GAL_R36 RES_K(22) #define GAL_R37 RES_K(470) @@ -673,6 +123,11 @@ MACHINE_DRIVER_END #define GAL_C46 CAP_U(0.1) +/************************************* + * + * Structures for discrete core + * + *************************************/ static const discrete_dac_r1_ladder galaxian_bck_dac = @@ -736,7 +191,6 @@ static const discrete_lfsr_desc galaxian_lfsr = 0 /* Output bit */ }; -#if HARDWARE == HARDWARE_GALAXIAN static const discrete_mixer_desc galaxian_mixerpre_desc = { DISC_MIXER_IS_RESISTOR, @@ -748,6 +202,7 @@ static const discrete_mixer_desc galaxian_mixerpre_desc = 0, 0, 1 }; + static const discrete_mixer_desc galaxian_mixer_desc = { DISC_MIXER_IS_RESISTOR, @@ -759,11 +214,13 @@ static const discrete_mixer_desc galaxian_mixer_desc = GAL_C46, 0, 1 }; -#else -static const discrete_mixer_desc galaxian_mixer_desc = + +/* moon cresta has different mixing */ + +static const discrete_mixer_desc mooncrst_mixer_desc = { DISC_MIXER_IS_RESISTOR, - {GAL_R51, 0, GAL_R50, 0, GAL_R34, GAL_R40, GAL_R43}, /* A, C, C, D */ + {GAL_R51, 0, GAL_R50, 0, MCRST_R34, GAL_R40, GAL_R43}, /* A, C, C, D */ {0, GAL_INP_VOL1, 0, GAL_INP_VOL2, 0, 0, 0}, {0,0,0,0,0,0,GAL_C26}, 0, 0*GAL_R91, @@ -771,7 +228,7 @@ static const discrete_mixer_desc galaxian_mixer_desc = GAL_C46, 0, 1 }; -#endif + static const discrete_op_amp_filt_info galaxian_bandpass_desc = { GAL_R35, GAL_R36, 0, 0, @@ -781,6 +238,13 @@ static const discrete_op_amp_filt_info galaxian_bandpass_desc = 5, 0 }; +/************************************* + * + * Discrete Sound Blocks + * + *************************************/ + + static DISCRETE_SOUND_START(galaxian) /************************************************/ @@ -875,21 +339,41 @@ static DISCRETE_SOUND_START(galaxian) /* FINAL MIX */ /************************************************/ -#if HARDWARE == HARDWARE_GALAXIAN DISCRETE_MIXER5(NODE_279, 1, NODE_133, NODE_134, NODE_134, NODE_135, NODE_120, &galaxian_mixerpre_desc) DISCRETE_MIXER3(NODE_280, 1, NODE_279, NODE_157, NODE_172, &galaxian_mixer_desc) -#else - DISCRETE_MIXER7(NODE_280, 1, NODE_133, NODE_134, NODE_134, NODE_135, NODE_120, NODE_157, NODE_172, &galaxian_mixer_desc) -#endif DISCRETE_OUTPUT(NODE_280, 32767.0/5.0*5) DISCRETE_SOUND_END + +static DISCRETE_SOUND_START(mooncrst) + DISCRETE_IMPORT(galaxian) + + /************************************************/ + /* Moon Cresta mixing stage */ + /************************************************/ + DISCRETE_DELETE(NODE_279, NODE_279) + DISCRETE_REPLACE + DISCRETE_MIXER7(NODE_280, 1, NODE_133, NODE_134, NODE_134, NODE_135, NODE_120, NODE_157, NODE_172, &mooncrst_mixer_desc) +DISCRETE_SOUND_END + +/************************************* + * + * Static Variables + * + *************************************/ + static UINT8 lfo_val; static emu_timer *pitch_timer; static UINT8 pitch_l; static UINT8 pitch_h; +/************************************* + * + * Callbacks + * + *************************************/ + static TIMER_CALLBACK( pitch_callback ) { const device_config *device = devtag_get_device(machine, GAL_AUDIO); @@ -915,6 +399,12 @@ static SOUND_START(galaxian) timer_adjust_oneshot(pitch_timer, ATTOTIME_IN_HZ(SOUND_CLOCK/256), 0); } +/************************************* + * + * Write handlers + * + *************************************/ + /* IC 9J */ WRITE8_DEVICE_HANDLER( galaxian_pitch_w ) { @@ -988,6 +478,12 @@ WRITE8_DEVICE_HANDLER( galaxian_sound_w ) } } +/************************************* + * + * Driver definitions + * + *************************************/ + MACHINE_DRIVER_START( galaxian_audio ) MDRV_SOUND_START(galaxian) @@ -998,4 +494,12 @@ MACHINE_DRIVER_START( galaxian_audio ) MDRV_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0) MACHINE_DRIVER_END -#endif +MACHINE_DRIVER_START( mooncrst_audio ) + + MDRV_SOUND_START(galaxian) + + MDRV_SOUND_ADD(GAL_AUDIO, DISCRETE, 0) + MDRV_SOUND_CONFIG_DISCRETE(mooncrst) + + MDRV_SOUND_ROUTE(ALL_OUTPUTS, "mono", 1.0) +MACHINE_DRIVER_END diff --git a/src/mame/drivers/galaxian.c b/src/mame/drivers/galaxian.c index 7387776284f..9bb1dd161dc 100644 --- a/src/mame/drivers/galaxian.c +++ b/src/mame/drivers/galaxian.c @@ -1853,11 +1853,14 @@ MACHINE_DRIVER_END static MACHINE_DRIVER_START( mooncrst ) - MDRV_IMPORT_FROM(galaxian) + + MDRV_IMPORT_FROM(galaxian_base) /* alternate memory map */ MDRV_CPU_MODIFY("maincpu") MDRV_CPU_PROGRAM_MAP(mooncrst_map) + + MDRV_IMPORT_FROM(mooncrst_audio) MACHINE_DRIVER_END diff --git a/src/mame/includes/galaxian.h b/src/mame/includes/galaxian.h index 22cd937b4b4..779498e26eb 100644 --- a/src/mame/includes/galaxian.h +++ b/src/mame/includes/galaxian.h @@ -4,19 +4,7 @@ ***************************************************************************/ -#define GALAXIAN_USE_DISCRETE (1) - -#define HARDWARE_GALAXIAN 1 -#define HARDWARE_MCRESTA 2 - -#define HARDWARE HARDWARE_GALAXIAN - -#if GALAXIAN_USE_DISCRETE #include "sound/discrete.h" -#else -#include "sound/samples.h" -#endif - /* we scale horizontally by 3 to render stars correctly */ #define GALAXIAN_XSCALE 3 @@ -38,6 +26,7 @@ #define GALAXIAN_VBEND (16) #define GALAXIAN_VBSTART (224+16) +#define GAL_AUDIO "discrete" /*----------- defined in video/galaxian.c -----------*/ @@ -136,12 +125,7 @@ void jumpbug_extend_sprite_info(const UINT8 *base, UINT8 *sx, UINT8 *sy, UINT8 * /*----------- defined in audio/galaxian.c -----------*/ -#if GALAXIAN_USE_DISCRETE -#define GAL_AUDIO "discrete" -#else -#define GAL_AUDIO "samples" -#endif - +MACHINE_DRIVER_EXTERN( mooncrst_audio ); MACHINE_DRIVER_EXTERN( galaxian_audio ); WRITE8_DEVICE_HANDLER( galaxian_sound_w );