[Scummvm-cvs-logs] scummvm master -> 2dee92a908b84ae870bfdbfd00318549485b7984
dreammaster
dreammaster at scummvm.org
Mon Aug 6 12:04:41 CEST 2012
This automated email contains information about 1 new commit which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .
Summary:
2dee92a908 TINSEL: Fixed portability issue with earlier savegames
Commit: 2dee92a908b84ae870bfdbfd00318549485b7984
https://github.com/scummvm/scummvm/commit/2dee92a908b84ae870bfdbfd00318549485b7984
Author: Paul Gilbert (dreammaster at scummvm.org)
Date: 2012-08-06T03:03:56-07:00
Commit Message:
TINSEL: Fixed portability issue with earlier savegames
Changed paths:
engines/tinsel/dialogs.cpp
engines/tinsel/dialogs.h
engines/tinsel/saveload.cpp
diff --git a/engines/tinsel/dialogs.cpp b/engines/tinsel/dialogs.cpp
index dde3484..56ee2ea 100644
--- a/engines/tinsel/dialogs.cpp
+++ b/engines/tinsel/dialogs.cpp
@@ -1263,6 +1263,20 @@ static INV_OBJECT *GetInvObject(int id) {
}
/**
+ * Returns true if the given id represents a valid inventory object
+ */
+bool GetIsInvObject(int id) {
+ INV_OBJECT *pObject = g_invObjects;
+
+ for (int i = 0; i < g_numObjects; i++, pObject++) {
+ if (pObject->id == id)
+ return true;
+ }
+
+ return false;
+}
+
+/**
* Convert item ID number to index.
*/
static int GetObjectIndex(int id) {
diff --git a/engines/tinsel/dialogs.h b/engines/tinsel/dialogs.h
index 8c48eb8..ab53ba7 100644
--- a/engines/tinsel/dialogs.h
+++ b/engines/tinsel/dialogs.h
@@ -152,6 +152,8 @@ void InvSetLimit(int invno, int n);
void InvSetSize(int invno, int MinWidth, int MinHeight,
int StartWidth, int StartHeight, int MaxWidth, int MaxHeight);
+bool GetIsInvObject(int id);
+
int WhichInventoryOpen();
bool IsTopWindow();
diff --git a/engines/tinsel/saveload.cpp b/engines/tinsel/saveload.cpp
index 0a552c8..518e27f 100644
--- a/engines/tinsel/saveload.cpp
+++ b/engines/tinsel/saveload.cpp
@@ -55,8 +55,7 @@ namespace Tinsel {
* only saves/loads those which are valid for the version of the savegame
* which is being loaded/saved currently.
*/
-#define CURRENT_VER 1
-// TODO: Not yet used
+#define CURRENT_VER 2
/**
* An auxillary macro, used to specify savegame versions. We use this instead
@@ -97,12 +96,13 @@ struct SaveGameHeader {
TimeDate dateTime;
bool scnFlag;
byte language;
+ uint16 numInterpreters; // Savegame version 2 or later only
};
enum {
DW1_SAVEGAME_ID = 0x44575399, // = 'DWSc' = "DiscWorld 1 ScummVM"
DW2_SAVEGAME_ID = 0x44573253, // = 'DW2S' = "DiscWorld 2 ScummVM"
- SAVEGAME_HEADER_SIZE = 4 + 4 + 4 + SG_DESC_LEN + 7 + 1 + 1
+ SAVEGAME_HEADER_SIZE = 4 + 4 + 4 + SG_DESC_LEN + 7 + 1 + 1 + 2
};
#define SAVEGAME_ID (TinselV2 ? (uint32)DW2_SAVEGAME_ID : (uint32)DW1_SAVEGAME_ID)
@@ -186,6 +186,15 @@ static bool syncSaveGameHeader(Common::Serializer &s, SaveGameHeader &hdr) {
}
}
+ // Handle the number of interpreter contexts that will be saved in the savegame
+ if (tmp >= 2) {
+ tmp -= 2;
+ hdr.numInterpreters = NUM_INTERPRET;
+ s.syncAsUint16LE(hdr.numInterpreters);
+ } else {
+ hdr.numInterpreters = (TinselV2 ? 70 : 64) - 20;
+ }
+
// Skip over any extra bytes
s.skip(tmp);
return true;
@@ -262,7 +271,7 @@ static void syncSoundReel(Common::Serializer &s, SOUNDREELS &sr) {
s.syncAsSint32LE(sr.actorCol);
}
-static void syncSavedData(Common::Serializer &s, SAVED_DATA &sd) {
+static void syncSavedData(Common::Serializer &s, SAVED_DATA &sd, int numInterp) {
s.syncAsUint32LE(sd.SavedSceneHandle);
s.syncAsUint32LE(sd.SavedBgroundHandle);
for (int i = 0; i < MAX_MOVERS; ++i)
@@ -273,7 +282,7 @@ static void syncSavedData(Common::Serializer &s, SAVED_DATA &sd) {
s.syncAsSint32LE(sd.NumSavedActors);
s.syncAsSint32LE(sd.SavedLoffset);
s.syncAsSint32LE(sd.SavedToffset);
- for (int i = 0; i < NUM_INTERPRET; ++i)
+ for (int i = 0; i < numInterp; ++i)
sd.SavedICInfo[i].syncWithSerializer(s);
for (int i = 0; i < MAX_POLY; ++i)
s.syncAsUint32LE(sd.SavedDeadPolys[i]);
@@ -422,7 +431,7 @@ char *ListEntry(int i, letype which) {
return NULL;
}
-static void DoSync(Common::Serializer &s) {
+static bool DoSync(Common::Serializer &s, int numInterp) {
int sg = 0;
if (TinselV2) {
@@ -434,7 +443,7 @@ static void DoSync(Common::Serializer &s) {
if (TinselV2 && s.isLoading())
HoldItem(INV_NOICON);
- syncSavedData(s, *g_srsd);
+ syncSavedData(s, *g_srsd, numInterp);
syncGlobInfo(s); // Glitter globals
syncInvInfo(s); // Inventory data
@@ -443,6 +452,10 @@ static void DoSync(Common::Serializer &s) {
sg = WhichItemHeld();
s.syncAsSint32LE(sg);
if (s.isLoading()) {
+ if (sg != -1 && !GetIsInvObject(sg))
+ // Not a valid inventory object, so return false
+ return false;
+
if (TinselV2)
g_thingHeld = sg;
else
@@ -459,7 +472,7 @@ static void DoSync(Common::Serializer &s) {
if (*g_SaveSceneSsCount != 0) {
SAVED_DATA *sdPtr = g_SaveSceneSsData;
for (int i = 0; i < *g_SaveSceneSsCount; ++i, ++sdPtr)
- syncSavedData(s, *sdPtr);
+ syncSavedData(s, *sdPtr, numInterp);
// Flag that there is a saved scene to return to. Note that in this context 'saved scene'
// is a stored scene to return to from another scene, such as from the Summoning Book close-up
@@ -469,6 +482,8 @@ static void DoSync(Common::Serializer &s) {
if (!TinselV2)
syncAllActorsAlive(s);
+
+ return true;
}
/**
@@ -487,8 +502,23 @@ static bool DoRestore() {
delete f; // Invalid header, or savegame too new -> skip it
return false;
}
+
+ // Load in the data. For older savegame versions, we potentially need to load the data twice, once
+ // for pre 1.5 savegames, and if that fails, a second time for 1.5 savegames
+ int numInterpreters = hdr.numInterpreters;
+ int32 currentPos = f->pos();
+ for (int tryNumber = 0; tryNumber < ((hdr.ver >= 2) ? 1 : 2); ++tryNumber) {
+ // If it's the second loop iteration, try with the 1.5 savegame number of interpreter contexts
+ if (tryNumber == 1) {
+ f->seek(currentPos);
+ numInterpreters = 80;
+ }
- DoSync(s);
+ // Load the savegame data
+ if (DoSync(s, numInterpreters))
+ // Data load was successful (or likely), so break out of loop
+ break;
+ }
uint32 id = f->readSint32LE();
if (id != (uint32)0xFEEDFACE)
@@ -575,7 +605,7 @@ static void DoSave() {
return;
}
- DoSync(s);
+ DoSync(s, hdr.numInterpreters);
// Write out the special Id for Discworld savegames
f->writeUint32LE(0xFEEDFACE);
More information about the Scummvm-git-logs
mailing list