[Scummvm-git-logs] scummvm master -> b58b09323cfac7ab4f261e5d943e1c83846c1ea0

aquadran aquadran at gmail.com
Tue Dec 8 07:09:23 UTC 2020


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

Summary:
26207d29b7 SCUMM: Don't error out on invalid bundles
b58b09323c SCUMM: Support for uncompressed bundles like used in some fan translations


Commit: 26207d29b7e62ee3eaccd32fc200e4f3da601ec6
    https://github.com/scummvm/scummvm/commit/26207d29b7e62ee3eaccd32fc200e4f3da601ec6
Author: Vladimir Serbinenko (phcoder at google.com)
Date: 2020-12-08T08:09:17+01:00

Commit Message:
SCUMM: Don't error out on invalid bundles

Akella COMI localization contaions 2 garbage sounds: one is in RIFF WAV and
other is raw sound instead of iMuse. As itÅ› only 2 utterances it's not
critical but avoid crashing on them

Changed paths:
    engines/scumm/imuse_digi/dimuse_bndmgr.cpp


diff --git a/engines/scumm/imuse_digi/dimuse_bndmgr.cpp b/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
index bf024aa098..7339f064bb 100644
--- a/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
+++ b/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
@@ -224,7 +224,7 @@ bool BundleMgr::loadCompTable(int32 index) {
 	_file->seek(8, SEEK_CUR);
 
 	if (tag != MKTAG('C','O','M','P')) {
-		error("BundleMgr::loadCompTable() Compressed sound %d (%s:%d) invalid (%s)", index, _file->getName(), _bundleTable[index].offset, tag2str(tag));
+		debug("BundleMgr::loadCompTable() Compressed sound %d (%s:%d) invalid (%s)", index, _file->getName(), _bundleTable[index].offset, tag2str(tag));
 		return false;
 	}
 


Commit: b58b09323cfac7ab4f261e5d943e1c83846c1ea0
    https://github.com/scummvm/scummvm/commit/b58b09323cfac7ab4f261e5d943e1c83846c1ea0
Author: Vladimir Serbinenko (phcoder at google.com)
Date: 2020-12-08T08:09:17+01:00

Commit Message:
SCUMM: Support for uncompressed bundles like used in some fan translations

Apparently it's a beta variant of storing files in the bundle without
compression and in little-endian. I tried to find an indicator for endianness
in uncompressed iMuse file but apparently there isn't any. Hence we need to
propagate a bool from bundle to imuse layer.

This is used by Akella Russification of COMI

Changed paths:
    engines/scumm/imuse_digi/dimuse.cpp
    engines/scumm/imuse_digi/dimuse_bndmgr.cpp
    engines/scumm/imuse_digi/dimuse_bndmgr.h
    engines/scumm/imuse_digi/dimuse_sndmgr.cpp
    engines/scumm/imuse_digi/dimuse_sndmgr.h
    engines/scumm/imuse_digi/dimuse_track.cpp
    engines/scumm/imuse_digi/dimuse_track.h


diff --git a/engines/scumm/imuse_digi/dimuse.cpp b/engines/scumm/imuse_digi/dimuse.cpp
index 80b8edcee8..1ea5aff8a5 100644
--- a/engines/scumm/imuse_digi/dimuse.cpp
+++ b/engines/scumm/imuse_digi/dimuse.cpp
@@ -86,6 +86,8 @@ static int32 makeMixerFlags(Track *track) {
 	if (track->sndDataExtComp)
 		mixerFlags |= Audio::FLAG_LITTLE_ENDIAN;
 #endif
+	if (track->littleEndian)
+		mixerFlags |= Audio::FLAG_LITTLE_ENDIAN;
 	if (flags & kFlagStereo)
 		mixerFlags |= Audio::FLAG_STEREO;
 	return mixerFlags;
@@ -182,6 +184,7 @@ void IMuseDigital::saveLoadEarly(Common::Serializer &s) {
 			int freq = _sound->getFreq(track->soundDesc);
 			track->feedSize = freq * channels;
 			track->mixerFlags = 0;
+			track->littleEndian = track->soundDesc->littleEndian;
 			if (channels == 2)
 				track->mixerFlags = kFlagStereo;
 
diff --git a/engines/scumm/imuse_digi/dimuse_bndmgr.cpp b/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
index 7339f064bb..53169d9c35 100644
--- a/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
+++ b/engines/scumm/imuse_digi/dimuse_bndmgr.cpp
@@ -193,6 +193,7 @@ bool BundleMgr::open(const char *filename, bool &compressed, bool errorFlag) {
 	_indexTable = _cache->getIndexTable(slot);
 	assert(_bundleTable);
 	_compTableLoaded = false;
+	_isUncompressed = false;
 	_outputSize = 0;
 	_lastBlock = -1;
 
@@ -206,6 +207,7 @@ void BundleMgr::close() {
 		_numFiles = 0;
 		_numCompItems = 0;
 		_compTableLoaded = false;
+		_isUncompressed = false;
 		_lastBlock = -1;
 		_outputSize = 0;
 		_curSampleId = -1;
@@ -219,6 +221,12 @@ void BundleMgr::close() {
 bool BundleMgr::loadCompTable(int32 index) {
 	_file->seek(_bundleTable[index].offset, SEEK_SET);
 	uint32 tag = _file->readUint32BE();
+
+	if (tag == MKTAG('i','M','U','S')) {
+		_isUncompressed = true;
+		return true;
+	}
+
 	_numCompItems = _file->readUint32BE();
 	assert(_numCompItems > 0);
 	_file->seek(8, SEEK_CUR);
@@ -247,10 +255,12 @@ bool BundleMgr::loadCompTable(int32 index) {
 }
 
 int32 BundleMgr::decompressSampleByCurIndex(int32 offset, int32 size, byte **compFinal, int headerSize, bool headerOutside) {
-	return decompressSampleByIndex(_curSampleId, offset, size, compFinal, headerSize, headerOutside);
+	bool ignored = false;
+	return decompressSampleByIndex(_curSampleId, offset, size, compFinal, headerSize, headerOutside, ignored);
 }
 
-int32 BundleMgr::decompressSampleByIndex(int32 index, int32 offset, int32 size, byte **compFinal, int headerSize, bool headerOutside) {
+int32 BundleMgr::decompressSampleByIndex(int32 index, int32 offset, int32 size, byte **compFinal, int headerSize, bool headerOutside,
+					 bool &uncompressedBundle) {
 	int32 i, finalSize, outputSize;
 	int skip, firstBlock, lastBlock;
 
@@ -272,6 +282,16 @@ int32 BundleMgr::decompressSampleByIndex(int32 index, int32 offset, int32 size,
 			return 0;
 	}
 
+	uncompressedBundle = _isUncompressed;
+
+	if (_isUncompressed) {
+		_file->seek(_bundleTable[index].offset + offset + headerSize, SEEK_SET);
+		*compFinal = (byte *)malloc(size);
+		assert(*compFinal);
+		_file->read(*compFinal, size);
+		return size;
+	}
+
 	firstBlock = (offset + headerSize) / 0x2000;
 	lastBlock = (offset + headerSize + size - 1) / 0x2000;
 
@@ -330,7 +350,8 @@ int32 BundleMgr::decompressSampleByIndex(int32 index, int32 offset, int32 size,
 	return finalSize;
 }
 
-int32 BundleMgr::decompressSampleByName(const char *name, int32 offset, int32 size, byte **comp_final, bool header_outside) {
+int32 BundleMgr::decompressSampleByName(const char *name, int32 offset, int32 size, byte **comp_final, bool header_outside,
+					bool &uncompressedBundle) {
 	int32 final_size = 0;
 
 	if (!_file->isOpen()) {
@@ -343,7 +364,7 @@ int32 BundleMgr::decompressSampleByName(const char *name, int32 offset, int32 si
 	BundleDirCache::IndexNode *found = (BundleDirCache::IndexNode *)bsearch(&target, _indexTable, _numFiles,
 			sizeof(BundleDirCache::IndexNode), (int (*)(const void*, const void*))scumm_stricmp);
 	if (found) {
-		final_size = decompressSampleByIndex(found->index, offset, size, comp_final, 0, header_outside);
+		final_size = decompressSampleByIndex(found->index, offset, size, comp_final, 0, header_outside, uncompressedBundle);
 		return final_size;
 	}
 
diff --git a/engines/scumm/imuse_digi/dimuse_bndmgr.h b/engines/scumm/imuse_digi/dimuse_bndmgr.h
index 2d04e88246..ca7e434bf2 100644
--- a/engines/scumm/imuse_digi/dimuse_bndmgr.h
+++ b/engines/scumm/imuse_digi/dimuse_bndmgr.h
@@ -84,6 +84,7 @@ private:
 	int _curSampleId;
 	BaseScummFile *_file;
 	bool _compTableLoaded;
+	bool _isUncompressed;
 	int _fileBundleId;
 	byte _compOutputBuff[0x2000];
 	byte *_compInputBuff;
@@ -100,8 +101,8 @@ public:
 	bool open(const char *filename, bool &compressed, bool errorFlag = false);
 	void close();
 	Common::SeekableReadStream *getFile(const char *filename, int32 &offset, int32 &size);
-	int32 decompressSampleByName(const char *name, int32 offset, int32 size, byte **compFinal, bool headerOutside);
-	int32 decompressSampleByIndex(int32 index, int32 offset, int32 size, byte **compFinal, int header_size, bool headerOutside);
+	int32 decompressSampleByName(const char *name, int32 offset, int32 size, byte **compFinal, bool headerOutside, bool &uncompressedBundle);
+	int32 decompressSampleByIndex(int32 index, int32 offset, int32 size, byte **compFinal, int header_size, bool headerOutside, bool &uncompressedBundle);
 	int32 decompressSampleByCurIndex(int32 offset, int32 size, byte **compFinal, int headerSize, bool headerOutside);
 };
 
diff --git a/engines/scumm/imuse_digi/dimuse_sndmgr.cpp b/engines/scumm/imuse_digi/dimuse_sndmgr.cpp
index a34e24f28b..ffd020a3fe 100644
--- a/engines/scumm/imuse_digi/dimuse_sndmgr.cpp
+++ b/engines/scumm/imuse_digi/dimuse_sndmgr.cpp
@@ -151,7 +151,7 @@ void ImuseDigiSndMgr::prepareSoundFromRMAP(Common::SeekableReadStream *file, Sou
 	}
 }
 
-void ImuseDigiSndMgr::prepareSound(byte *ptr, SoundDesc *sound) {
+void ImuseDigiSndMgr::prepareSound(byte *ptr, SoundDesc *sound, bool rawBundle) {
 	if (READ_BE_UINT32(ptr) == MKTAG('C','r','e','a')) {
 		bool quit = false;
 		int len;
@@ -251,6 +251,8 @@ void ImuseDigiSndMgr::prepareSound(byte *ptr, SoundDesc *sound) {
 			switch (tag) {
 			case MKTAG('F','R','M','T'):
 				ptr += 12;
+				sound->littleEndian = READ_BE_UINT32(ptr) == 16 && rawBundle;
+
 				sound->bits = READ_BE_UINT32(ptr); ptr += 4;
 				sound->freq = READ_BE_UINT32(ptr); ptr += 4;
 				sound->channels = READ_BE_UINT32(ptr); ptr += 4;
@@ -389,6 +391,7 @@ bool ImuseDigiSndMgr::openVoiceBundle(SoundDesc *sound, int &disk) {
 ImuseDigiSndMgr::SoundDesc *ImuseDigiSndMgr::openSound(int32 soundId, const char *soundName, int soundType, int volGroupId, int disk) {
 	assert(soundId >= 0);
 	assert(soundType);
+	bool rawBundle = false;
 
 	SoundDesc *sound = allocSlot();
 	if (!sound) {
@@ -440,13 +443,13 @@ ImuseDigiSndMgr::SoundDesc *ImuseDigiSndMgr::openSound(int32 soundId, const char
 			sound->disk = disk;
 			return sound;
 		} else if (soundName[0] == 0) {
-			if (sound->bundle->decompressSampleByIndex(soundId, 0, 0x2000, &ptr, 0, header_outside) == 0 || ptr == NULL) {
+			if (sound->bundle->decompressSampleByIndex(soundId, 0, 0x2000, &ptr, 0, header_outside, rawBundle) == 0 || ptr == NULL) {
 				closeSound(sound);
 				free(ptr);
 				return NULL;
 			}
 		} else {
-			if (sound->bundle->decompressSampleByName(soundName, 0, 0x2000, &ptr, header_outside) == 0 || ptr == NULL) {
+			if (sound->bundle->decompressSampleByName(soundName, 0, 0x2000, &ptr, header_outside, rawBundle) == 0 || ptr == NULL) {
 				closeSound(sound);
 				free(ptr);
 				return NULL;
@@ -463,7 +466,7 @@ ImuseDigiSndMgr::SoundDesc *ImuseDigiSndMgr::openSound(int32 soundId, const char
 	sound->type = soundType;
 	sound->volGroupId = volGroupId;
 	sound->disk = _disk;
-	prepareSound(ptr, sound);
+	prepareSound(ptr, sound, rawBundle);
 	if ((soundType == IMUSE_BUNDLE) && !sound->compressed) {
 		free(ptr);
 	}
diff --git a/engines/scumm/imuse_digi/dimuse_sndmgr.h b/engines/scumm/imuse_digi/dimuse_sndmgr.h
index 2f91405588..a3f65c194c 100644
--- a/engines/scumm/imuse_digi/dimuse_sndmgr.h
+++ b/engines/scumm/imuse_digi/dimuse_sndmgr.h
@@ -82,6 +82,7 @@ public:
 		uint16 freq;		// frequency
 		byte channels;		// stereo or mono
 		byte bits;			// 8, 12, 16
+		bool littleEndian;      // Endianness: default is big for original files and native for recompressed ones
 
 		int numJumps;		// number of Jumps
 		Region *region;
@@ -117,7 +118,7 @@ private:
 
 	bool checkForProperHandle(SoundDesc *soundDesc);
 	SoundDesc *allocSlot();
-	void prepareSound(byte *ptr, SoundDesc *sound);
+	void prepareSound(byte *ptr, SoundDesc *sound, bool uncompressedBundle);
 	void prepareSoundFromRMAP(Common::SeekableReadStream *file, SoundDesc *sound, int32 offset, int32 size);
 
 	ScummEngine *_vm;
diff --git a/engines/scumm/imuse_digi/dimuse_track.cpp b/engines/scumm/imuse_digi/dimuse_track.cpp
index 94e6475a23..ebd2fa2a9e 100644
--- a/engines/scumm/imuse_digi/dimuse_track.cpp
+++ b/engines/scumm/imuse_digi/dimuse_track.cpp
@@ -164,6 +164,8 @@ void IMuseDigital::startSound(int soundId, const char *soundName, int soundType,
 		} else
 			error("IMuseDigital::startSound(): Can't handle %d bit samples", bits);
 
+		track->littleEndian = track->soundDesc->littleEndian;
+
 		int fadeDelay = 30; // Default fade value if not found anywhere else
 
 		if (otherTrack && otherTrack->used && !otherTrack->toBeRemoved) {
diff --git a/engines/scumm/imuse_digi/dimuse_track.h b/engines/scumm/imuse_digi/dimuse_track.h
index 3be31cb7f3..9cad1c1fc6 100644
--- a/engines/scumm/imuse_digi/dimuse_track.h
+++ b/engines/scumm/imuse_digi/dimuse_track.h
@@ -72,6 +72,7 @@ struct Track {
 	int32 feedSize;		   // size of sound data needed to be filled at each callback iteration
 	int32 dataMod12Bit;	   // value used between all callback to align 12 bit source of data
 	int32 mixerFlags;	   // flags for sound mixer's channel (kFlagStereo, kFlag16Bits, kFlagUnsigned)
+	bool littleEndian;	   // Endianness: default is big for original files and native for recompressed ones
 
 	ImuseDigiSndMgr::SoundDesc *soundDesc;	// sound handle used by iMuse sound manager
 	Audio::SoundHandle mixChanHandle;		// sound mixer's channel handle
@@ -110,6 +111,7 @@ struct Track {
 		soundDesc = nullptr;
 		stream = nullptr;
 		speakingActor = nullptr;
+		littleEndian = false;
 	}
 
 	int getPan() const { return (pan != 64) ? 2 * pan - 127 : 0; }




More information about the Scummvm-git-logs mailing list