diff options
author | 2020-10-22 00:46:30 -0400 | |
---|---|---|
committer | 2020-10-22 00:46:58 -0400 | |
commit | 0e466c241bb91696d98bd46889cf606a07899b8c (patch) | |
tree | 294baf58149cf2a3c221b5f58a1bc987111ec138 | |
parent | 433eb54a0a7cc0c3f445cd30822684e302da1999 (diff) |
Add DAC filtering to Midway "Sounds Good" hardware, and add notes/mirroring regarding the undumped memory mapper PAL. [Lord Nightmare]
-rw-r--r-- | src/devices/sound/flt_biquad.cpp | 26 | ||||
-rw-r--r-- | src/mame/audio/midway.cpp | 56 | ||||
-rw-r--r-- | src/mame/audio/midway.h | 6 |
3 files changed, 68 insertions, 20 deletions
diff --git a/src/devices/sound/flt_biquad.cpp b/src/devices/sound/flt_biquad.cpp index a0416bfafb1..c625b28c6df 100644 --- a/src/devices/sound/flt_biquad.cpp +++ b/src/devices/sound/flt_biquad.cpp @@ -143,6 +143,11 @@ filter_biquad_device& filter_biquad_device::opamp_sk_lowpass_setup(double r1, do * NOTE: vRef is not definable when setting up the filter. * If the analog effects caused by vRef are important to the operation of the specific filter * in question, a netlist implementation may work better under those circumstances. + * NOTE2: a variant of this circuit has the c1 capacitor left off. if so, set c1 to 0 + * which will form a controllable gain 1st order version of the circuit. + * NOTE3: There is a well known 'proper' 1st order version of this circuit where r2 is + * a dead short, and c1 is also ommitted as in NOTE2. Set both r2 to 0 and c1 to 0 to + * emulate a circuit of this type. * * .--------+---------. * | | | @@ -160,14 +165,13 @@ filter_biquad_device& filter_biquad_device::opamp_sk_lowpass_setup(double r1, do */ filter_biquad_device& filter_biquad_device::opamp_mfb_lowpass_setup(double r1, double r2, double r3, double c1, double c2) { - if ((r1 == 0) || (r2 == 0) || (r3 == 0) || (c2 == 0)) + if ((r1 == 0) || ((r2 == 0) && (c1 != 0)) || (r3 == 0) || (c2 == 0)) { - fatalerror("filter_biquad_device::opamp_mfb_lowpass_setup() - only c1 can be 0; parameters were: r1: %f, r2: %f, r3: %f, c1: %f, c2: %f", r1, r2, r3, c1, c2); /* Filter can not be setup. Undefined results. */ + fatalerror("filter_biquad_device::opamp_mfb_lowpass_setup() - only c1 can be 0 (and if c1 is 0, r2 can also be 0); parameters were: r1: %f, r2: %f, r3: %f, c1: %f, c2: %f", r1, r2, r3, c1, c2); /* Filter can not be setup. Undefined results. */ } - double const gain = -r3 / r1; double fc, q = (M_SQRT2 / 2.0); - if (c1 == 0) // set C1 to 0 to run this filter in a degraded single pole mode where C1 was left off the filter entirely. Certain Williams boards seem to have omitted C1, presumably by accident. + if ((r2 != 0) && (c1 == 0)) // set C1 to 0 to run this filter in single pole mode where C1 was left off the filter entirely. Certain Williams boards seem to have omitted C1, presumably by accident. { fc = (r1 * r3) / (2 * M_PI * ((r1 * r2) + (r1 * r3) + (r2 * r3)) * r3 * c2); #ifdef FLT_BIQUAD_DEBUG_SETUP @@ -175,12 +179,20 @@ filter_biquad_device& filter_biquad_device::opamp_mfb_lowpass_setup(double r1, d #endif return setup(biquad_type::LOWPASS1P, fc, q, gain); } - else + else if ((r2 == 0) && (c1 == 0)) // proper first order case, set both C1 to 0 and R2 to 0 for the first order + { + fc = 1.0 / (2 * M_PI * r3 * c2); +#ifdef FLT_BIQUAD_DEBUG_SETUP + logerror("filter_biquad_device::opamp_mfb_lowpass_setup() in 1st order mode yields: fc = %f, Q = %f(ignored), gain = %f\n", fc, q, gain); +#endif + return setup(biquad_type::LOWPASS1P, fc, q, gain); + } + else // common case, (r2 != 0) && (c1 != 0) { fc = 1.0 / (2 * M_PI * sqrt(r2 * r3 * c1 * c2)); q = sqrt(r2 * r3 * c1 * c2) / ((r3 * c2) + (r2 * c2) + ((r2 * c2) * -gain)); #ifdef FLT_BIQUAD_DEBUG_SETUP - logerror("filter_biquad_device::opamp_mfb_lowpass_setup() yields: fc = %f, Q = %f, gain = %f\n", fc, q, gain); + logerror("filter_biquad_device::opamp_mfb_lowpass_setup() in 2nd order mode yields: fc = %f, Q = %f, gain = %f\n", fc, q, gain); #endif return setup(biquad_type::LOWPASS, fc, q, gain); } @@ -226,7 +238,7 @@ filter_biquad_device& filter_biquad_device::opamp_mfb_bandpass_setup(double r1, r_in = 1.0 / (1.0/r1 + 1.0/r2); } - double const fc = 1.0 / (2 * M_PI * sqrt(r_in * r3 * c1 * c2)); + double const fc = 1.0 / (2 * M_PI * sqrt(r_in * r3 * c1 * c2)); // technically this is the center frequency of the bandpass double const q = sqrt(r3 / r_in * c1 * c2) / (c1 + c2); gain *= -r3 / r_in * c2 / (c1 + c2); #ifdef FLT_BIQUAD_DEBUG_SETUP diff --git a/src/mame/audio/midway.cpp b/src/mame/audio/midway.cpp index 6a1b9972ff4..075a7beadc9 100644 --- a/src/mame/audio/midway.cpp +++ b/src/mame/audio/midway.cpp @@ -470,13 +470,14 @@ void midway_ssio_device::device_timer(emu_timer &timer, device_timer_id id, int //------------------------------------------------- midway_sounds_good_device::midway_sounds_good_device(const machine_config &mconfig, const char *tag, device_t *owner, uint32_t clock) - : device_t(mconfig, MIDWAY_SOUNDS_GOOD, tag, owner, clock), - device_mixer_interface(mconfig, *this), - m_cpu(*this, "cpu"), - m_pia(*this, "pia"), - m_dac(*this, "dac"), - m_status(0), - m_dacval(0) + : device_t(mconfig, MIDWAY_SOUNDS_GOOD, tag, owner, clock) + , device_mixer_interface(mconfig, *this) + , m_cpu(*this, "cpu") + , m_pia(*this, "pia") + , m_dac(*this, "dac") + , m_dac_filter(*this, "dac_filter%u", 0U) + , m_status(0) + , m_dacval(0) { } @@ -555,14 +556,36 @@ WRITE_LINE_MEMBER(midway_sounds_good_device::irq_w) // audio CPU map //------------------------------------------------- -// address map determined by PAL; not verified +// address map determined by PAL20L10 @U15; not dumped/verified yet +//Address map (x = ignored; * = selects address within this range) +//68k address map known for certain: +//a23 a22 a21 a20 a19 a18 a17 a16 a15 a14 a13 a12 a11 a10 a9 a8 a7 a6 a5 a4 a3 a2 a1 (a0 via UDS/LDS) +//x x x x x * * * ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? RW PAL@ +//BEGIN 68k map guesses (until we have a pal dump): +//x x x x x 0 [a] [b] * * * * * * * * * * * * * * * -> R ROM U7, U17 +//x x x x x 0 [c] [d] * * * * * * * * * * * * * * * -> R ROM U8, U18 +//x x x x x 1 1 0 x x x x x x x x x x x x 0 *e* *f* 1 RW PIA U9 (e goes to PIA RS0, f goes to PIA RS1, D8-D15 go to PIA D0-D7) +//x x x x x 1 1 1 x x x x * * * * * * * * * * * ? RW RAM U6, U16 +//The ROMTYPE PAL line, is pulled low if JW1 is present, and this presumably controls [a] [b] [c] [d] as such: +//When ROMTYPE is HIGH/JW1 absent, 27256 roms: (JW3 should be present, JW2 absent) +//x x x x x 0 0? 0 * * * * * * * * * * * * * * * -> R ROM U7, U17 +//x x x x x 0 0? 1 * * * * * * * * * * * * * * * -> R ROM U8, U18 +//When ROMTYPE is LOW/JW1 present, 27512 roms: (JW3 should be absent, JW2 present) +//x x x x x 0 0 * * * * * * * * * * * * * * * * -> R ROM U7, U17 +//x x x x x 0 1 * * * * * * * * * * * * * * * * -> R ROM U8, U18 +//JW2 and JW3 are mutually exclusive, and control whether 68k a16 connects to the EPROM pin 1 line (JW2 present), or whether it is tied high (JW3 present). +//EPROM pin 1 is A15 on 27512, and VPP(usually an active high enable) on 27256 +//END guesses + + + void midway_sounds_good_device::soundsgood_map(address_map &map) { map.unmap_value_high(); map.global_mask(0x7ffff); map(0x000000, 0x03ffff).rom(); - map(0x060000, 0x060007).rw("pia", FUNC(pia6821_device::read_alt), FUNC(pia6821_device::write_alt)).umask16(0xff00); - map(0x070000, 0x070fff).ram(); + map(0x060000, 0x060007).mirror(0x00fff0).rw(m_pia, FUNC(pia6821_device::read_alt), FUNC(pia6821_device::write_alt)).umask16(0xff00); // RS0 connects to A2, RS1 connects to A1, hence the "alt" functions are used. + map(0x070000, 0x070fff).mirror(0x00f000).ram(); } @@ -581,7 +604,18 @@ void midway_sounds_good_device::device_add_mconfig(machine_config &config) m_pia->irqa_handler().set(FUNC(midway_sounds_good_device::irq_w)); m_pia->irqb_handler().set(FUNC(midway_sounds_good_device::irq_w)); - AD7533(config, m_dac, 0).add_route(ALL_OUTPUTS, *this, 1.0); /// ad7533jn.u10 + AD7533(config, m_dac, 0); /// ad7533jn.u10 + + //LM359 @U2.2, 2nd order MFB low-pass (fc = 5404.717733, Q = 0.625210, gain = -1.000000) + FILTER_BIQUAD(config, m_dac_filter[2]).opamp_mfb_lowpass_setup(RES_K(150), RES_K(82), RES_K(150), CAP_P(470), CAP_P(150)); // R115, R109, R108, C112, C111 + m_dac_filter[2]->add_route(ALL_OUTPUTS, *this, 1.0); + //LM359 @U3.2, 2nd order MFB low-pass (fc = 5310.690763, Q = 1.608630, gain = -1.000000) + FILTER_BIQUAD(config, m_dac_filter[1]).opamp_mfb_lowpass_setup(RES_K(33), RES_K(18), RES_K(33), CAP_P(5600), CAP_P(270)); // R113, R117, R116, C115, C118 + m_dac_filter[1]->add_route(ALL_OUTPUTS, m_dac_filter[2], 1.0); + //LM359 @U3.1, 1st order MFB low-pass (fc = 4912.189602, Q = 0.707107(ignored), gain = -1.000000) + FILTER_BIQUAD(config, m_dac_filter[0]).opamp_mfb_lowpass_setup(RES_K(120), RES_K(0), RES_K(120), CAP_P(0), CAP_P(270)); // R112, <short>, R111, <nonexistent>, C113 + m_dac_filter[0]->add_route(ALL_OUTPUTS, m_dac_filter[1], 1.0); + m_dac->add_route(ALL_OUTPUTS, m_dac_filter[0], 1.0); } diff --git a/src/mame/audio/midway.h b/src/mame/audio/midway.h index ea813eaf1af..59135e72d35 100644 --- a/src/mame/audio/midway.h +++ b/src/mame/audio/midway.h @@ -18,10 +18,11 @@ #include "cpu/m6800/m6800.h" #include "cpu/m6809/m6809.h" #include "machine/6821pia.h" -#include "sound/tms5220.h" #include "sound/ay8910.h" #include "sound/dac.h" +#include "sound/flt_biquad.h" #include "sound/hc55516.h" +#include "sound/tms5220.h" //************************************************************************** @@ -148,7 +149,8 @@ private: // devices required_device<m68000_device> m_cpu; required_device<pia6821_device> m_pia; - required_device<dac_word_interface> m_dac; + required_device<ad7533_device> m_dac; + required_device_array<filter_biquad_device, 3> m_dac_filter; // internal state uint8_t m_status; |