[Scummvm-git-logs] scummvm master -> 335da77f49f0ca1c6e9be017eab03084430c34e8

AndywinXp noreply at scummvm.org
Sun Jun 15 08:01:44 UTC 2025


This automated email contains information about 1 new commit which have been
pushed to the 'scummvm' repo located at https://api.github.com/repos/scummvm/scummvm .

Summary:
335da77f49 SCUMM: SOUND/DiMUSE: Attempt to fix various data races


Commit: 335da77f49f0ca1c6e9be017eab03084430c34e8
    https://github.com/scummvm/scummvm/commit/335da77f49f0ca1c6e9be017eab03084430c34e8
Author: AndywinXp (andywinxp at gmail.com)
Date: 2025-06-15T10:01:34+02:00

Commit Message:
SCUMM: SOUND/DiMUSE: Attempt to fix various data races

Data races reported in ticket #15215:
"SCUMM: DIG: Error box 29 is out of bounds in ScummVM 2.8.1"

Changed paths:
    engines/scumm/imuse_digi/dimuse_engine.cpp
    engines/scumm/imuse_digi/dimuse_tracks.cpp
    engines/scumm/imuse_digi/dimuse_utils.cpp
    engines/scumm/resource.cpp
    engines/scumm/resource.h
    engines/scumm/sound.cpp
    engines/scumm/sound.h


diff --git a/engines/scumm/imuse_digi/dimuse_engine.cpp b/engines/scumm/imuse_digi/dimuse_engine.cpp
index c874c7f576d..92266d58fcc 100644
--- a/engines/scumm/imuse_digi/dimuse_engine.cpp
+++ b/engines/scumm/imuse_digi/dimuse_engine.cpp
@@ -902,6 +902,7 @@ int IMuseDigital::diMUSEGetParam(int soundId, int paramId) {
 }
 
 int IMuseDigital::diMUSEFadeParam(int soundId, int opcode, int destValue, int fadeLength) {
+	Common::StackLock lock(*_mutex);
 	return cmdsHandleCmd(DIMUSE_C_FADE_PARAM, nullptr, soundId, opcode, destValue, fadeLength);
 }
 
