[Scummvm-cvs-logs] SF.net SVN: scummvm:[34015] scummvm/trunk/engines/kyra/sound_towns.cpp

athrxx at users.sourceforge.net athrxx at users.sourceforge.net
Tue Aug 19 03:00:16 CEST 2008


Revision: 34015
          http://scummvm.svn.sourceforge.net/scummvm/?rev=34015&view=rev
Author:   athrxx
Date:     2008-08-19 01:00:15 +0000 (Tue, 19 Aug 2008)

Log Message:
-----------
fixed bug that caused a lockup in certain configurations when the music was fading

Modified Paths:
--------------
    scummvm/trunk/engines/kyra/sound_towns.cpp

Modified: scummvm/trunk/engines/kyra/sound_towns.cpp
===================================================================
--- scummvm/trunk/engines/kyra/sound_towns.cpp	2008-08-18 22:27:21 UTC (rev 34014)
+++ scummvm/trunk/engines/kyra/sound_towns.cpp	2008-08-19 01:00:15 UTC (rev 34015)
@@ -1592,7 +1592,7 @@
 	void loadMusicData(uint8 *data, bool loadPaused = false);
 	void loadSoundEffectData(uint8 *data, uint8 trackNum);
 	void reset();
-	void fadeOut();
+	void fadeStep();
 
 	void pause() { _musicPlaying = false; }
 	void cont() { _musicPlaying = true; }
@@ -1601,6 +1601,7 @@
 	void nextTick(int32 *buffer, uint32 bufferSize);
 
 	bool looping() { return _looping == _updateChannelsFlag ? true : false; }
+	bool musicPlaying() { return _musicPlaying; }
 
 	// AudioStream interface
 	int inline readBuffer(int16 *buffer, const int numSamples);
@@ -1660,7 +1661,7 @@
 	uint16 _tempo;
 	bool _musicPlaying;
 	bool _sfxPlaying;
-	bool _fading;
+	uint8 _fading;
 	uint8 _looping;
 	uint32 _musicTickCounter;
 
@@ -2798,6 +2799,63 @@
 	*_regIndex = value;
 }
 
+void TownsPC98_OpnSquareSineSource::nextTick(int32 *buffer, uint32 bufferSize) {
+	if (!_ready)
+		return;
+
+	for (uint32 i = 0; i < bufferSize; i++) {
+		_timer += _tickLength;
+		while (_timer > 0x30000) {
+			_timer -= 0x30000;
+
+			if (++_nTick >= (_reg[6] & 0x1f)) {
+				if ((_rand + 1) & 2)
+					_outN ^= 1;
+
+				_rand = (((_rand & 1) ^ ((_rand >> 3) & 1)) << 16) | (_rand >> 1);
+				_nTick = 0;
+			}
+
+			for (int ii = 0; ii < 3; ii++) {
+				if (++_channels[ii].tick >= (((_reg[ii * 2 + 1] & 0x0f) << 8) | _reg[ii * 2])) {
+					_channels[ii].tick = 0;
+					_channels[ii].smp ^= 1;
+				}
+				_channels[ii].out = (_channels[ii].smp | ((_reg[7] >> ii) & 1)) & (_outN | ((_reg[7] >> (ii + 3)) & 1));
+			}
+
+			if (_evpUpdate) {
+				if (++_evpUpdateCnt >= ((_reg[12] << 8) | _reg[11])) {
+					_evpUpdateCnt = 0;
+
+					if (--_evpTimer < 0) {
+						if (_cont) {
+							_evpTimer &= 0x1f;
+						} else {
+							_evpUpdate = false;
+							_evpTimer = 0;
+						}
+					}
+				}
+			}
+			_pReslt = _evpTimer ^ _attack;
+			updatesRegs();
+		}
+
+		int32 finOut = 0;
+		for (int ii = 0; ii < 3; ii++) {
+			if ((_reg[ii + 8] >> 4) & 1)
+				finOut += _tleTable[_channels[ii].out ? _pReslt : 0];
+			else
+				finOut += _tlTable[_channels[ii].out ? (_reg[ii + 8] & 0x0f) : 0];
+		}
+
+		finOut /= 2;
+		buffer[i << 1] += finOut;
+		buffer[(i << 1) + 1] += finOut;
+	}
+}
+
 void TownsPC98_OpnSquareSineSource::updatesRegs() {
 	for (int i = 0; i < _updateRequest;) {
 		uint8 b = _updateRequestBuf[i++];
@@ -2977,63 +3035,6 @@
 	}
 }
 
