2009-05-24 19:13:58 +00:00
|
|
|
#include "engines/grim/savegame.h"
|
|
|
|
#include "engines/grim/grim.h"
|
2008-08-03 13:02:45 +00:00
|
|
|
|
|
|
|
#include "common/endian.h"
|
|
|
|
#include "common/debug.h"
|
|
|
|
|
2009-05-24 19:13:58 +00:00
|
|
|
#include "engines/grim/lua/ltask.h"
|
|
|
|
#include "engines/grim/lua/lauxlib.h"
|
|
|
|
#include "engines/grim/lua/lmem.h"
|
|
|
|
#include "engines/grim/lua/ldo.h"
|
|
|
|
#include "engines/grim/lua/ltm.h"
|
|
|
|
#include "engines/grim/lua/ltable.h"
|
|
|
|
#include "engines/grim/lua/lvm.h"
|
|
|
|
#include "engines/grim/lua/lopcodes.h"
|
|
|
|
#include "engines/grim/lua/lstring.h"
|
|
|
|
#include "engines/grim/lua/lua.h"
|
2011-03-21 05:16:27 +08:00
|
|
|
#include "engines/grim/actor.h"
|
2004-12-25 18:23:07 +00:00
|
|
|
|
2009-05-25 06:49:57 +00:00
|
|
|
namespace Grim {
|
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
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++;
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
assert(0);
|
|
|
|
break;
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
case LUA_T_NUMBER:
|
|
|
|
case LUA_T_TASK:
|
|
|
|
{
|
2008-08-03 10:59:35 +00:00
|
|
|
byte *udata = (byte *)(&object->value.n);
|
2008-07-25 22:21:04 +00:00
|
|
|
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
|
2008-08-03 10:59:35 +00:00
|
|
|
saveUint32(v);
|
2008-07-25 22:21:04 +00:00
|
|
|
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;
|
2008-08-03 08:20:56 +00:00
|
|
|
default:
|
2009-05-30 21:05:58 +00:00
|
|
|
saveUint32(makeIdFromPointer(object->value.ts).low);
|
|
|
|
saveUint32(makeIdFromPointer(object->value.ts).hi);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-07-20 21:08:22 +00:00
|
|
|
static int32 opcodeSizeTable[] = {
|
2004-12-30 08:04:55 +00:00
|
|
|
1, 2, 1, 2, 1, 1, 1, 3, 2, 1, 1, 1, 1, 1, 1, 1, 1, 3, 2, 1,
|
|
|
|
1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 3,
|
|
|
|
1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 3, 2, 1, 1, 1, 1, 1, 1, 1, 1,
|
|
|
|
3, 2, 1, 1, 3, 2, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1,
|
|
|
|
1, 1, 1, 3, 1, 2, 3, 2, 4, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
|
|
|
1, 1, 1, 1, 1, 2, 3, 2, 3, 2, 3, 2, 3, 2, 3, 2, 3, 2, 1, 1,
|
|
|
|
3, 2, 2, 2, 2, 3, 2, 1, 1, 1, 2, 1, 2, 1, 1, 1, 3, 2, 1, 1,
|
|
|
|
1, 1, 1, 1, 1, 1, 3, 2, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 2,
|
|
|
|
1, 1, 1, 1, 1, 1, 1, 1, 3, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 3,
|
|
|
|
2, 1, 1, 1, 1, 1, 1, 1, 1, 3, 2, 1, 1, 3, 2, 1, 1, 1, 1, 1,
|
|
|
|
1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 3, 1, 2, 3, 2, 4, 2, 1,
|
|
|
|
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 2, 3, 2, 3,
|
|
|
|
2, 3, 2, 3, 2, 3, 2, 1, 1, 3, 2, 2, 2, 2, 3, 2, 1, 1
|
|
|
|
};
|
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
void lua_Save(SaveStream saveStream, SaveSint32 saveSint32, SaveUint32 saveUint32) {
|
2004-12-30 08:04:55 +00:00
|
|
|
lua_collectgarbage(0);
|
2008-07-20 21:08:22 +00:00
|
|
|
int32 i, l;
|
|
|
|
int32 countElements = 0;
|
|
|
|
int32 maxStringLength = 0;
|
2008-07-25 22:21:04 +00:00
|
|
|
|
|
|
|
|
|
|
|
// Check for max length for strings and count them
|
2004-12-30 08:04:55 +00:00
|
|
|
for (i = 0; i < NUM_HASHS; i++) {
|
2009-06-18 16:23:25 +00:00
|
|
|
stringtable *tempStringTable = &string_root[i];
|
2009-05-23 06:15:18 +00:00
|
|
|
for (l = 0; l < tempStringTable->size; l++) {
|
2008-07-25 22:21:04 +00:00
|
|
|
if (tempStringTable->hash[l] && tempStringTable->hash[l] != &EMPTY) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countElements++;
|
|
|
|
if (tempStringTable->hash[l]->constindex != -1) {
|
2009-05-23 03:08:19 +00:00
|
|
|
int len = strlen(tempStringTable->hash[l]->str);
|
|
|
|
if (maxStringLength < len) {
|
|
|
|
maxStringLength = len;
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
// save number of strings
|
|
|
|
saveSint32(countElements);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save number of closures
|
|
|
|
countElements = 0;
|
2004-12-30 08:04:55 +00:00
|
|
|
GCnode *tempNode;
|
2009-06-18 16:23:25 +00:00
|
|
|
tempNode = rootcl.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempNode) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countElements++;
|
|
|
|
tempNode = tempNode->next;
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countElements);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save number of tables
|
|
|
|
countElements = 0;
|
2009-06-18 16:23:25 +00:00
|
|
|
tempNode = roottable.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempNode) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countElements++;
|
|
|
|
tempNode = tempNode->next;
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countElements);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save number of prototypes
|
|
|
|
countElements = 0;
|
2009-06-18 16:23:25 +00:00
|
|
|
tempNode = rootproto.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempNode) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countElements++;
|
|
|
|
tempNode = tempNode->next;
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countElements);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save number of global strings
|
|
|
|
countElements = 0;
|
2009-06-18 16:23:25 +00:00
|
|
|
tempNode = rootglobal.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempNode) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countElements++;
|
|
|
|
tempNode = tempNode->next;
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countElements);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save maximum length for string
|
|
|
|
saveSint32(maxStringLength);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-05-17 08:24:17 +00:00
|
|
|
//printf("1: %d\n", g_grim->_savedState->getBufferPos());
|
2008-08-03 13:02:45 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
// save hash tables for strings and user data
|
2004-12-30 08:04:55 +00:00
|
|
|
TaggedString *tempString;
|
|
|
|
for (i = 0; i < NUM_HASHS; i++) {
|
2009-06-18 16:23:25 +00:00
|
|
|
stringtable *tempStringTable = &string_root[i];
|
2004-12-30 08:04:55 +00:00
|
|
|
for (l = 0; l < tempStringTable->size; l++) {
|
2008-07-25 22:21:04 +00:00
|
|
|
if (tempStringTable->hash[l] && tempStringTable->hash[l] != &EMPTY) {
|
2004-12-30 08:04:55 +00:00
|
|
|
tempString = tempStringTable->hash[l];
|
2008-07-25 22:21:04 +00:00
|
|
|
saveUint32(makeIdFromPointer(tempString).low);
|
|
|
|
saveUint32(makeIdFromPointer(tempString).hi);
|
|
|
|
saveSint32(tempString->constindex);
|
2004-12-30 08:04:55 +00:00
|
|
|
if (tempString->constindex != -1) {
|
2009-05-23 03:08:19 +00:00
|
|
|
saveObjectValue(&tempString->globalval, saveSint32, saveUint32);
|
|
|
|
int len = strlen(tempString->str);
|
|
|
|
saveSint32(len);
|
|
|
|
saveStream(tempString->str, len);
|
2008-07-25 22:21:04 +00:00
|
|
|
} else {
|
|
|
|
if (saveCallbackPtr) {
|
2009-05-23 03:08:19 +00:00
|
|
|
PointerId ptr = makeIdFromPointer(tempString->globalval.value.ts);
|
|
|
|
ptr = saveCallbackPtr(tempString->globalval.ttype, ptr, saveSint32);
|
|
|
|
tempString->globalval.value.ts = (TaggedString *)makePointerFromId(ptr);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2009-05-23 03:08:19 +00:00
|
|
|
saveObjectValue((TObject *)&tempString->globalval, saveSint32, saveUint32);
|
2011-03-21 05:16:27 +08:00
|
|
|
if (tempString->globalval.value.ts) {
|
|
|
|
saveUint32(1);
|
|
|
|
Object *o = (Object *)tempString->globalval.value.ts;
|
|
|
|
|
|
|
|
if (Actor *a = dynamic_cast<Actor *>(o)) {
|
|
|
|
saveUint32(1);
|
|
|
|
saveUint32(g_grim->actorId(a));
|
|
|
|
} else if (TextObject *t = dynamic_cast<TextObject *>(o)) {
|
|
|
|
saveUint32(2);
|
|
|
|
saveUint32(g_grim->textObjectId(t));
|
|
|
|
} else if (ObjectState *s = dynamic_cast<ObjectState *>(o)) {
|
|
|
|
saveUint32(3);
|
|
|
|
saveUint32(g_grim->objectStateId(s));
|
|
|
|
} else {
|
|
|
|
saveUint32(4);
|
|
|
|
ObjectManager::saveObject(g_grim->_savedState, o);
|
|
|
|
}
|
|
|
|
} else {
|
|
|
|
saveUint32(0);
|
|
|
|
}
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2008-08-03 13:02:45 +00:00
|
|
|
|
2009-05-17 08:24:17 +00:00
|
|
|
//printf("2: %d\n", g_grim->_savedState->getBufferPos());
|
2008-08-03 13:02:45 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
Closure *tempClosure = (Closure *)rootcl.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
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);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
tempClosure = (Closure *)tempClosure->head.next;
|
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
Hash *tempHash = (Hash *)roottable.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempHash) {
|
|
|
|
saveUint32(makeIdFromPointer(tempHash).low);
|
|
|
|
saveUint32(makeIdFromPointer(tempHash).hi);
|
|
|
|
saveSint32(tempHash->nhash);
|
2008-07-20 21:08:22 +00:00
|
|
|
int32 countUsedHash = 0;
|
2009-05-17 08:57:38 +00:00
|
|
|
for (i = 0; i < tempHash->nhash; i++) {
|
2004-12-30 08:04:55 +00:00
|
|
|
Node *newNode = &tempHash->node[i];
|
2008-07-25 22:21:04 +00:00
|
|
|
if (newNode->ref.ttype != LUA_T_NIL && newNode->val.ttype != LUA_T_NIL) {
|
2004-12-30 08:04:55 +00:00
|
|
|
countUsedHash++;
|
|
|
|
}
|
|
|
|
}
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countUsedHash);
|
|
|
|
saveSint32(tempHash->htag);
|
2004-12-30 08:04:55 +00:00
|
|
|
for (i = 0; i < tempHash->nhash; i++) {
|
|
|
|
Node *newNode = &tempHash->node[i];
|
2008-07-25 22:21:04 +00:00
|
|
|
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);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
tempHash = (Hash *)tempHash->head.next;
|
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
TProtoFunc *tempProtoFunc = (TProtoFunc *)rootproto.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
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);
|
2004-12-30 08:04:55 +00:00
|
|
|
for (i = 0; i < tempProtoFunc->nconsts; i++) {
|
2008-07-25 22:21:04 +00:00
|
|
|
saveObjectValue(&tempProtoFunc->consts[i], saveSint32, saveUint32);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2008-07-20 21:08:22 +00:00
|
|
|
int32 countVariables = 0;
|
2004-12-30 08:04:55 +00:00
|
|
|
if (tempProtoFunc->locvars) {
|
|
|
|
for (; tempProtoFunc->locvars[countVariables++].line != -1;) { }
|
|
|
|
}
|
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(countVariables);
|
2004-12-30 08:04:55 +00:00
|
|
|
for (i = 0; i < countVariables; i++) {
|
2008-07-25 22:21:04 +00:00
|
|
|
saveUint32(makeIdFromPointer(tempProtoFunc->locvars[i].varname).low);
|
|
|
|
saveUint32(makeIdFromPointer(tempProtoFunc->locvars[i].varname).hi);
|
|
|
|
saveSint32(tempProtoFunc->locvars[i].line);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
|
2008-07-29 14:57:13 +00:00
|
|
|
byte *codePtr = tempProtoFunc->code + 2;
|
|
|
|
byte *tmpPtr = codePtr;
|
2008-07-20 21:08:22 +00:00
|
|
|
int32 opcodeId;
|
2004-12-30 08:04:55 +00:00
|
|
|
do {
|
|
|
|
opcodeId = *tmpPtr;
|
|
|
|
tmpPtr += opcodeSizeTable[opcodeId];
|
|
|
|
} while (opcodeId != ENDCODE);
|
2008-07-20 21:08:22 +00:00
|
|
|
int32 codeSize = (tmpPtr - codePtr) + 2;
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(codeSize);
|
|
|
|
saveStream(tempProtoFunc->code, codeSize);
|
2004-12-30 08:04:55 +00:00
|
|
|
tempProtoFunc = (TProtoFunc *)tempProtoFunc->head.next;
|
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
tempString = (TaggedString *)rootglobal.next;
|
2008-07-25 22:21:04 +00:00
|
|
|
while (tempString) {
|
|
|
|
saveUint32(makeIdFromPointer(tempString).low);
|
|
|
|
saveUint32(makeIdFromPointer(tempString).hi);
|
2004-12-30 08:04:55 +00:00
|
|
|
tempString = (TaggedString *)tempString->head.next;
|
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveObjectValue(&errorim, saveSint32, saveUint32);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
IM *tempIm = IMtable;
|
|
|
|
saveSint32(IMtable_size);
|
|
|
|
for (i = 0; i < IMtable_size; i++) {
|
2004-12-30 08:04:55 +00:00
|
|
|
for (l = 0; l < IM_N; l++) {
|
2008-07-25 22:21:04 +00:00
|
|
|
saveObjectValue(&tempIm->int_method[l], saveSint32, saveUint32);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
tempIm++;
|
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(last_tag);
|
|
|
|
saveSint32(refSize);
|
|
|
|
for (i = 0 ; i < refSize; i++) {
|
|
|
|
saveObjectValue(&refArray[i].o, saveSint32, saveUint32);
|
|
|
|
saveSint32(refArray[i].status);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(GCthreshold);
|
|
|
|
saveSint32(nblocks);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(Mbuffsize);
|
|
|
|
saveStream(Mbuffer, Mbuffsize);
|
|
|
|
int32 MbaseOffset = Mbuffbase - Mbuffer;
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(MbaseOffset);
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(Mbuffnext);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(globalTaskSerialId);
|
2005-01-14 20:33:01 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
int32 countStates = 0, currentState = 0;
|
|
|
|
LState *state = lua_rootState;
|
|
|
|
while (state) {
|
2011-03-21 05:16:27 +08:00
|
|
|
if (lua_state == state)
|
2009-06-18 16:23:25 +00:00
|
|
|
currentState = countStates;
|
|
|
|
countStates++;
|
|
|
|
state = state->next;
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(countStates);
|
|
|
|
saveSint32(currentState);
|
|
|
|
|
|
|
|
state = lua_rootState;
|
|
|
|
while (state) {
|
|
|
|
lua_Task *task = state->task;
|
|
|
|
int32 countTasks = 0, n = -1;
|
|
|
|
while (task) {
|
|
|
|
if (state->some_task && state->some_task == task)
|
|
|
|
n = countTasks;
|
|
|
|
countTasks++;
|
|
|
|
task = task->next;
|
|
|
|
}
|
|
|
|
saveSint32(countTasks);
|
|
|
|
task = state->task;
|
|
|
|
while (task) {
|
|
|
|
saveUint32(makeIdFromPointer(task->cl).low);
|
|
|
|
saveUint32(makeIdFromPointer(task->cl).hi);
|
|
|
|
saveUint32(makeIdFromPointer(task->tf).low);
|
|
|
|
saveUint32(makeIdFromPointer(task->tf).hi);
|
|
|
|
saveSint32(task->base);
|
|
|
|
saveSint32(task->some_base);
|
|
|
|
saveSint32(task->some_results);
|
|
|
|
saveSint32(task->some_flag);
|
|
|
|
int32 pcOffset = task->pc - task->tf->code;
|
|
|
|
saveSint32(pcOffset);
|
|
|
|
saveSint32(task->aux);
|
|
|
|
task = task->next;
|
|
|
|
}
|
|
|
|
|
|
|
|
saveSint32(n);
|
|
|
|
|
|
|
|
saveSint32(state->flag2);
|
|
|
|
saveSint32(state->paused);
|
|
|
|
saveSint32(state->state_counter1);
|
|
|
|
saveSint32(state->state_counter2);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
int32 stackLastSize = (state->stack.last - state->stack.stack) + 1;
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(stackLastSize);
|
2009-06-18 16:23:25 +00:00
|
|
|
int32 stackTopSize = state->stack.top - state->stack.stack;
|
2008-07-25 22:21:04 +00:00
|
|
|
saveSint32(stackTopSize);
|
2004-12-30 08:04:55 +00:00
|
|
|
for (i = 0; i < stackTopSize; i++) {
|
2009-06-18 16:23:25 +00:00
|
|
|
saveObjectValue(&state->stack.stack[i], saveSint32, saveUint32);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(state->Cstack.base);
|
|
|
|
saveSint32(state->Cstack.lua2C);
|
|
|
|
saveSint32(state->Cstack.num);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(state->numCblocks);
|
|
|
|
for (i = 0; i < state->numCblocks; i++) {
|
|
|
|
saveSint32(state->Cblocks[i].base);
|
|
|
|
saveSint32(state->Cblocks[i].lua2C);
|
|
|
|
saveSint32(state->Cblocks[i].num);
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
saveSint32(state->id);
|
|
|
|
saveObjectValue(&state->taskFunc, saveSint32, saveUint32);
|
2004-12-30 08:04:55 +00:00
|
|
|
|
2009-06-18 16:23:25 +00:00
|
|
|
state = state->next;
|
2004-12-30 08:04:55 +00:00
|
|
|
}
|
2004-12-25 18:23:07 +00:00
|
|
|
}
|
2009-05-25 06:49:57 +00:00
|
|
|
|
|
|
|
} // end of namespace Grim
|