From d0cb81fbfc1bb42056e224ae2bd381a79b4210fa Mon Sep 17 00:00:00 2001 From: goyuken Date: Sat, 7 Dec 2013 21:23:23 +0000 Subject: [PATCH] add some real versioning to binary savestates. also make binary savestates able to store text savestate data as well, so they're more accurately called "zip" savestates. at the moment, zip savestates are always binary, but the code exists for future use. --- BizHawk.Client.Common/BinarySaveStates.cs | 43 +++++++++++++++++++---- BizHawk.Client.Common/SavestateManager.cs | 18 +++++++++- 2 files changed, 54 insertions(+), 7 deletions(-) diff --git a/BizHawk.Client.Common/BinarySaveStates.cs b/BizHawk.Client.Common/BinarySaveStates.cs index a706050524..c8e5f80a94 100644 --- a/BizHawk.Client.Common/BinarySaveStates.cs +++ b/BizHawk.Client.Common/BinarySaveStates.cs @@ -10,9 +10,12 @@ namespace BizHawk.Client.Common public const string Corestate = "Core"; public const string Framebuffer = "Framebuffer"; public const string Input = "Input Log"; + public const string CorestateText = "CoreText"; } - + /// + /// more accurately should be called ZipStateLoader, as it supports both text and binary core data + /// public class BinaryStateLoader : IDisposable { private bool isDisposed; @@ -36,11 +39,25 @@ namespace BizHawk.Client.Common } ZipFile zip; + Version ver; private BinaryStateLoader() { } + private void ReadVersion(Stream s) + { + // the "BizState 1.0" tag contains an integer in it describing the sub version. + if (s.Length == 0) + ver = new Version(1, 0, 0); // except for the first release, which doesn't + else + { + StreamReader sr = new StreamReader(s); + ver = new Version(1, 0, int.Parse(sr.ReadLine())); + } + Console.WriteLine("Read a zipstate of version {0}", ver.ToString()); + } + public static BinaryStateLoader LoadAndDetect(string Filename) { BinaryStateLoader ret = new BinaryStateLoader(); @@ -59,7 +76,7 @@ namespace BizHawk.Client.Common { ret.zip = new ZipFile(Filename); var e = ret.zip.GetEntry(BinaryStateFileNames.Versiontag); - if (e == null) + if (!ret.GetFileByName(BinaryStateFileNames.Versiontag, false, ret.ReadVersion)) { ret.zip.Close(); return null; @@ -93,9 +110,11 @@ namespace BizHawk.Client.Common } } - public void GetCoreState(Action callback) + public void GetCoreState(Action callbackBinary, Action callbackText) { - GetFileByName(BinaryStateFileNames.Corestate, true, callback); + if (!GetFileByName(BinaryStateFileNames.Corestate, false, callbackBinary) + && !GetFileByName(BinaryStateFileNames.CorestateText, false, callbackText)) + throw new Exception("Couldn't find Binary or Text savestate"); } public bool GetFrameBuffer(Action callback) @@ -113,6 +132,13 @@ namespace BizHawk.Client.Common { private readonly ZipOutputStream zip; + private void WriteVersion(Stream s) + { + StreamWriter sw = new StreamWriter(s); + sw.WriteLine("1"); // version 1.0.1 + sw.Flush(); + } + /// /// /// @@ -126,7 +152,7 @@ namespace BizHawk.Client.Common }; zip.SetLevel(0); - PutFileByName(BinaryStateFileNames.Versiontag, ss => { }); + PutFileByName(BinaryStateFileNames.Versiontag, WriteVersion); } void PutFileByName(string Name, Action callback) @@ -137,11 +163,16 @@ namespace BizHawk.Client.Common zip.CloseEntry(); } - public void PutCoreState(Action callback) + public void PutCoreStateBinary(Action callback) { PutFileByName(BinaryStateFileNames.Corestate, callback); } + public void PutCoreStateText(Action callback) + { + PutFileByName(BinaryStateFileNames.CorestateText, callback); + } + public void PutFrameBuffer(Action callback) { PutFileByName(BinaryStateFileNames.Framebuffer, callback); diff --git a/BizHawk.Client.Common/SavestateManager.cs b/BizHawk.Client.Common/SavestateManager.cs index f1e44982f5..bc7386afba 100644 --- a/BizHawk.Client.Common/SavestateManager.cs +++ b/BizHawk.Client.Common/SavestateManager.cs @@ -29,13 +29,24 @@ namespace BizHawk.Client.Common using (FileStream fs = new FileStream(filename, FileMode.Create, FileAccess.Write)) using (BinaryStateSaver bs = new BinaryStateSaver(fs)) { - bs.PutCoreState( +#if true + bs.PutCoreStateBinary( delegate(Stream s) { BinaryWriter bw = new BinaryWriter(s); Global.Emulator.SaveStateBinary(bw); bw.Flush(); }); +#else + // this would put text states inside the zipfile + bs.PutCoreStateText( + delegate(Stream s) + { + StreamWriter sw = new StreamWriter(s); + Global.Emulator.SaveStateText(sw); + sw.Flush(); + }); +#endif if (Global.Config.SaveScreenshotWithStates) { bs.PutFrameBuffer( @@ -92,6 +103,11 @@ namespace BizHawk.Client.Common { BinaryReader br = new BinaryReader(s); Global.Emulator.LoadStateBinary(br); + }, + delegate(Stream s) + { + StreamReader sr = new StreamReader(s); + Global.Emulator.LoadStateText(sr); }); bw.GetFrameBuffer(