-void TownsPC98_OpnSquareSineSource::nextTick(int32 *buffer, uint32 bufferSize) {
-	if (!_ready)
-		return;
-
-	for (uint32 i = 0; i < bufferSize; i++) {
-		_timer += _tickLength;
-		while (_timer > 0x30000) {
-			_timer -= 0x30000;
-
-			if (++_nTick >= (_reg[6] & 0x1f)) {
-				if ((_rand + 1) & 2)
-					_outN ^= 1;
-
-				_rand = (((_rand & 1) ^ ((_rand >> 3) & 1)) << 16) | (_rand >> 1);
-				_nTick = 0;
-			}
-
-			for (int ii = 0; ii < 3; ii++) {
-				if (++_channels[ii].tick >= (((_reg[ii * 2 + 1] & 0x0f) << 8) | _reg[ii * 2])) {
-					_channels[ii].tick = 0;
-					_channels[ii].smp ^= 1;
-				}
-				_channels[ii].out = (_channels[ii].smp | ((_reg[7] >> ii) & 1)) & (_outN | ((_reg[7] >> (ii + 3)) & 1));
-			}
-
-			if (_evpUpdate) {
-				if (++_evpUpdateCnt >= ((_reg[12] << 8) | _reg[11])) {
-					_evpUpdateCnt = 0;
-
-					if (--_evpTimer < 0) {
-						if (_cont) {
-							_evpTimer &= 0x1f;
-						} else {
-							_evpUpdate = false;
-							_evpTimer = 0;
-						}
-					}
-				}
-			}
-			_pReslt = _evpTimer ^ _attack;
-			updatesRegs();
-		}
-
-		int32 finOut = 0;
-		for (int ii = 0; ii < 3; ii++) {
-			if ((_reg[ii + 8] >> 4) & 1)
-				finOut += _tleTable[_channels[ii].out ? _pReslt : 0];
-			else
-				finOut += _tlTable[_channels[ii].out ? (_reg[ii + 8] & 0x0f) : 0];
-		}
-
-		finOut /= 2;
-		buffer[i << 1] += finOut;
-		buffer[(i << 1) + 1] += finOut;
-	}
-}
-
 TownsPC98_OpnDriver::TownsPC98_OpnDriver(Audio::Mixer *mixer, OpnType type) :
 	_mixer(mixer), _trackPtr(0), _musicPlaying(false), _sfxPlaying(false), _fading(false), _channels(0),
 	_ssgChannels(0), _sfxChannels(0), _pcmChannel(0),	_looping(0), _opnCarrier(_drvTables + 76),
@@ -3317,41 +3318,34 @@
 	unlock();
 }
 
-void TownsPC98_OpnDriver::fadeOut() {
+void TownsPC98_OpnDriver::fadeStep() {
 	if (!_musicPlaying)
 		return;
 
-	if (_hasPCM) {
-		lock();
-		if (_updatePCMFlag & _pcmChannel->_idFlag)
-			_pcmChannel->reset();
-		unlock();
+	lock();
+
+	for (int j = 0; j < _numChan; j++) {
+		if (_updateChannelsFlag & _channels[j]->_idFlag)
+			_channels[j]->fadeStep();
 	}
+		
+	for (int j = 0; j < _numSSG; j++) {
+		if (_updateSSGFlag & _ssgChannels[j]->_idFlag)
+			_ssgChannels[j]->fadeStep();
+	}
 
-	for (int i = 0; i < 20; i++) {
-		lock();
-
-		_fading = true;
-
-		uint32 dTime = _musicTickCounter + 2;
-		for (int j = 0; j < _numChan; j++) {
-			if (_updateChannelsFlag & _channels[j]->_idFlag)
-				_channels[j]->fadeStep();
+	if (!_fading) {
+		_fading = 19;
+		if (_hasPCM) {
+			if (_updatePCMFlag & _pcmChannel->_idFlag)
+				_pcmChannel->reset();
 		}
-		for (int j = 0; j < _numSSG; j++) {
-			if (_updateSSGFlag & _ssgChannels[j]->_idFlag)
-				_ssgChannels[j]->fadeStep();
-		}
-
-		unlock();
-
-		while (_musicPlaying) {
-			if (_musicTickCounter >= dTime)
-				break;
-		}
+	} else {
+		if (!--_fading)
+			reset();
 	}
 
-	reset();
+	unlock();
 }
 
 void TownsPC98_OpnDriver::callback() {
@@ -3831,7 +3825,13 @@
 }
 
 void SoundPC98::beginFadeOut() {
-	_driver->fadeOut();
+	if (!_driver->musicPlaying())
+		return;
+
+	for (int i = 0; i < 20; i++) {
+		_driver->fadeStep();
+		_vm->delay(32);
+	}
 	haltTrack();
 }
 
@@ -3930,7 +3930,14 @@
 }
 
 void SoundTownsPC98_v2::beginFadeOut() {
-	_driver->fadeOut();
+	if (!_driver->musicPlaying())
+		return;
+
+	for (int i = 0; i < 20; i++) {
+		_driver->fadeStep();
+		_vm->delay(32);
+	}
+
 	haltTrack();
 }
 


This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.




More information about the Scummvm-git-logs mailing list