From fe33ad0eac5382b0bd6ff1df02687844d6d6b157 Mon Sep 17 00:00:00 2001 From: arbee Date: Thu, 25 May 2023 22:46:05 -0400 Subject: sound/es5503.cpp: Support sync and AM modes and the last oscillator volume bug. [R. Belmont] --- src/devices/sound/es5503.cpp | 69 ++++++++++++++++++++++++++++++++++++++------ 1 file changed, 60 insertions(+), 9 deletions(-) diff --git a/src/devices/sound/es5503.cpp b/src/devices/sound/es5503.cpp index 08b12f3512c..70117baaca2 100644 --- a/src/devices/sound/es5503.cpp +++ b/src/devices/sound/es5503.cpp @@ -2,7 +2,7 @@ // copyright-holders:R. Belmont /* - ES5503 - Ensoniq ES5503 "DOC" emulator v2.1.3 + ES5503 - Ensoniq ES5503 "DOC" emulator v2.3 By R. Belmont. Copyright R. Belmont. @@ -13,8 +13,8 @@ (used in the "Soundscape" series of ISA PC sound cards) followed on a fundamentally similar architecture. - Bugs: On the real silicon, oscillators 30 and 31 have random volume fluctuations and are - unusable for playback. We don't attempt to emulate that. :-) + Bugs: On the real silicon, the uppermost enabled oscillator contributes to the output 3 times. + This is likely why the Apple IIgs system software doesn't let you use oscillators 30 and 31. Additionally, in "swap" mode, there's one cycle when the switch takes place where the oscillator's output is 0x80 (centerline) regardless of the sample data. This can @@ -35,6 +35,7 @@ want to loop. 2.1.3 (RB) - Fixed oscillator enable register off-by-1 which caused everything to be half a step sharp. 2.2 (RB) - More precise one-shot even/swap odd behavior from hardware observations with Ian Brumby's SWAPTEST. + 2.3 (RB) - Sync & AM modes added, emulate the volume glitch for the highest-numbered enabled oscillator. */ #include "emu.h" @@ -93,9 +94,26 @@ void es5503_device::halt_osc(int onum, int type, uint32_t *accumulator, int ress { ES5503Osc *pOsc = &oscillators[onum]; ES5503Osc *pPartner = &oscillators[onum^1]; - const int mode = (pOsc->control>>1) & 3; + int mode = (pOsc->control>>1) & 3; const int partnerMode = (pPartner->control>>1) & 3; + // check for sync mode + if (mode == MODE_SYNCAM) + { + if (!(onum & 1)) + { + // we're even, so if the odd oscillator 1 below us is playing, + // restart it. + if (!(oscillators[onum - 1].control & 1)) + { + oscillators[onum - 1].accumulator = 0; + } + } + + // loop this oscillator for both sync and AM + mode = MODE_FREE; + } + // if 0 found in sample data or mode is not free-run, halt this oscillator if ((mode != MODE_FREE) || (type != 0)) { @@ -154,13 +172,14 @@ void es5503_device::sound_stream_update(sound_stream &stream, std::vectorwavetblpointer & wavemasks[pOsc->wavetblsize], altram; uint32_t acc = pOsc->accumulator; - uint16_t wtsize = pOsc->wtsize - 1; + const uint16_t wtsize = pOsc->wtsize - 1; uint8_t ctrl = pOsc->control; - uint16_t freq = pOsc->freq; + const uint16_t freq = pOsc->freq; int16_t vol = pOsc->vol; int8_t data = -128; - int resshift = resshifts[pOsc->resolution] - pOsc->wavetblsize; - uint32_t sizemask = accmasks[pOsc->wavetblsize]; + const int resshift = resshifts[pOsc->resolution] - pOsc->wavetblsize; + const uint32_t sizemask = accmasks[pOsc->wavetblsize]; + const int mode = (pOsc->control>>1) & 3; mixp = &m_mix_buffer[0] + chan; for (snum = 0; snum < samples; snum++) @@ -180,7 +199,39 @@ void es5503_device::sound_stream_update(sound_stream &stream, std::vector= wtsize) -- cgit v1.2.3