OpenJK icon indicating copy to clipboard operation
OpenJK copied to clipboard

Serialization for Save games

Open ensiform opened this issue 10 years ago • 11 comments

Save games should be serialized if possible to fix portability issues with saves. Ideally would want to avoid changes to existing structures like gentity etc. Not sure if its possible to retain the format though. Serialization doesn't seem to fit well with how they currently handle things with string limitations and also chunk ids. Also not sure how to serialize across dll boundaries since sv_savegame and g_savegame are both needed to handle the save contents. And avoiding C++ objects across the dll boundary is required.

@mrwonko

ensiform avatar Oct 25 '15 04:10 ensiform

Ugh, this sounds like a lot of work.

Compat with existing Windows saves should be possible though, if I'm not mistaken. We "just" need to write a function that manually serializes/deserializes all the fields.

mrwonko avatar Oct 25 '15 09:10 mrwonko

I don't see how that works with chunkids though. Or how to serialize character arrays. Since they seem to just store the max size of the array in bytes but only fill in whats used.

ensiform avatar Oct 25 '15 15:10 ensiform

If new format: https://google.github.io/flatbuffers/ ?

ensiform avatar Nov 02 '15 22:11 ensiform

Maybe. But if possible, no new format.

If a new format is used, it should be thought through thoroughly first; it should be future proof.

mrwonko avatar Nov 02 '15 22:11 mrwonko

Should saves be something that needs to be done prior to a release? I kind of think so.

ensiform avatar Nov 03 '15 20:11 ensiform

Maybe #434 can also be fixed as part of this; we'll see.

mrwonko avatar Nov 07 '15 22:11 mrwonko

Try fixing #757 as part of this, too.

mrwonko avatar Nov 29 '15 10:11 mrwonko

Not sure if the new code qualifies as serialization or maybe it does but now that #878 is done can this be closed?

bb0b2f0a541117aba77fc7b59ee51defda99a5b6

ensiform avatar Oct 20 '16 20:10 ensiform

Not sure if the new code qualifies as serialization

I think it does, but one issue that still remains is that it writes numbers in the CPU's native endianness. So you can now have savegames that are portable between 32-bit and 64-bit x86 (which are both little-endian: 0x12345678 is serialized as "\x78\x56\x34\x12"), but not between 32-bit x86 and 32-bit PowerPC (which is big-endian: 0x12345678 is serialized as "\x12\x34\x56\x78").

Because savegames seem to start with a 32-bit "magic number", it would be possible to check whether the magic number is in native or opposite-of-native endianness, and set a flag in the reader object; every time a multi-byte number is read, the reader object would have to byteswap it, and every time an array of numbers is read, the reader object would have to byteswap each member.

smcv avatar Oct 28 '16 10:10 smcv

Please do not close the issue, I'll fix the endianness stuff.

bibendovsky avatar Jan 23 '17 07:01 bibendovsky

Loading ordinary integers etc. (for example array lengths and the FPSL chunk) should be something the template code can do. I noticed while fixing #902 that the Icarus stuff saves/loads its own formatted binary blob, which won't be affected by generic endianness-swapping - but code/icarus/BlockStream.cpp uses LittleLong() so it looks as though someone already thought about endianness there. Any other arbitrary binary blobs will need special care.

Do any of the OpenJK developers have access to a big-endian test machine? A PowerPC (pre-x86) Mac running Linux is probably the most likely. I have one, but won't be able to access it for a while.

You'll need #886 to be able to compile on big-endian machines, assuming you're using a recent version of gcc or clang.

smcv avatar Jan 23 '17 09:01 smcv