diff --git a/engines/scumm/imuse_digi/dimuse_tracks.cpp b/engines/scumm/imuse_digi/dimuse_tracks.cpp
index d38559decf0..28a6defc0f7 100644
--- a/engines/scumm/imuse_digi/dimuse_tracks.cpp
+++ b/engines/scumm/imuse_digi/dimuse_tracks.cpp
@@ -483,6 +483,8 @@ int IMuseDigital::tracksFeedStream(int soundId, uint8 *srcBuf, int32 sizeToFeed,
 }
 
 void IMuseDigital::tracksClear(IMuseDigiTrack *trackPtr) {
+	Common::StackLock lock(*_mutex);
+
 	if (_vm->_game.id == GID_CMI) {
 		if (trackPtr->syncPtr_0) {
 			trackPtr->syncSize_0 = 0;
diff --git a/engines/scumm/imuse_digi/dimuse_utils.cpp b/engines/scumm/imuse_digi/dimuse_utils.cpp
index 64a754e8e70..dfc68204fe0 100644
--- a/engines/scumm/imuse_digi/dimuse_utils.cpp
+++ b/engines/scumm/imuse_digi/dimuse_utils.cpp
@@ -24,6 +24,8 @@
 namespace Scumm {
 
 int IMuseDigital::addTrackToList(IMuseDigiTrack **listPtr, IMuseDigiTrack *listPtr_Item) {
+	Common::StackLock lock(*_mutex);
+
 	// [0] is ->prev, [1] is ->next
 	if (!listPtr_Item || listPtr_Item->prev || listPtr_Item->next) {
 		debug(5, "IMuseDigital::addTrackToList(): ERROR: arguments might be null");
@@ -49,6 +51,8 @@ int IMuseDigital::addTrackToList(IMuseDigiTrack **listPtr, IMuseDigiTrack *listP
 }
 
 int IMuseDigital::removeTrackFromList(IMuseDigiTrack **listPtr, IMuseDigiTrack *listPtr_Item) {
+	Common::StackLock lock(*_mutex);
+
 	IMuseDigiTrack *currentTrack = *listPtr;
 	IMuseDigiTrack *nextTrack;
 	if (listPtr_Item && currentTrack) {
diff --git a/engines/scumm/resource.cpp b/engines/scumm/resource.cpp
index 1960caefe18..e0a72312985 100644
--- a/engines/scumm/resource.cpp
+++ b/engines/scumm/resource.cpp
@@ -818,7 +818,10 @@ void ResourceManager::increaseResourceCounters() {
 	for (ResType type = rtFirst; type <= rtLast; type = ResType(type + 1)) {
 		ResId idx = _types[type].size();
 		while (idx-- > 0) {
+			_mutex->lock();
 			byte counter = _types[type][idx].getResourceCounter();
+			_mutex->unlock();
+
 			if (counter && counter < RF_USAGE_MAX) {
 				setResourceCounter(type, idx, counter + 1);
 			}
@@ -827,6 +830,7 @@ void ResourceManager::increaseResourceCounters() {
 }
 
 void ResourceManager::setResourceCounter(ResType type, ResId idx, byte counter) {
+	Common::StackLock lock(*_mutex);
 	_types[type][idx].setResourceCounter(counter);
 }
 
@@ -909,6 +913,7 @@ ResourceManager::ResTypeData::~ResTypeData() {
 }
 
 ResourceManager::ResourceManager(ScummEngine *vm) : _vm(vm) {
+	_mutex = &vm->_resourceAccessMutex;
 	_allocatedSize = 0;
 	_maxHeapThreshold = 0;
 	_minHeapThreshold = 0;
@@ -935,6 +940,7 @@ bool ResourceManager::validateResource(const char *str, ResType type, ResId idx)
 }
 
 void ResourceManager::nukeResource(ResType type, ResId idx) {
+	Common::StackLock lock(*_mutex);
 	byte *ptr = _types[type][idx]._address;
 	if (ptr != nullptr) {
 		debugC(DEBUG_RESOURCE, "nukeResource(%s,%d)", nameOfResType(type), idx);
@@ -969,18 +975,21 @@ int ScummEngine::getResourceDataSize(const byte *ptr) const {
 }
 
 void ResourceManager::lock(ResType type, ResId idx) {
+	Common::StackLock lock(*_mutex);
 	if (!validateResource("Locking", type, idx))
 		return;
 	_types[type][idx].lock();
 }
 
 void ResourceManager::unlock(ResType type, ResId idx) {
+	Common::StackLock lock(*_mutex);
 	if (!validateResource("Unlocking", type, idx))
 		return;
 	_types[type][idx].unlock();
 }
 
 bool ResourceManager::isLocked(ResType type, ResId idx) const {
+	Common::StackLock lock(*_mutex);
 	if (!validateResource("isLocked", type, idx))
 		return false;
 	return _types[type][idx].isLocked();
diff --git a/engines/scumm/resource.h b/engines/scumm/resource.h
index c812c4a3922..3e684bd72d5 100644
--- a/engines/scumm/resource.h
+++ b/engines/scumm/resource.h
@@ -82,6 +82,7 @@ class ResourceManager {
 	//friend class ScummEngine;
 protected:
 	ScummEngine *_vm;
+	Common::Mutex *_mutex;
 
 public:
 	class Resource {
diff --git a/engines/scumm/sound.cpp b/engines/scumm/sound.cpp
index 52846a66784..6967a103621 100644
--- a/engines/scumm/sound.cpp
+++ b/engines/scumm/sound.cpp
@@ -377,7 +377,7 @@ void Sound::processSfxQueues() {
 
 		if (_vm->_imuseDigital) {
 			finished = !isSoundRunning(kTalkSoundID);
-			if (_vm->_game.id == GID_CMI) {
+			if (_vm->_game.id == GID_CMI) { // No mutex lock here, COMI doesn't use the speech timer thread
 #if defined(ENABLE_SCUMM_7_8)
 				_curSoundPos = _vm->_imuseDigital->getSoundElapsedTimeInMs(kTalkSoundID) * 60 / 1000;
 #endif
@@ -392,6 +392,8 @@ void Sound::processSfxQueues() {
 			((uint)act < 0x80 && ((_vm->_game.version == 8) || (_vm->_game.version <= 7 && !_vm->_string[0].no_talk_anim)))) {
 			a = _vm->derefActor(act, "processSfxQueues");
 			if (a->isInCurrentRoom()) {
+				_speechTimerMutex.lock();
+
 				if (finished || (isMouthSyncOff(_curSoundPos) && _mouthSyncMode)) {
 					a->runActorTalkScript(a->_talkStopFrame);
 					_mouthSyncMode = 0;
@@ -399,6 +401,8 @@ void Sound::processSfxQueues() {
 					a->runActorTalkScript(a->_talkStartFrame);
 					_mouthSyncMode = 1;
 				}
+
+				_speechTimerMutex.unlock();
 			}
 #if defined(ENABLE_SCUMM_7_8)
 			if (_vm->_imuseDigital && !_vm->_imuseDigital->isFTSoundEngine()) {
@@ -1205,11 +1209,14 @@ bool Sound::isSfxFinished() const {
 }
 
 void Sound::incrementSpeechTimer() {
+	Common::StackLock lock(_speechTimerMutex);
+
 	if (!_soundsPaused)
 		_curSoundPos++;
 }
 
 void Sound::resetSpeechTimer() {
+	Common::StackLock lock(_speechTimerMutex);
 	_curSoundPos = 0;
 }
 
diff --git a/engines/scumm/sound.h b/engines/scumm/sound.h
index 46dda84541c..2b9b1e66c78 100644
--- a/engines/scumm/sound.h
+++ b/engines/scumm/sound.h
@@ -69,6 +69,8 @@ protected:
 	ScummEngine *_vm;
 	Audio::Mixer *_mixer;
 
+	Common::Mutex _speechTimerMutex;
+
 	int16 _midiQueuePos, _midiQueue[0x100];
 	int16 _soundQueuePos;
 




More information about the Scummvm-git-logs mailing list