[Scummvm-cvs-logs] SF.net SVN: scummvm:[33293] residual/trunk/engine

aquadran at users.sourceforge.net aquadran at users.sourceforge.net
Sat Jul 26 00:21:05 CEST 2008


Revision: 33293
          http://scummvm.svn.sourceforge.net/scummvm/?rev=33293&view=rev
Author:   aquadran
Date:     2008-07-25 22:21:04 +0000 (Fri, 25 Jul 2008)

Log Message:
-----------
make savegames portable, still have some bugs, WIP

Modified Paths:
--------------
    residual/trunk/engine/engine.cpp
    residual/trunk/engine/engine.h
    residual/trunk/engine/imuse/imuse.cpp
    residual/trunk/engine/lua/lrestore.cpp
    residual/trunk/engine/lua/lsave.cpp
    residual/trunk/engine/lua/lua.h
    residual/trunk/engine/lua.cpp
    residual/trunk/engine/savegame.cpp
    residual/trunk/engine/savegame.h

Modified: residual/trunk/engine/engine.cpp
===================================================================
--- residual/trunk/engine/engine.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/engine.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -464,14 +464,30 @@
 	}
 }
 
-void Engine::savegameRead(void *data, int size) {
+void Engine::savegameReadStream(void *data, int32 size) {
 	g_engine->_savedState->read(data, size);
 }
 
-void Engine::savegameWrite(void *data, int size) {
+void Engine::savegameWriteStream(void *data, int32 size) {
 	g_engine->_savedState->write(data, size);
 }
 
+int32 Engine::savegameReadSint32() {
+	return g_engine->_savedState->readLESint32();
+}
+
+void Engine::savegameWriteSint32(int32 val) {
+	g_engine->_savedState->writeLESint32(val);
+}
+
+uint32 Engine::savegameReadUint32() {
+	return g_engine->_savedState->readLEUint32();
+}
+
+void Engine::savegameWriteUint32(uint32 val) {
+	g_engine->_savedState->writeLEUint32(val);
+}
+
 void Engine::savegameRestore() {
 	printf("Engine::savegameRestore() started.\n");
 	_savegameLoadRequest = false;
@@ -502,7 +518,7 @@
 	//Smush_Restore(_savedState);
 	g_imuse->restoreState(_savedState);
 	_savedState->beginSection('LUAS');
-	lua_Restore(savegameRead);
+	lua_Restore(savegameReadStream, savegameReadSint32, savegameReadUint32);
 	_savedState->endSection();
 	//  unlock resources
 	delete _savedState;
@@ -566,7 +582,7 @@
 	//Smush_Save(_savedState);
 	g_imuse->saveState(_savedState);
 	_savedState->beginSection('LUAS');
-	lua_Save(savegameWrite);
+	lua_Save(savegameWriteStream, savegameWriteSint32, savegameWriteUint32);
 	_savedState->endSection();
 
 	delete _savedState;

Modified: residual/trunk/engine/engine.h
===================================================================
--- residual/trunk/engine/engine.h	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/engine.h	2008-07-25 22:21:04 UTC (rev 33293)
@@ -168,8 +168,13 @@
 	void savegameSave();
 	void savegameRestore();
 	void savegameCallback();
-	static void savegameRead(void *data, int size);
-	static void savegameWrite(void *data, int size);
+	static void savegameReadStream(void *data, int32 size);
+	static void savegameWriteStream(void *data, int32 size);
+	static int32 savegameReadSint32();
+	static void savegameWriteSint32(int32 val);
+	static uint32 savegameReadUint32();
+	static void savegameWriteUint32(uint32 val);
+
 	void storeSaveGameImage(SaveGame *savedState);
 
 	bool _savegameLoadRequest;

Modified: residual/trunk/engine/imuse/imuse.cpp
===================================================================
--- residual/trunk/engine/imuse/imuse.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/imuse/imuse.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -88,33 +88,35 @@
 	printf("Imuse::restoreState() started.\n");
 
 	savedState->beginSection('IMUS');
-	savedState->read(&_curMusicState, sizeof(int32));
-	savedState->read(&_curMusicSeq, sizeof(int32));
-	savedState->read(_attributes, sizeof(int32) * 185);
+	_curMusicState = savedState->readLESint32();
+	_curMusicSeq = savedState->readLESint32();
+	for (int r = 0; r < 185; r++) {
+		_attributes[r] = savedState->readLESint32();
+	}
 
 	for (int l = 0; l < MAX_IMUSE_TRACKS + MAX_IMUSE_FADETRACKS; l++) {
 		Track *track = _track[l];
 		memset(track, 0, sizeof(Track));
 		track->trackId = l;
-		savedState->read(&track->pan, sizeof(int32));
-		savedState->read(&track->panFadeDest, sizeof(int32));
-		savedState->read(&track->panFadeDelay, sizeof(int32));
-		savedState->read(&track->panFadeUsed, sizeof(bool));
-		savedState->read(&track->vol, sizeof(int32));
-		savedState->read(&track->volFadeDest, sizeof(int32));
-		savedState->read(&track->volFadeDelay, sizeof(int32));
-		savedState->read(&track->volFadeUsed, sizeof(bool));
+		track->pan = savedState->readLESint32();
+		track->panFadeDest = savedState->readLESint32();
+		track->panFadeDelay = savedState->readLESint32();
+		track->panFadeUsed = savedState->readLEBool();
+		track->vol = savedState->readLESint32();
+		track->volFadeDest = savedState->readLESint32();
+		track->volFadeDelay = savedState->readLESint32();
+		track->volFadeUsed = savedState->readLEBool();
 		savedState->read(track->soundName, 32);
-		savedState->read(&track->used, sizeof(bool));
-		savedState->read(&track->toBeRemoved, sizeof(bool));
-		savedState->read(&track->priority, sizeof(int32));
-		savedState->read(&track->regionOffset, sizeof(int32));
-		savedState->read(&track->dataOffset, sizeof(int32));
-		savedState->read(&track->curRegion, sizeof(int32));
-		savedState->read(&track->curHookId, sizeof(int32));
-		savedState->read(&track->volGroupId, sizeof(int32));
-		savedState->read(&track->feedSize, sizeof(int32));
-		savedState->read(&track->mixerFlags, sizeof(int32));
+		track->used = savedState->readLEBool();
+		track->toBeRemoved = savedState->readLEBool();
+		track->priority = savedState->readLESint32();
+		track->regionOffset = savedState->readLESint32();
+		track->dataOffset = savedState->readLESint32();
+		track->curRegion = savedState->readLESint32();
+		track->curHookId = savedState->readLESint32();
+		track->volGroupId = savedState->readLESint32();
+		track->feedSize = savedState->readLESint32();
+		track->mixerFlags = savedState->readLESint32();
 
 		if (!track->used)
 			continue;
@@ -152,31 +154,33 @@
 	printf("Imuse::saveState() started.\n");
 
 	savedState->beginSection('IMUS');
-	savedState->write(&_curMusicState, sizeof(int32));
-	savedState->write(&_curMusicSeq, sizeof(int32));
-	savedState->write(_attributes, sizeof(int32) * 185);
+	savedState->writeLESint32(_curMusicState);
+	savedState->writeLESint32(_curMusicSeq);
+	for (int r = 0; r < 185; r++) {
+		savedState->writeLESint32(_attributes[r]);
+	}
 
 	for (int l = 0; l < MAX_IMUSE_TRACKS + MAX_IMUSE_FADETRACKS; l++) {
 		Track *track = _track[l];
-		savedState->write(&track->pan, sizeof(int32));
-		savedState->write(&track->panFadeDest, sizeof(int32));
-		savedState->write(&track->panFadeDelay, sizeof(int32));
-		savedState->write(&track->panFadeUsed, sizeof(bool));
-		savedState->write(&track->vol, sizeof(int32));
-		savedState->write(&track->volFadeDest, sizeof(int32));
-		savedState->write(&track->volFadeDelay, sizeof(int32));
-		savedState->write(&track->volFadeUsed, sizeof(bool));
+		savedState->writeLESint32(track->pan);
+		savedState->writeLESint32(track->panFadeDest);
+		savedState->writeLESint32(track->panFadeDelay);
+		savedState->writeLEBool(track->panFadeUsed);
+		savedState->writeLESint32(track->vol);
+		savedState->writeLESint32(track->volFadeDest);
+		savedState->writeLESint32(track->volFadeDelay);
+		savedState->writeLEBool(track->volFadeUsed);
 		savedState->write(track->soundName, 32);
-		savedState->write(&track->used, sizeof(bool));
-		savedState->write(&track->toBeRemoved, sizeof(bool));
-		savedState->write(&track->priority, sizeof(int32));
-		savedState->write(&track->regionOffset, sizeof(int32));
-		savedState->write(&track->dataOffset, sizeof(int32));
-		savedState->write(&track->curRegion, sizeof(int32));
-		savedState->write(&track->curHookId, sizeof(int32));
-		savedState->write(&track->volGroupId, sizeof(int32));
-		savedState->write(&track->feedSize, sizeof(int32));
-		savedState->write(&track->mixerFlags, sizeof(int32));
+		savedState->writeLEBool(track->used);
+		savedState->writeLEBool(track->toBeRemoved);
+		savedState->writeLESint32(track->priority);
+		savedState->writeLESint32(track->regionOffset);
+		savedState->writeLESint32(track->dataOffset);
+		savedState->writeLESint32(track->curRegion);
+		savedState->writeLESint32(track->curHookId);
+		savedState->writeLESint32(track->volGroupId);
+		savedState->writeLESint32(track->feedSize);
+		savedState->writeLESint32(track->mixerFlags);
 	}
 	savedState->endSection();
 	printf("Imuse::saveState() finished.\n");

Modified: residual/trunk/engine/lua/lrestore.cpp
===================================================================
--- residual/trunk/engine/lua/lrestore.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/lua/lrestore.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -9,21 +9,132 @@
 #include "lstring.h"
 #include "lua.h"
 
-SaveRestoreCallback restoreCallback = NULL;
+#include "common/endian.h"
 
+RestoreCallback restoreCallbackPtr = NULL;
+
+static void restoreObjectValue(TObject *object, RestoreSint32 restoreSint32, RestoreUint32 restoreUint32) {
+	object->ttype = (lua_Type)restoreSint32();
+
+	switch (object->ttype) {
+		case LUA_T_NUMBER:
+		case LUA_T_TASK:
+			{
+				byte *udata = (byte *)(&object->value.n);
+				uint32 v = restoreUint32();
+				restoreUint32();
+#if defined(SYSTEM_LITTLE_ENDIAN)
+				byte b[4];
+				*(uint32 *)&b = v;
+				udata[0] = b[3];
+				udata[1] = b[2];
+				udata[2] = b[1];
+				udata[3] = b[0];
+#else
+				memcpy(&udata, v, 4);
+#endif
+			}
+			break;
+		case LUA_T_NIL:
+			{
+				restoreUint32();
+				restoreUint32();
+				object->value.ts = NULL;
+			}
+			break;
+		case LUA_T_ARRAY:
+			{
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.a = (Hash *)makePointerFromId(ptr);
+			}
+			break;
+		case LUA_T_USERDATA:
+		case LUA_T_STRING:
+			{
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.ts = (TaggedString *)makePointerFromId(ptr);
+			}
+			break;
+		case LUA_T_PROTO:
+		case LUA_T_PMARK:
+			{
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.tf = (TProtoFunc *)makePointerFromId(ptr);
+			}
+			break;
+		case LUA_T_CPROTO:
+		case LUA_T_CMARK:
+			{
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.f = (lua_CFunction)makePointerFromId(ptr);
+			}
+			break;
+		case LUA_T_CLOSURE:
+		case LUA_T_CLMARK:
+			{
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.cl = (Closure *)makePointerFromId(ptr);
+			}
+			break;
+		case LUA_T_LINE:
+			{
+				object->value.i = restoreSint32();
+				restoreSint32();
+			}
+			break;
+		case MKID_BE('ACTR'):
+		case MKID_BE('COLR'):
+		case MKID_BE('STAT'):
+		case MKID_BE('FONT'):
+		case MKID_BE('VBUF'):
+		case MKID_BE('PRIM'):
+		case MKID_BE('TEXT'):
+			{ // TODO
+				PointerId ptr;
+				ptr.low = restoreUint32();
+				ptr.hi = restoreUint32();
+				object->value.ts = (TaggedString *)makePointerFromId(ptr);
+			}
+			break;
+		default:
+			lua_error("saveObjectValue: Unsupported object type");
+	}
+}
+
 struct ArrayIDObj {
 	void *object;
-	int32 idObj;
+	PointerId idObj;
 };
 
 static int32 sortCallback(const void *id1, const void *id2) {
-	if (((ArrayIDObj *)id1)->idObj > ((ArrayIDObj *)id2)->idObj) {
+#ifdef TARGET_64BITS
+	uint64 p1 = ((ArrayIDObj *)id1)->idObj.low | (uint64)(((ArrayIDObj *)id1)->idObj.hi << 32)
+	uint64 p2 = ((ArrayIDObj *)id1)->idObj.low | (uint64)(((ArrayIDObj *)id1)->idObj.hi << 32)
+	if (p1 > p2) {
 		return 1;
-	} else if (((ArrayIDObj *)id1)->idObj < ((ArrayIDObj *)id2)->idObj) {
+	} else if (p1 < p2) {
 		return -1;
 	} else {
 		return 0;
+#else
+	if (((ArrayIDObj *)id1)->idObj.low > ((ArrayIDObj *)id2)->idObj.low) {
+		return 1;
+	} else if (((ArrayIDObj *)id1)->idObj.low < ((ArrayIDObj *)id2)->idObj.low) {
+		return -1;
+	} else {
+		return 0;
 	}
+#endif
 }
 
 int32 arrayHashTablesCount = 0;
@@ -38,23 +149,31 @@
 
 static void recreateObj(TObject *obj) {
 	if (obj->ttype == LUA_T_CPROTO) {
-		unsigned long some = ((unsigned long)(obj->value.f)) >> 16;
+#ifdef TARGET_64BITS
+		uint64 id = ((uint64)(obj->value.f)) >> 16;
+#else
+		uint32 id = ((uint32)(obj->value.f)) >> 16;
+#endif
 		luaL_libList *list = list_of_libs;
-		while (list != NULL) {
-			if (some == 0)
+		while (list) {
+			if (id == 0)
 				break;
-			some--;
+			id--;
 			list = list->next;
 		}
 
-		long numberFunc = (long)(obj->value.f) & 0xffff;
-		if ((list != NULL) && (some == 0) && (numberFunc < list->number)) {
+#ifdef TARGET_64BITS
+		int32 numberFunc = (uint64)(obj->value.f) & 0xffff;
+#else
+		int32 numberFunc = (uint32)(obj->value.f) & 0xffff;
+#endif
+		if (list && id == 0 && numberFunc < list->number) {
 			obj->value.f = list->list[numberFunc].func;
 		} else {
 			obj->value.f = NULL;
 			assert(obj->value.f);
 		}
-	} else if ((obj->ttype == LUA_T_NIL) || (obj->ttype == LUA_T_LINE) || (obj->ttype == LUA_T_NUMBER) ) {
+	} else if (obj->ttype == LUA_T_NIL || obj->ttype == LUA_T_LINE || obj->ttype == LUA_T_NUMBER) {
 		return;
 	} else {
 		if (obj->value.i == 0)
@@ -70,83 +189,98 @@
 
 		ArrayIDObj *found;
 		ArrayIDObj tmpId;
-
-		tmpId.idObj = obj->value.i;
 		tmpId.object = NULL;
-		obj->value.i = 0;
 
 		switch (obj->ttype) {
 		case LUA_T_PMARK:
+			tmpId.idObj = makeIdFromPointer(obj->value.tf);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayProtoFuncs, arrayProtoFuncsCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.tf = (TProtoFunc *)found->object;
 			break;
 		case LUA_T_USERDATA:
+			tmpId.idObj = makeIdFromPointer(obj->value.ts);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayStrings, arrayStringsCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.ts = (TaggedString *)found->object;
 			break;
 		case LUA_T_PROTO:
+			tmpId.idObj = makeIdFromPointer(obj->value.tf);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayProtoFuncs, arrayProtoFuncsCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.tf = (TProtoFunc *)found->object;
 			break;
 		case LUA_T_CLOSURE:
+			tmpId.idObj = makeIdFromPointer(obj->value.cl);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayClosures, arrayClosuresCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.cl = (Closure *)found->object;
 			break;
 		case LUA_T_ARRAY:
+			tmpId.idObj = makeIdFromPointer(obj->value.a);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayHashTables, arrayHashTablesCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.a = (Hash *)found->object;
 			break;
 		case LUA_T_STRING:
+			tmpId.idObj = makeIdFromPointer(obj->value.ts);
 			found = (ArrayIDObj *)bsearch(&tmpId, arrayStrings, arrayStringsCount, sizeof(ArrayIDObj), sortCallback);
+			assert(found);
+			obj->value.ts = (TaggedString *)found->object;
 			break;
 		default:
+			obj->value.i = 0;
+			obj->value.ts = 0;
 			return;
 		}
-
-		//obj->value.i = (int32)found->object;
 	}
 }
 
-void lua_Restore(SaveRestoreFunc restoreFunc) {
+void lua_Restore(RestoreStream restoreStream, RestoreSint32 restoreSint32, RestoreUint32 restoreUint32) {
 	printf("lua_Restore() started.\n");
-/*
+
 	lua_close();
 	L = luaM_new(lua_State);
 	lua_resetglobals();
 
-	restoreFunc(&arrayStringsCount, sizeof(int32));
-	restoreFunc(&arrayClosuresCount, sizeof(int32));
-	restoreFunc(&arrayHashTablesCount, sizeof(int32));
-	restoreFunc(&arrayProtoFuncsCount, sizeof(int32));
-	int32 rootGlobalCount;
-	restoreFunc(&rootGlobalCount, sizeof(int32));
+	arrayStringsCount = restoreSint32();
+	arrayClosuresCount = restoreSint32();
+	arrayHashTablesCount = restoreSint32();
+	arrayProtoFuncsCount = restoreSint32();
+	int32 rootGlobalCount = restoreSint32();
 
 	arrayStrings = (ArrayIDObj *)luaM_malloc(sizeof(ArrayIDObj) * arrayStringsCount);
 	ArrayIDObj *arraysObj = arrayStrings;
 	int32 maxStringsLength;
-	restoreFunc(&maxStringsLength, sizeof(int32));
+	maxStringsLength = restoreSint32();
 	char *tempStringBuffer = (char *)luaM_malloc(maxStringsLength);
 
 	int32 i;
 	for (i = 0; i < arrayStringsCount; i++) {
-		restoreFunc(&arraysObj->idObj, sizeof(int32));
-		int32 constIndex;
-		restoreFunc(&constIndex, sizeof(int32));
-		lua_Type tag;
-		restoreFunc(&tag, sizeof(int32));
-		void *value;
-		restoreFunc(&value, sizeof(void *));
+		arraysObj->idObj.low = restoreSint32();
+		arraysObj->idObj.hi = restoreSint32();
+		int32 constIndex = restoreSint32();
+		lua_Type tag = (lua_Type)restoreSint32();
+		PointerId ptr;
+		ptr.low = restoreUint32();
+		ptr.hi = restoreUint32();
 
 		TaggedString *tempString;
 		if (constIndex != -1) {
-			int32 length;
-			restoreFunc(&length, sizeof(int32));
-			restoreFunc(tempStringBuffer, length);
+			int32 length = restoreSint32();
+			restoreStream(tempStringBuffer, length);
 			tempString = luaS_newlstr(tempStringBuffer, length);
 			tempString->u.s.globalval.ttype = tag;
-			tempString->u.s.globalval.value.ts = (TaggedString *)value;
+			tempString->u.s.globalval.value.ts = (TaggedString *)makePointerFromId(ptr);
 		} else {
 			if (tag == 0)
-				tempString = luaS_createudata(value, LUA_ANYTAG);
+				tempString = luaS_createudata((void *)makePointerFromId(ptr), LUA_ANYTAG);
 			else
-				tempString = luaS_createudata(value, tag);
-			if (restoreCallback != NULL) {
-				tempString->u.s.globalval.value.ts = (TaggedString *)restoreCallback(tempString->u.s.globalval.ttype, (int32)tempString->u.s.globalval.value.ts, restoreFunc);
+				tempString = luaS_createudata((void *)makePointerFromId(ptr), tag);
+			if (restoreCallbackPtr) {
+				PointerId ptr = makeIdFromPointer(tempString->u.s.globalval.value.ts);
+				ptr = restoreCallbackPtr(tempString->u.s.globalval.ttype, ptr, restoreSint32);
+				tempString->u.s.globalval.value.ts = (TaggedString *)makePointerFromId(ptr);
 			}
 		}
 		tempString->constindex = constIndex;
@@ -160,16 +294,15 @@
 	arraysObj = (ArrayIDObj *)luaM_malloc(sizeof(ArrayIDObj) * arrayClosuresCount);
 	arrayClosures = arraysObj;
 	for (i = 0; i < arrayClosuresCount; i++) {
-		restoreFunc(&arraysObj->idObj, sizeof(int32));
-		int32 countElements;
-		restoreFunc(&countElements, sizeof(int32));
+		arraysObj->idObj.low = restoreSint32();
+		arraysObj->idObj.hi = restoreSint32();
+		int32 countElements = restoreSint32();
 		tempClosure = (Closure *)luaM_malloc((countElements * sizeof(TObject)) + sizeof(Closure));
 		luaO_insertlist(&L->rootcl, (GCnode *)tempClosure);
 
 		tempClosure->nelems = countElements;
 		for (l = 0; l <= tempClosure->nelems; l++) {
-			restoreFunc(&tempClosure->consts[l].ttype, sizeof(lua_Type));
-			restoreFunc(&tempClosure->consts[l].value, sizeof(Value));
+			restoreObjectValue(&tempClosure->consts[l], restoreSint32, restoreUint32);
 		}
 		arraysObj->object = tempClosure;
 		arraysObj++;
@@ -179,19 +312,18 @@
 	arraysObj = (ArrayIDObj *)luaM_malloc(sizeof(ArrayIDObj) * arrayHashTablesCount);
 	arrayHashTables = arraysObj;
 	for (i = 0; i < arrayHashTablesCount; i++) {
-		restoreFunc(&arraysObj->idObj, sizeof(int32));
+		arraysObj->idObj.low = restoreSint32();
+		arraysObj->idObj.hi = restoreSint32();
 		tempHash = luaM_new(Hash);
-		restoreFunc(&tempHash->nhash, sizeof(int32));
-		restoreFunc(&tempHash->nuse, sizeof(int32));
-		restoreFunc(&tempHash->htag, sizeof(int32));
+		tempHash->nhash = restoreSint32();
+		tempHash->nuse = restoreSint32();
+		tempHash->htag = restoreSint32();
 		tempHash->node = hashnodecreate(tempHash->nhash);
 		luaO_insertlist(&L->roottable, (GCnode *)tempHash);
 
 		for (l = 0; l < tempHash->nuse; l++) {
-			restoreFunc(&tempHash->node[l].ref.ttype, sizeof(lua_Type));
-			restoreFunc(&tempHash->node[l].ref.value, sizeof(Value));
-			restoreFunc(&tempHash->node[l].val.ttype, sizeof(lua_Type));
-			restoreFunc(&tempHash->node[l].val.value, sizeof(Value));
+			restoreObjectValue(&tempHash->node[l].ref, restoreSint32, restoreUint32);
+			restoreObjectValue(&tempHash->node[l].val, restoreSint32, restoreUint32);
 		}
 		arraysObj->object = tempHash;
 		arraysObj++;
@@ -201,36 +333,40 @@
 	arrayProtoFuncs = (ArrayIDObj *)luaM_malloc(sizeof(ArrayIDObj) * arrayProtoFuncsCount);
 	arraysObj = arrayProtoFuncs;
 	for (i = 0; i < arrayProtoFuncsCount; i++) {
-		restoreFunc(&arraysObj->idObj, sizeof(int32));
+		arraysObj->idObj.low = restoreSint32();
+		arraysObj->idObj.hi = restoreSint32();
 		tempProtoFunc = luaM_new(TProtoFunc);
 		luaO_insertlist(&L->rootproto, (GCnode *)tempProtoFunc);
-		restoreFunc(&tempProtoFunc->fileName, sizeof(TaggedString *));
-		restoreFunc(&tempProtoFunc->lineDefined, sizeof(int32));
-		restoreFunc(&tempProtoFunc->nconsts, sizeof(int32));
+		PointerId ptr;
+		ptr.low = restoreSint32();
+		ptr.hi = restoreSint32();
+		tempProtoFunc->fileName = (TaggedString *)makePointerFromId(ptr);
+		tempProtoFunc->lineDefined = restoreSint32();
+		tempProtoFunc->nconsts = restoreSint32();
 		tempProtoFunc->consts = (TObject *)luaM_malloc(tempProtoFunc->nconsts * sizeof(TObject));
 
 		for (l = 0; l < tempProtoFunc->nconsts; l++) {
-			restoreFunc(&tempProtoFunc->consts[l].ttype, sizeof(lua_Type));
-			restoreFunc(&tempProtoFunc->consts[l].value, sizeof(Value));
+			restoreObjectValue(&tempProtoFunc->consts[l], restoreSint32, restoreUint32);
 		}
 
-		int32 countVariables;
-		restoreFunc(&countVariables, sizeof(int32));
-		if (countVariables != 0) {
+		int32 countVariables = restoreSint32();
+		if (countVariables) {
 			tempProtoFunc->locvars = (LocVar *)luaM_malloc(countVariables * sizeof(LocVar));
 		} else {
 			tempProtoFunc->locvars = NULL;
 		}
 
 		for (l = 0; l < countVariables; l++) {
-			restoreFunc(&tempProtoFunc->locvars[l].varname, sizeof(TaggedString *));
-			restoreFunc(&tempProtoFunc->locvars[l].line, sizeof(int32));
+			PointerId ptr;
+			ptr.low = restoreSint32();
+			ptr.hi = restoreSint32();
+			tempProtoFunc->locvars[l].varname = (TaggedString *)makePointerFromId(ptr);
+			tempProtoFunc->locvars[l].line = restoreSint32();
 		}
 
-		int32 codeSize;
-		restoreFunc(&codeSize, sizeof(int32));
+		int32 codeSize = restoreSint32();
 		tempProtoFunc->code = (lua_Byte *)luaM_malloc(codeSize);
-		restoreFunc(tempProtoFunc->code, codeSize);
+		restoreStream(tempProtoFunc->code, codeSize);
 		arraysObj->object = tempProtoFunc;
 		arraysObj++;
 	}
@@ -239,14 +375,14 @@
 		stringtable *tempStringTable = &L->string_root[i];
 		for (l = 0; l < tempStringTable->size; l++) {
 			TaggedString *tempString = tempStringTable->hash[l];
-			if ((tempString != NULL) && (tempString->constindex != -1) && (tempString != &EMPTY)) {
+			if (tempString && tempString->constindex != -1 && tempString != &EMPTY) {
 				recreateObj(&tempString->u.s.globalval);
 			}
 		}
 	}
 
 	tempProtoFunc = (TProtoFunc *)L->rootproto.next;
-	while (tempProtoFunc != NULL) {
+	while (tempProtoFunc) {
 		TObject tempObj;
 		tempObj.value.ts = (TaggedString *)tempProtoFunc->fileName;
 		tempObj.ttype = LUA_T_STRING;
@@ -271,7 +407,7 @@
 	}
 
 	tempHash = (Hash *)L->roottable.next;
-	while (tempHash != NULL) {
+	while (tempHash) {
 		for (i = 0; i < tempHash->nuse; i++) {
 			recreateObj(&tempHash->node[i].ref);
 			recreateObj(&tempHash->node[i].val);
@@ -280,7 +416,7 @@
 		tempHash->node = hashnodecreate(tempHash->nhash);
 		for (i = 0; i < tempHash->nuse; i++) {
 			Node *newNode = oldNode + i;
-			if ((newNode->val.ttype != LUA_T_NIL) && (newNode->ref.ttype != LUA_T_NIL)) {
+			if (newNode->ref.ttype != LUA_T_NIL && newNode->val.ttype != LUA_T_NIL) {
 				*node(tempHash, present(tempHash, &newNode->ref)) = *newNode;
 			}
 		}
@@ -289,7 +425,7 @@
 	}
 
 	tempClosure = (Closure *)L->rootcl.next;
-	while (tempClosure != NULL) {
+	while (tempClosure) {
 		for (i = 0; i <= tempClosure->nelems; i++) {
 			recreateObj(&tempClosure->consts[i]);
 		}
@@ -301,7 +437,10 @@
 		TObject tempObj;
 		TaggedString *tempString = NULL;
 		tempObj.ttype = LUA_T_STRING;
-		restoreFunc(&tempObj.value, sizeof(TaggedString *));
+		PointerId ptr;
+		ptr.low = restoreSint32();
+		ptr.hi = restoreSint32();
+		tempObj.value.ts = (TaggedString *)makePointerFromId(ptr);
 		recreateObj(&tempObj);
  		tempString = (TaggedString *)tempObj.value.ts;
 		assert(tempString);
@@ -310,81 +449,74 @@
 	}
 	tempListString->head.next = NULL;
 
-	restoreFunc(&L->errorim.ttype, sizeof(lua_Type));
-	restoreFunc(&L->errorim.value, sizeof(Value));
+	restoreObjectValue(&L->errorim, restoreSint32, restoreUint32);
 	recreateObj(&L->errorim);
 
-	restoreFunc(&L->IMtable_size, sizeof(int32));
+	L->IMtable_size = restoreSint32();
 	L->IMtable = (IM *)luaM_malloc(L->IMtable_size * sizeof(IM));
 	for (i = 0; i < L->IMtable_size; i++) {
 		IM *im = &L->IMtable[i];
 		for (l = 0; l < IM_N; l++) {
-			restoreFunc(&im->int_method[l].ttype, sizeof(lua_Type));
-			restoreFunc(&im->int_method[l].value, sizeof(Value));
+			restoreObjectValue(&im->int_method[l], restoreSint32, restoreUint32);
 			recreateObj(&im->int_method[l]);
 		}
 	}
 
-	restoreFunc(&L->last_tag, sizeof(int32));
-	restoreFunc(&L->refSize, sizeof(int32));
+	L->last_tag = restoreSint32();
+	L->refSize = restoreSint32();
 	L->refArray = (ref *)luaM_malloc(L->refSize * sizeof(ref));
 	for (i = 0; i < L->refSize; i++) {
-		restoreFunc(&L->refArray[i].o.ttype, sizeof(lua_Type));
-		restoreFunc(&L->refArray[i].o.value, sizeof(Value));
+		restoreObjectValue(&L->refArray[i].o, restoreSint32, restoreUint32);
 		recreateObj(&L->refArray[i].o);
-		restoreFunc(&L->refArray[i].status, sizeof(Status));
+		L->refArray[i].status = (Status)restoreSint32();
 	}
 
-	restoreFunc(&L->GCthreshold, sizeof(int32));
-	restoreFunc(&L->nblocks, sizeof(int32));
+	L->GCthreshold = restoreSint32();
+	L->nblocks = restoreSint32();
 
-	restoreFunc(&L->Mbuffsize, sizeof(int32));
+	L->Mbuffsize = restoreSint32();
 	L->Mbuffer = (char *)luaM_malloc(L->Mbuffsize);
-	restoreFunc(L->Mbuffer, L->Mbuffsize);
+	restoreStream(L->Mbuffer, L->Mbuffsize);
 	int32 MbaseOffset;
-	restoreFunc(&MbaseOffset, sizeof(int32));
+	MbaseOffset = restoreSint32();
 	L->Mbuffbase = MbaseOffset + L->Mbuffer;
-	restoreFunc(&L->Mbuffnext, sizeof(int32));
+	L->Mbuffnext = restoreSint32();
 
-	restoreFunc(&globalTaskSerialId, sizeof(int32));
+	globalTaskSerialId = restoreSint32();
 
-	int32 countTasks;
 	lua_Task *tempTask = NULL;
-	restoreFunc(&countTasks, sizeof(int32));
 	lua_Task *prevTask = L->root_task;
+	int32 countTasks = restoreSint32();
 	for (l = 0; l < countTasks; l++) {
 		tempTask = luaM_new(lua_Task);
 		memset(tempTask, 0, sizeof(lua_Task));
 		prevTask->next = tempTask;
 		prevTask = tempTask;
 
-		int32 stackLastSize;
-		restoreFunc(&stackLastSize, sizeof(int32));
+		int32 stackLastSize = restoreSint32();
 		tempTask->stack.stack = (TObject *)luaM_malloc(stackLastSize * sizeof(TObject));
 		tempTask->stack.last = tempTask->stack.stack + stackLastSize - 1;
 
-		int32 stackTopSize;
-		restoreFunc(&stackTopSize, sizeof(int32));
+		int32 stackTopSize = restoreSint32();
 		tempTask->stack.top = tempTask->stack.stack + stackTopSize;
 		for (i = 0; i < stackTopSize; i++) {
-			restoreFunc(&tempTask->stack.stack[i].ttype, sizeof(lua_Type));
-			restoreFunc(&tempTask->stack.stack[i].value, sizeof(Value));
+			restoreObjectValue(&tempTask->stack.stack[i], restoreSint32, restoreUint32);
 			recreateObj(&tempTask->stack.stack[i]);
 		}
 
-		restoreFunc(&tempTask->Cstack.base, sizeof(StkId));
-		restoreFunc(&tempTask->Cstack.lua2C, sizeof(StkId));
-		restoreFunc(&tempTask->Cstack.num, sizeof(int32));
+		tempTask->Cstack.base = restoreSint32();
+		tempTask->Cstack.lua2C = restoreSint32();
+		tempTask->Cstack.num = restoreSint32();
 
-		restoreFunc(&tempTask->numCblocks, sizeof(int32));
+		tempTask->numCblocks = restoreSint32();
 		for (i = 0; i < tempTask->numCblocks; i++) {
-			restoreFunc(&tempTask->Cblocks[i].base,	sizeof(StkId));
-			restoreFunc(&tempTask->Cblocks[i].lua2C, sizeof(StkId));
-			restoreFunc(&tempTask->Cblocks[i].num, sizeof(int32));
+			tempTask->Cblocks[i].base = restoreSint32();
+			tempTask->Cblocks[i].lua2C = restoreSint32();
+			tempTask->Cblocks[i].num = restoreSint32();
 		}
 
 		int32 pcOffset, taskCi;
-		restoreFunc(&tempTask->base_ci_size, sizeof(int32));
+		tempTask->base_ci_size = restoreSint32();
 		tempTask->base_ci = (CallInfo *)luaM_malloc(tempTask->base_ci_size * sizeof(CallInfo));
 		memset(tempTask->base_ci, 0, sizeof(CallInfo) * tempTask->base_ci_size);
 		CallInfo *tempCi = tempTask->base_ci;
@@ -392,35 +524,39 @@
 		for (i = 0; i < countCi; i++) {
 			TObject tempObj;
 			tempObj.ttype = LUA_T_CLOSURE;
-			restoreFunc(&tempObj.value, sizeof(Closure *));
+			PointerId ptr;
+			ptr.low = restoreUint32();
+			ptr.hi = restoreUint32();
+			tempObj.value.cl = (Closure *)makePointerFromId(ptr);
 			recreateObj(&tempObj);
 			tempCi->c = (Closure *)tempObj.value.cl;
 			tempObj.ttype = LUA_T_PROTO;
-			restoreFunc(&tempObj.value, sizeof(TProtoFunc *));
+			ptr.low = restoreUint32();
+			ptr.hi = restoreUint32();
+			tempObj.value.tf = (TProtoFunc *)makePointerFromId(ptr);
 			recreateObj(&tempObj);
 			tempCi->tf = (TProtoFunc *)tempObj.value.tf;
 
-			restoreFunc(&pcOffset, sizeof(int32));
-			if (pcOffset != 0)
+			pcOffset = restoreSint32();
+			if (pcOffset)
 				tempCi->pc = tempCi->tf->code + pcOffset;
 			else
 				tempCi->pc = NULL;
 
-			restoreFunc(&tempCi->base, sizeof(StkId));
-			restoreFunc(&tempCi->nResults, sizeof(int32));
+			tempCi->base = restoreSint32();
+			tempCi->nResults = restoreSint32();
 			tempCi++;
 		}
-		restoreFunc(&taskCi, sizeof(int32));
+		taskCi = restoreSint32();
 		tempTask->ci = tempTask->base_ci + taskCi;
 		tempTask->end_ci = tempTask->base_ci + countCi;
 
-		int32 Mbasepos;
-		restoreFunc(&Mbasepos, sizeof(int32));
+		int32 Mbasepos = restoreSint32();
 		tempTask->Mbuffbase = Mbasepos + tempTask->Mbuffer;
-		restoreFunc(&tempTask->Mbuffnext, sizeof(int32));
+		tempTask->Mbuffnext = restoreSint32();
 
-		restoreFunc(&tempTask->Tstate, sizeof(TaskState));
-		restoreFunc(&tempTask->id, sizeof(int32));
+		tempTask->Tstate = (TaskState)restoreSint32();
+		tempTask->id = restoreSint32();
 	}
 	L->last_task = tempTask;
 
@@ -437,6 +573,6 @@
 	arrayClosures = NULL;
 	arrayProtoFuncs = NULL;
 	arrayStrings = NULL;
-*/
+
 	printf("lua_Restore() finished.\n");
 }

Modified: residual/trunk/engine/lua/lsave.cpp
===================================================================
--- residual/trunk/engine/lua/lsave.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/lua/lsave.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -7,28 +7,136 @@
 #include "lvm.h"
 #include "lopcodes.h"
 #include "lstring.h"
+#include "lua.h"
 
-SaveRestoreCallback saveCallback = NULL;
+#include "common/endian.h"
 
-static void saveObjectValue(TObject *object, SaveRestoreFunc saveFunc) {
-	saveFunc(&object->ttype, sizeof(lua_Type));
-	if (object->ttype == LUA_T_CPROTO) {
-		luaL_libList *list = list_of_libs;
-		int32 idObj = 0;
-		while (list != NULL) {
-			for (int32 l = 0; l < list->number; l++) {
-				if (list->list[l].func == object->value.f) {
-					idObj = (idObj << 16) | l;
-					saveFunc(&idObj, sizeof(int32));
-					return;
+PointerId makeIdFromPointer(void *ptr) {
+	PointerId pointer;
+
+#ifdef TARGET_64BITS
+	uint64 v = (uint64)ptr;
+	pointer.low = v & 0xffffffff;
+	pointer.hi = v >> 32;
+#else
+	pointer.low = (uint32)ptr;
+	pointer.hi = 0;
+#endif
+
+	return pointer;
+}
+
+void *makePointerFromId(PointerId ptr) {
+	void *pointer;
+
+#ifdef TARGET_64BITS
+	uint64 v = ptr.low | ((uint64)ptr.hi << 32);
+	pointer = (void *)v;
+#else
+	pointer = (void *)ptr.low;
+#endif
+
+	return pointer;
+}
+
+SaveCallback saveCallbackPtr = NULL;
+
+static void saveObjectValue(TObject *object, SaveSint32 saveSint32, SaveUint32 saveUint32) {
+	saveSint32(object->ttype);
+
+	switch (object->ttype) {
+		case LUA_T_CPROTO:
+		case LUA_T_CMARK:
+			{
+				luaL_libList *list = list_of_libs;
+				int32 idObj = 0;
+				while (list) {
+					for (int32 l = 0; l < list->number; l++) {
+						if (list->list[l].func == object->value.f) {
+							idObj = (idObj << 16) | l;
+							saveSint32(idObj);
+							saveSint32(0);
+							return;
+						}
+					}
+					list = list->next;
+					idObj++;
 				}
+				assert(0);
+				break;
 			}
-			list = list->next;
-			idObj++;
-		}
-		assert(0);
-	} else {
-		saveFunc(&object->value, sizeof(Value));
+		case LUA_T_NUMBER:
+		case LUA_T_TASK:
+			{
+				byte *udata = (byte *)(&object->value.n);
+				uint32 v;
+#if defined(SYSTEM_LITTLE_ENDIAN)
+				byte b[4];
+				b[0] = udata[3];
+				b[1] = udata[2];
+				b[2] = udata[1];
+				b[3] = udata[0];
+				v = *(uint32 *)b;
+#else
+				memcpy(&v, udata, 4);
+#endif
+				saveUint32(v);
+				saveUint32(0);
+			}
+			break;
+		case LUA_T_NIL:
+			{
+				saveUint32(0);
+				saveUint32(0);
+			}
+			break;
+		case LUA_T_ARRAY:
+			{
+				saveUint32(makeIdFromPointer(object->value.a).low);
+				saveUint32(makeIdFromPointer(object->value.a).hi);
+			}
+			break;
+		case LUA_T_USERDATA:
+		case LUA_T_STRING:
+			{
+				saveUint32(makeIdFromPointer(object->value.ts).low);
+				saveUint32(makeIdFromPointer(object->value.ts).hi);
+			}
+			break;
+		case LUA_T_PROTO:
+		case LUA_T_PMARK:
+			{
+				saveUint32(makeIdFromPointer(object->value.tf).low);
+				saveUint32(makeIdFromPointer(object->value.tf).hi);
+			}
+			break;
+		case LUA_T_CLOSURE:
+		case LUA_T_CLMARK:
+			{
+				saveUint32(makeIdFromPointer(object->value.cl).low);
+				saveUint32(makeIdFromPointer(object->value.cl).hi);
+			}
+			break;
+		case LUA_T_LINE:
+			{
+				saveSint32(object->value.i);
+				saveSint32(0);
+			}
+			break;
+		case MKID_BE('ACTR'):
+		case MKID_BE('COLR'):
+		case MKID_BE('STAT'):
+		case MKID_BE('FONT'):
+		case MKID_BE('VBUF'):
+		case MKID_BE('PRIM'):
+		case MKID_BE('TEXT'):
+			{ // TODO
+				saveUint32(makeIdFromPointer(object->value.ts).low);
+				saveUint32(makeIdFromPointer(object->value.ts).hi);
+			}
+			break;
+		default:
+			lua_error("saveObjectValue: Unsupported object type");
 	}
 }
 
@@ -48,17 +156,20 @@
 	2, 3, 2, 3, 2, 3, 2, 1, 1, 3, 2, 2, 2, 2, 3, 2, 1, 1
 };
 
-void lua_Save(SaveRestoreFunc saveFunc) {
+void lua_Save(SaveStream saveStream, SaveSint32 saveSint32, SaveUint32 saveUint32) {
 	printf("lua_Save() started.\n");
-/*
+
 	lua_collectgarbage(0);
 	int32 i, l;
 	int32 countElements = 0;
 	int32 maxStringLength = 0;
+
+
+	// Check for max length for strings and count them
 	for (i = 0; i < NUM_HASHS; i++) {
 		stringtable *tempStringTable = &L->string_root[i];
 		for (int32 l = 0; l < tempStringTable->size; l++) {
-			if ((tempStringTable->hash[l] != NULL) && (tempStringTable->hash[l] != &EMPTY)) {
+			if (tempStringTable->hash[l] && tempStringTable->hash[l] != &EMPTY) {
 				countElements++;
 				if (tempStringTable->hash[l]->constindex != -1) {
 					if (maxStringLength < tempStringTable->hash[l]->u.s.len) {
@@ -68,117 +179,132 @@
 			}
 		}
 	}
+	// save number of strings
+	saveSint32(countElements);
 
-	saveFunc(&countElements, sizeof(int32));
+
+	// save number of closures
 	countElements = 0;
-
 	GCnode *tempNode;
 	tempNode = L->rootcl.next;
-	while (tempNode != NULL) {
+	while (tempNode) {
 		countElements++;
 		tempNode = tempNode->next;
 	}
-	saveFunc(&countElements, sizeof(int32));
+	saveSint32(countElements);
+
+	// save number of tables
 	countElements = 0;
-
 	tempNode = L->roottable.next;
-	while (tempNode != NULL) {
+	while (tempNode) {
 		countElements++;
 		tempNode = tempNode->next;
 	}
-	saveFunc(&countElements, sizeof(int32));
+	saveSint32(countElements);
+
+	// save number of prototypes
 	countElements = 0;
-
 	tempNode = L->rootproto.next;
-	while (tempNode != NULL) {
+	while (tempNode) {
 		countElements++;
 		tempNode = tempNode->next;
 	}
-	saveFunc(&countElements, sizeof(int32));
+	saveSint32(countElements);
+
+	// save number of global strings
 	countElements = 0;
-
 	tempNode = L->rootglobal.next;
-	while (tempNode != NULL) {
+	while (tempNode) {
 		countElements++;
 		tempNode = tempNode->next;
 	}
-	saveFunc(&countElements, sizeof(int32));
+	saveSint32(countElements);
 
-	saveFunc(&maxStringLength, sizeof(int32));
+	// save maximum length for string
+	saveSint32(maxStringLength);
 
+	// save hash tables for strings and user data
 	TaggedString *tempString;
 	for (i = 0; i < NUM_HASHS; i++) {
 		stringtable *tempStringTable = &L->string_root[i];
 		for (l = 0; l < tempStringTable->size; l++) {
-			if ((tempStringTable->hash[l] != NULL) && (tempStringTable->hash[l] != &EMPTY)) {
+			if (tempStringTable->hash[l] && tempStringTable->hash[l] != &EMPTY) {
 				tempString = tempStringTable->hash[l];
-				saveFunc(&tempString, sizeof(TaggedString *));
-				saveFunc(&tempString->constindex, sizeof(int32));
+				saveUint32(makeIdFromPointer(tempString).low);
+				saveUint32(makeIdFromPointer(tempString).hi);
+				saveSint32(tempString->constindex);
 				if (tempString->constindex != -1) {
-					saveObjectValue(&tempString->u.s.globalval, saveFunc);
-					saveFunc(&tempString->u.s.len, sizeof(int32));
-					saveFunc(tempString->str, tempString->u.s.len);
-				}  else {
-					if (saveCallback != NULL) {
-						tempString->u.s.globalval.value.ts = (TaggedString *)saveCallback(tempString->u.s.globalval.ttype, (int32)tempString->u.s.globalval.value.ts, saveFunc);
+					saveObjectValue(&tempString->u.s.globalval, saveSint32, saveUint32);
+					saveSint32(tempString->u.s.len);
+					saveStream(tempString->str, tempString->u.s.len);
+				} else {
+					if (saveCallbackPtr) {
+						PointerId ptr = makeIdFromPointer(tempString->u.s.globalval.value.ts);
+						ptr = saveCallbackPtr(tempString->u.s.globalval.ttype, ptr, saveSint32);
+						tempString->u.s.globalval.value.ts = (TaggedString *)makePointerFromId(ptr);
 					}
-					saveObjectValue(&tempString->u.s.globalval, saveFunc);
+					saveObjectValue(&tempString->u.s.globalval, saveSint32, saveUint32);
 				}
 			}
 		}
 	}
 	
 	Closure *tempClosure = (Closure *)L->rootcl.next;
-	while (tempClosure != NULL) {
-		saveFunc(&tempClosure, sizeof(Closure *));
-		saveFunc(&tempClosure->nelems, sizeof(int32));
-		for(i = 0; i <= tempClosure->nelems; i++) {
-			saveObjectValue(&tempClosure->consts[i], saveFunc);
+	while (tempClosure) {
+		saveUint32(makeIdFromPointer(tempClosure).low);
+		saveUint32(makeIdFromPointer(tempClosure).hi);
+		saveSint32(tempClosure->nelems);
+		for (i = 0; i <= tempClosure->nelems; i++) {
+			saveObjectValue(&tempClosure->consts[i], saveSint32, saveUint32);
 		}
 		tempClosure = (Closure *)tempClosure->head.next;
 	}
 
 	Hash *tempHash = (Hash *)L->roottable.next;
-	while (tempHash != NULL) {
-		saveFunc(&tempHash, sizeof(Hash *));
-		saveFunc(&tempHash->nhash, sizeof(uint32));
+	while (tempHash) {
+		saveUint32(makeIdFromPointer(tempHash).low);
+		saveUint32(makeIdFromPointer(tempHash).hi);
+		saveSint32(tempHash->nhash);
 		int32 countUsedHash = 0;
 		for(i = 0; i < tempHash->nhash; i++) {
 			Node *newNode = &tempHash->node[i];
-			if ((newNode->ref.ttype != LUA_T_NIL) && (newNode->val.ttype != LUA_T_NIL)) {
+			if (newNode->ref.ttype != LUA_T_NIL && newNode->val.ttype != LUA_T_NIL) {
 				countUsedHash++;
 			}
 		}
-		saveFunc(&countUsedHash, sizeof(int32));
-		saveFunc(&tempHash->htag, sizeof(int32));
+		saveSint32(countUsedHash);
+		saveSint32(tempHash->htag);
 		for (i = 0; i < tempHash->nhash; i++) {
 			Node *newNode = &tempHash->node[i];
-			if ((newNode->ref.ttype != LUA_T_NIL) && (newNode->val.ttype != LUA_T_NIL)) {
-				saveObjectValue(&tempHash->node[i].ref, saveFunc);
-				saveObjectValue(&tempHash->node[i].val, saveFunc);
+			if (newNode->ref.ttype != LUA_T_NIL && newNode->val.ttype != LUA_T_NIL) {
+				saveObjectValue(&tempHash->node[i].ref, saveSint32, saveUint32);
+				saveObjectValue(&tempHash->node[i].val, saveSint32, saveUint32);
 			}
 		}
 		tempHash = (Hash *)tempHash->head.next;
 	}
 
 	TProtoFunc *tempProtoFunc = (TProtoFunc *)L->rootproto.next;
-	while (tempProtoFunc != NULL) {
-		saveFunc(&tempProtoFunc, sizeof(TProtoFunc *));
-		saveFunc(&tempProtoFunc->fileName, sizeof(TaggedString *));
-		saveFunc(&tempProtoFunc->lineDefined, sizeof(int32));
-		saveFunc(&tempProtoFunc->nconsts, sizeof(int32));
+	while (tempProtoFunc) {
+		saveUint32(makeIdFromPointer(tempProtoFunc).low);
+		saveUint32(makeIdFromPointer(tempProtoFunc).hi);
+		saveUint32(makeIdFromPointer(tempProtoFunc->fileName).low);
+		saveUint32(makeIdFromPointer(tempProtoFunc->fileName).hi);
+		saveSint32(tempProtoFunc->lineDefined);
+		saveSint32(tempProtoFunc->nconsts);
 		for (i = 0; i < tempProtoFunc->nconsts; i++) {
-			saveObjectValue(&tempProtoFunc->consts[i], saveFunc);
+			saveObjectValue(&tempProtoFunc->consts[i], saveSint32, saveUint32);
 		}
 		int32 countVariables = 0;
 		if (tempProtoFunc->locvars) {
 			for (; tempProtoFunc->locvars[countVariables++].line != -1;) { }
 		}
 
-		saveFunc(&countVariables, sizeof(int32));
+		saveSint32(countVariables);
 		for (i = 0; i < countVariables; i++) {
-			saveFunc(&tempProtoFunc->locvars[i].varname, sizeof(TaggedString *));
-			saveFunc(&tempProtoFunc->locvars[i].line, sizeof(int32));
+			saveUint32(makeIdFromPointer(tempProtoFunc->locvars[i].varname).low);
+			saveUint32(makeIdFromPointer(tempProtoFunc->locvars[i].varname).hi);
+			saveSint32(tempProtoFunc->locvars[i].line);
 		}
 
 		Byte *codePtr = tempProtoFunc->code + 2;
@@ -189,106 +315,109 @@
 			tmpPtr += opcodeSizeTable[opcodeId];
 		} while (opcodeId != ENDCODE);
 		int32 codeSize = (tmpPtr - codePtr) + 2;
-		saveFunc(&codeSize, sizeof(int32));
-		saveFunc(tempProtoFunc->code, codeSize);
+		saveSint32(codeSize);
+		saveStream(tempProtoFunc->code, codeSize);
 		tempProtoFunc = (TProtoFunc *)tempProtoFunc->head.next;
 	}
 
 	tempString = (TaggedString *)L->rootglobal.next;
-	while (tempString != NULL) {
-		saveFunc(&tempString, sizeof(TaggedString *));
+	while (tempString) {
+		saveUint32(makeIdFromPointer(tempString).low);
+		saveUint32(makeIdFromPointer(tempString).hi);
 		tempString = (TaggedString *)tempString->head.next;
 	}
 
-	saveObjectValue(&L->errorim, saveFunc);
+	saveObjectValue(&L->errorim, saveSint32, saveUint32);
 
 	IM *tempIm = L->IMtable;
-	saveFunc(&L->IMtable_size, sizeof(int32));
+	saveSint32(L->IMtable_size);
 	for (i = 0; i < L->IMtable_size; i++) {
 		for (l = 0; l < IM_N; l++) {
-			saveObjectValue(&tempIm->int_method[l], saveFunc);
+			saveObjectValue(&tempIm->int_method[l], saveSint32, saveUint32);
 		}
 		tempIm++;
 	}
 
-	saveFunc(&L->last_tag, sizeof(int32));
-	saveFunc(&L->refSize, sizeof(int32));
+	saveSint32(L->last_tag);
+	saveSint32(L->refSize);
 	for (i = 0 ; i < L->refSize; i++) {
-		saveObjectValue(&L->refArray[i].o, saveFunc);
-		saveFunc(&L->refArray[i].status, sizeof(Status));
+		saveObjectValue(&L->refArray[i].o, saveSint32, saveUint32);
+		saveSint32(L->refArray[i].status);
 	}
 
-	saveFunc(&L->GCthreshold, sizeof(int32));
-	saveFunc(&L->nblocks, sizeof(int32));
+	saveSint32(L->GCthreshold);
+	saveSint32(L->nblocks);
 
-	saveFunc(&L->Mbuffsize, sizeof(int32));
-	saveFunc(L->Mbuffer, L->Mbuffsize);
+	saveSint32(L->Mbuffsize);
+	saveStream(L->Mbuffer, L->Mbuffsize);
 	int32 MbaseOffset = L->Mbuffbase - L->Mbuffer;
-	saveFunc(&MbaseOffset, sizeof(int32));
-	saveFunc(&L->Mbuffnext, sizeof(int32));
+	saveSint32(MbaseOffset);
+	saveSint32(L->Mbuffnext);
 
-	saveFunc(&globalTaskSerialId, sizeof(int32));
+	saveSint32(globalTaskSerialId);
 
 	int32 countTasks = 0;
 	lua_Task *tempTask = L->root_task->next;
-	while (tempTask != NULL) {
+	while (tempTask) {
 		countTasks++;
 		tempTask = tempTask->next;
 	}
-	saveFunc(&countTasks, sizeof(int32));
+	saveSint32(countTasks);
 
 	tempTask = L->root_task->next;
-	while (tempTask != NULL) {
+	while (tempTask) {
 		int32 stackLastSize = (tempTask->stack.last - tempTask->stack.stack) + 1;
-		saveFunc(&stackLastSize, sizeof(int32));
+		saveSint32(stackLastSize);
 		int32 stackTopSize = tempTask->stack.top - tempTask->stack.stack;
-		saveFunc(&stackTopSize, sizeof(int32));
+		saveSint32(stackTopSize);
 		for (i = 0; i < stackTopSize; i++) {
-			saveObjectValue(&tempTask->stack.stack[i], saveFunc);
+			saveObjectValue(&tempTask->stack.stack[i], saveSint32, saveUint32);
 		}
 
-		saveFunc(&tempTask->Cstack.base, sizeof(StkId));
-		saveFunc(&tempTask->Cstack.lua2C, sizeof(StkId));
-		saveFunc(&tempTask->Cstack.num, sizeof(int32));
+		saveSint32(tempTask->Cstack.base);
+		saveSint32(tempTask->Cstack.lua2C);
+		saveSint32(tempTask->Cstack.num);
 
-		saveFunc(&tempTask->numCblocks, sizeof(int32));
+		saveSint32(tempTask->numCblocks);
 		for (i = 0; i < tempTask->numCblocks; i++) {
-			saveFunc(&tempTask->Cblocks[i].base, sizeof(StkId));
-			saveFunc(&tempTask->Cblocks[i].lua2C, sizeof(StkId));
-			saveFunc(&tempTask->Cblocks[i].num, sizeof(int32));
+			saveSint32(tempTask->Cblocks[i].base);
+			saveSint32(tempTask->Cblocks[i].lua2C);
+			saveSint32(tempTask->Cblocks[i].num);
 		}
 
 		int32 pcOffset, taskCi = -1;
-		saveFunc(&tempTask->base_ci_size, sizeof(int32));
+		saveSint32(tempTask->base_ci_size);
 		assert(tempTask->base_ci);
 		CallInfo *tempCi = tempTask->base_ci;
 		int32 countCi = tempTask->base_ci_size / sizeof(CallInfo);
 		for (i = 0; i < countCi; i++) {
-			saveFunc(&tempCi->c, sizeof(Closure *));
-			saveFunc(&tempCi->tf, sizeof(TProtoFunc *));
-			if ((tempCi->pc != NULL) && (tempTask->ci->tf != NULL))
+			saveUint32(makeIdFromPointer(tempCi->c).low);
+			saveUint32(makeIdFromPointer(tempCi->c).hi);
+			saveUint32(makeIdFromPointer(tempCi->tf).low);
+			saveUint32(makeIdFromPointer(tempCi->tf).hi);
+			if (tempCi->pc && tempTask->ci->tf)
 				pcOffset = tempCi->pc - tempCi->tf->code;
 			else
 				pcOffset = 0;
-			saveFunc(&pcOffset, sizeof(int32));
-			saveFunc(&tempCi->base, sizeof(StkId));
-			saveFunc(&tempCi->nResults, sizeof(int32));
+			saveSint32(pcOffset);
+			saveSint32(tempCi->base);
+			saveSint32(tempCi->nResults);
 			if (tempCi == tempTask->ci)
 				taskCi = i;
 			tempCi++;
 		}
 		assert(taskCi != -1);
-		saveFunc(&taskCi, sizeof(int32));
+		saveSint32(taskCi);
 
 		MbaseOffset = tempTask->Mbuffbase - tempTask->Mbuffer;
-		saveFunc(&MbaseOffset, sizeof(int32));
-		saveFunc(&tempTask->Mbuffnext, sizeof(int32));
+		saveSint32(MbaseOffset);
+		saveSint32(tempTask->Mbuffnext);
 
-		saveFunc(&tempTask->Tstate, sizeof(TaskState));
-		saveFunc(&tempTask->id, sizeof(int32));
+		saveSint32(tempTask->Tstate);
+		saveSint32(tempTask->id);
 
 		tempTask = tempTask->next;
 	}
-*/
+
 	printf("lua_Save() finished.\n");
 }

Modified: residual/trunk/engine/lua/lua.h
===================================================================
--- residual/trunk/engine/lua/lua.h	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/lua/lua.h	2008-07-25 22:21:04 UTC (rev 33293)
@@ -26,15 +26,29 @@
 typedef struct lua_State lua_State;
 extern lua_State *lua_state;
 
-typedef void (*SaveRestoreFunc)(void *, int32);
-typedef int32 (*SaveRestoreCallback)(int32, int32, SaveRestoreFunc);
+struct PointerId {
+	uint32	low;
+	uint32	hi;
+};
 
-extern SaveRestoreCallback saveCallback;
-extern SaveRestoreCallback restoreCallback;
+PointerId makeIdFromPointer(void *ptr);
+void *makePointerFromId(PointerId ptr);
 
-void lua_Save(SaveRestoreFunc);
-void lua_Restore(SaveRestoreFunc);
+typedef void (*SaveStream)(void *, int32);
+typedef void (*SaveSint32)(int32);
+typedef void (*SaveUint32)(uint32);
+typedef void (*RestoreStream)(void *, int32);
+typedef int32 (*RestoreSint32)();
+typedef uint32 (*RestoreUint32)();
+typedef PointerId (*SaveCallback)(int32, PointerId, SaveSint32);
+typedef PointerId (*RestoreCallback)(int32, PointerId, RestoreSint32);
 
+extern SaveCallback saveCallbackPtr;
+extern RestoreCallback restoreCallbackPtr;
+
+void lua_Save(SaveStream, SaveSint32, SaveUint32);
+void lua_Restore(RestoreStream, RestoreSint32, RestoreUint32);
+
 void lua_removelibslists(void);
 
 void	       lua_open			(void);

Modified: residual/trunk/engine/lua.cpp
===================================================================
--- residual/trunk/engine/lua.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/lua.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -3112,14 +3112,14 @@
 	g_engine->_savegameSaveRequest = true;
 }
 
-static int SaveCallback(int /*tag*/, int value, SaveRestoreFunc /*savedState*/) {
+static PointerId saveCallback(int32 /*tag*/, PointerId ptr, SaveSint32 /*savedState*/) {
 	DEBUG_FUNCTION();
-	return value;
+	return ptr;
 }
 
-static int RestoreCallback(int /*tag*/, int value, SaveRestoreFunc /*savedState*/) {
+static PointerId restoreCallback(int32 /*tag*/, PointerId ptr, RestoreSint32 /*savedState*/) {
 	DEBUG_FUNCTION();
-	return value;
+	return ptr;
 }
 
 static void LockFont() {
@@ -3871,8 +3871,8 @@
 	lua_pushnumber(0x8000);
 	lua_setglobal("HOT");
 
-	saveCallback = SaveCallback;
-	restoreCallback = RestoreCallback;
+	saveCallbackPtr = saveCallback;
+	restoreCallbackPtr = restoreCallback;
 }
 
 int bundle_dofile(const char *filename) {

Modified: residual/trunk/engine/savegame.cpp
===================================================================
--- residual/trunk/engine/savegame.cpp	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/savegame.cpp	2008-07-25 22:21:04 UTC (rev 33293)
@@ -25,6 +25,7 @@
 
 #include "common/debug.h"
 #include "common/savefile.h"
+#include "common/endian.h"
 
 #include "engine/savegame.h"
 
@@ -79,7 +80,7 @@
 	_sectionBuffer = (byte *)malloc(_sectionSize);
 	if (!_saving) {
 		uint32 tag = 0;
-		
+
 		while (tag != sectionTag) {
 			free(_sectionBuffer);
 			tag = _inSaveFile->readUint32BE();
@@ -116,6 +117,46 @@
 	_sectionPtr += size;
 }
 
+uint32 SaveGame::readLEUint32() {
+	if (_saving)
+		error("SaveGame::readBlock called when storing a savegame!");
+	if (_currentSection == 0)
+		error("Tried to read a block without starting a section!");
+	uint32 data = READ_LE_UINT32(&_sectionBuffer[_sectionPtr]);
+	_sectionPtr += 4;
+	return data;
+}
+
+int32 SaveGame::readLESint32() {
+	if (_saving)
+		error("SaveGame::readBlock called when storing a savegame!");
+	if (_currentSection == 0)
+		error("Tried to read a block without starting a section!");
+	int32 data = (int32)READ_LE_UINT32(&_sectionBuffer[_sectionPtr]);
+	_sectionPtr += 4;
+	return data;
+}
+
+byte SaveGame::readByte() {
+	if (_saving)
+		error("SaveGame::readBlock called when storing a savegame!");
+	if (_currentSection == 0)
+		error("Tried to read a block without starting a section!");
+	byte data = _sectionBuffer[_sectionPtr];
+	_sectionPtr++;
+	return data;
+}
+
+bool SaveGame::readLEBool() {
+	if (_saving)
+		error("SaveGame::readBlock called when storing a savegame!");
+	if (_currentSection == 0)
+		error("Tried to read a block without starting a section!");
+	uint32 data = READ_LE_UINT32(&_sectionBuffer[_sectionPtr]);
+	_sectionPtr += 4;
+	return data != 0;
+}
+
 void SaveGame::write(const void *data, int size) {
 	if (!_saving)
 		error("SaveGame::writeBlock called when restoring a savegame!");
@@ -127,3 +168,55 @@
 	memcpy(&_sectionBuffer[_sectionSize], data, size);
 	_sectionSize += size;
 }
+
+void SaveGame::writeLEUint32(uint32 data) {
+	if (!_saving)
+		error("SaveGame::writeBlock called when restoring a savegame!");
+	if (_currentSection == 0)
+		error("Tried to write a block without starting a section!");
+	_sectionBuffer = (byte *)realloc(_sectionBuffer, _sectionSize + 4);
+	if (!_sectionBuffer)
+		error("Failed to allocate space for buffer!");
+
+	WRITE_LE_UINT32(&_sectionBuffer[_sectionSize], data);
+	_sectionSize += 4;
+}
+
+void SaveGame::writeLESint32(int32 data) {
+	if (!_saving)
+		error("SaveGame::writeBlock called when restoring a savegame!");
+	if (_currentSection == 0)
+		error("Tried to write a block without starting a section!");
+	_sectionBuffer = (byte *)realloc(_sectionBuffer, _sectionSize + 4);
+	if (!_sectionBuffer)
+		error("Failed to allocate space for buffer!");
+
+	WRITE_LE_UINT32(&_sectionBuffer[_sectionSize], (uint32)data);
+	_sectionSize += 4;
+}
+
+void SaveGame::writeLEBool(bool data) {
+	if (!_saving)
+		error("SaveGame::writeBlock called when restoring a savegame!");
+	if (_currentSection == 0)
+		error("Tried to write a block without starting a section!");
+	_sectionBuffer = (byte *)realloc(_sectionBuffer, _sectionSize + 4);
+	if (!_sectionBuffer)
+		error("Failed to allocate space for buffer!");
+
+	WRITE_LE_UINT32(&_sectionBuffer[_sectionSize], (uint32)data);
+	_sectionSize += 4;
+}
+
+void SaveGame::writeByte(byte data) {
+	if (!_saving)
+		error("SaveGame::writeBlock called when restoring a savegame!");
+	if (_currentSection == 0)
+		error("Tried to write a block without starting a section!");
+	_sectionBuffer = (byte *)realloc(_sectionBuffer, _sectionSize + 1);
+	if (!_sectionBuffer)
+		error("Failed to allocate space for buffer!");
+
+	_sectionBuffer[_sectionSize] = data;
+	_sectionSize++;
+}

Modified: residual/trunk/engine/savegame.h
===================================================================
--- residual/trunk/engine/savegame.h	2008-07-25 21:24:09 UTC (rev 33292)
+++ residual/trunk/engine/savegame.h	2008-07-25 22:21:04 UTC (rev 33293)
@@ -53,6 +53,14 @@
 	void endSection();
 	void read(void *data, int size);
 	void write(const void *data, int size);
+	uint32 readLEUint32();
+	int32 readLESint32();
+	bool readLEBool();
+	byte readByte();
+	void writeLEUint32(uint32 data);
+	void writeLESint32(int32 data);
+	void writeLEBool(bool data);
+	void writeByte(byte data);
 
 protected:
 	bool _saving;


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