diff options
author | athrxx | 2019-11-10 15:24:41 +0100 |
---|---|---|
committer | athrxx | 2019-12-18 20:50:39 +0100 |
commit | 21b5f9262c14114f457120a0504a55fc3ca96489 (patch) | |
tree | cebb9eae8918ef1069cdbb2171021c71f4606ae9 /engines/sci | |
parent | 1083b94cbfbf687b40d487ab2530be9fb1556b1a (diff) | |
download | scummvm-rg350-21b5f9262c14114f457120a0504a55fc3ca96489.tar.gz scummvm-rg350-21b5f9262c14114f457120a0504a55fc3ca96489.tar.bz2 scummvm-rg350-21b5f9262c14114f457120a0504a55fc3ca96489.zip |
AUDIO: (FM-TOWNS/PC-98) - fix regression from 0e734722
My commit 0e734722 causes lockups in SCUMM (sometimes) and SCI (very often). I didn't like the way I had fixed this before, but in the end I now had to do it in a similar way.
Diffstat (limited to 'engines/sci')
-rw-r--r-- | engines/sci/sound/drivers/fmtowns.cpp | 2 | ||||
-rw-r--r-- | engines/sci/sound/drivers/pc9801.cpp | 31 |
2 files changed, 21 insertions, 12 deletions
diff --git a/engines/sci/sound/drivers/fmtowns.cpp b/engines/sci/sound/drivers/fmtowns.cpp index 7475b01a6f..4dd74bc42d 100644 --- a/engines/sci/sound/drivers/fmtowns.cpp +++ b/engines/sci/sound/drivers/fmtowns.cpp @@ -405,7 +405,7 @@ int TownsMidiPart::allocateChannel() { } MidiDriver_FMTowns::MidiDriver_FMTowns(Audio::Mixer *mixer, SciVersion version) : _version(version), _timerProc(0), _timerProcPara(0), _baseTempo(10080), _ready(false), _isOpen(false), _masterVolume(0x0f), _soundOn(true) { - _intf = new TownsAudioInterface(mixer, this); + _intf = new TownsAudioInterface(mixer, this, true); _out = new TownsChannel*[6]; for (int i = 0; i < 6; i++) _out[i] = new TownsChannel(this, i); diff --git a/engines/sci/sound/drivers/pc9801.cpp b/engines/sci/sound/drivers/pc9801.cpp index a4b634f1dd..13cb9d0371 100644 --- a/engines/sci/sound/drivers/pc9801.cpp +++ b/engines/sci/sound/drivers/pc9801.cpp @@ -328,6 +328,7 @@ private: const uint16 _baseTempo; PC98AudioCore *_pc98a; + Audio::Mixer *_mixer; const SciVersion _version; }; @@ -1317,27 +1318,28 @@ void MidiPart_PC9801::assignFreeChannels() { MidiPart_PC9801 **MidiDriver_PC9801::_parts = 0; MidiDriver_PC9801::MidiDriver_PC9801(Audio::Mixer *mixer, SciVersion version) - : _version(version), _pc98a(0), _chan(0), _numChan(6), _internalVersion(0xFF), _ssgPatchOffset(0xFF), _patchSize(0), + : _mixer(mixer), _version(version), _pc98a(0), _chan(0), _numChan(6), _internalVersion(0xFF), _ssgPatchOffset(0xFF), _patchSize(0), _timerProc(0), _timerProcPara(0), _baseTempo(10080), _ready(false), _isOpen(false), _masterVolume(0x0f) ,_soundOn(true), _playID(0), _polyphony(9), _channelMask1(0x10), _channelMask2(0x02) { - _pc98a = -#ifdef SCI_PC98_AUDIO_EXTENDED - new PC98AudioCore(mixer, this, kType86); -#else - new PC98AudioCore(mixer, this, kType26); -#endif } MidiDriver_PC9801::~MidiDriver_PC9801() { - _ready = false; close(); - delete _pc98a; } int MidiDriver_PC9801::open() { if (_isOpen) return MERR_ALREADY_OPEN; + if (!_pc98a) { + _pc98a = +#ifdef SCI_PC98_AUDIO_EXTENDED + new PC98AudioCore(_mixer, this, kType86); +#else + new PC98AudioCore(_mixer, this, kType26); +#endif + } + if (!_ready) { if (!_pc98a->init()) return MERR_CANNOT_CONNECT; @@ -1413,7 +1415,8 @@ void MidiDriver_PC9801::close() { bool ready = _ready; _isOpen = _ready = false; - PC98AudioCore::MutexLock lock = _pc98a->stackLockMutex(); + delete _pc98a; + _pc98a = 0; if (_parts) { for (int i = 0; i < 16; ++i) { @@ -1624,8 +1627,14 @@ bool MidiDriver_PC9801::loadInstruments(const SciSpan<const uint8> &data) { } void MidiDriver_PC9801::updateParser() { - if (_timerProc) + if (_timerProc) { + // The mutex lock has to be lifted, before entering the SCI engine space. The engine has its owns mutex and the different threads + // will often cause an immediate lockup (each thread caught in the mutex lock of the other). I consider this safe for all realistic + // scenarios, since a reentry of the space guarded by the PC98 audio mutex is not possible without triggering another mutex lock. + // I have also rearranged the driver deconstruction appropriately. + PC98AudioCore::MutexLock tempUnlock = _pc98a->stackUnlockMutex(); _timerProc(_timerProcPara); + } } void MidiDriver_PC9801::updateChannels() { |