aboutsummaryrefslogtreecommitdiff
path: root/SrcShared/SessionFile.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'SrcShared/SessionFile.cpp')
-rw-r--r--SrcShared/SessionFile.cpp1142
1 files changed, 1142 insertions, 0 deletions
diff --git a/SrcShared/SessionFile.cpp b/SrcShared/SessionFile.cpp
new file mode 100644
index 0000000..a5e2f72
--- /dev/null
+++ b/SrcShared/SessionFile.cpp
@@ -0,0 +1,1142 @@
+/* -*- mode: C++; tab-width: 4 -*- */
+/* ===================================================================== *\
+ Copyright (c) 1999-2001 Palm, Inc. or its subsidiaries.
+ All rights reserved.
+
+ This file is part of the Palm OS Emulator.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+\* ===================================================================== */
+
+#include "EmCommon.h"
+#include "SessionFile.h"
+
+#include "Byteswapping.h" // Canonical
+#include "EmErrCodes.h" // kError_InvalidDevice
+#include "EmPalmStructs.h" // EmProxySED1376RegsType
+#include "EmStreamFile.h" // EmStreamFile
+#include "ErrorHandling.h" // Errors::Throw
+#include "Miscellaneous.h" // StMemory, RunLengthEncode, GzipEncode, etc.
+#include "UAE.h" // regstruct
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile constructor
+ *
+ * DESCRIPTION: Initialize the SessionFile object. Sets the fFile data
+ * member to refer to the given ChunkFile (which must
+ * exist for the life of the SessionFile).
+ *
+ * PARAMETERS: None
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+SessionFile::SessionFile (ChunkFile& f) :
+ fFile (f),
+ fCanReload (false),
+ fCfg (),
+ fReadBugFixes (false),
+ fChangedBugFixes (false),
+ fBugFixes (0)
+{
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile destructor
+ *
+ * DESCRIPTION: Releases SessionFile resources. Currently does nothing.
+ *
+ * PARAMETERS: None
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+SessionFile::~SessionFile (void)
+{
+ if (fChangedBugFixes)
+ {
+ this->WriteBugFixes (fBugFixes);
+ }
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadROMFileReference
+ *
+ * DESCRIPTION: Read a reference to a paired ROM file from the session
+ * file. For robustness, several approaches are used to
+ * find a ROM file. Because these approaches are platform-
+ * specific, most of the work is off-loaded to the Platform
+ * sub-system. If the file reference can be read, it's
+ * recorded in the configuration record to be used the next
+ * time a new session is created.
+ *
+ * PARAMETERS: f - reference to EmFileRef to receive the read value.
+ *
+ * RETURNED: True if a value could be found, false otherwise.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadROMFileReference (EmFileRef& f)
+{
+ // Look for a ROM reference using a platform-specific method.
+
+ if (Platform::ReadROMFileReference (fFile, f))
+ return true;
+
+ // If a path can't be found, look for a simple ROM name.
+
+ string name;
+ if (fFile.ReadString (SessionFile::kROMNameTag, name))
+ {
+ // First, look in the same directory as the session file.
+
+ try
+ {
+ // Get the stream this ChunkFile is using and see if it's
+ // a file-based stream.
+
+ EmStream& stream = fFile.GetStream ();
+ EmStreamFile& fileStream = dynamic_cast<EmStreamFile&> (stream);
+
+ // If so, get the directory this file is in.
+
+ EmFileRef sessionRef = fileStream.GetFileRef ();
+ EmDirRef sessionParent = sessionRef.GetParent ();
+
+ f = EmFileRef (sessionParent, name);
+
+ if (f.Exists ())
+ return true;
+ }
+ catch (...) // Exception thrown if dynamic_cast fails.
+ {
+ }
+
+ // If not there, look in the same directory as Poser itself.
+
+ EmDirRef emulatorDir = EmDirRef::GetEmulatorDirectory ();
+
+ // Return this reference, even if the file doesn't exist.
+ // That way, we can at least form error messages.
+
+ f = EmFileRef (emulatorDir, name);
+ return true;
+ }
+
+ return false;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadRAMImage
+ *
+ * DESCRIPTION: Read the RAM image from the session file. Attempts to
+ * read a number of versions of the image, including
+ * compressed and uncompressed versions. If the image can
+ * be read, its size is recorded in the configuration
+ * record to be used the next time a new session is created.
+ *
+ * PARAMETERS: image - reference to the pointer to receive the address
+ * of the RAM image.
+ *
+ * size - reference to the integer to receive the size of
+ * the RAM image.
+ *
+ * RETURNED: True if the image was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadRAMImage (void* image)
+{
+ Bool result = this->ReadChunk (kRAMDataTag, image, kGzipCompression);
+
+ if (!result)
+ result = this->ReadChunk (kRLERAMDataTag, image, kRLECompression);
+
+ if (!result)
+ result = this->ReadChunk (kUncompRAMDataTag, image, kNoCompression);
+
+ return result;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadMetaRAMImage
+ *
+ * DESCRIPTION: Read the MetaRAM image from the session file. Attempts
+ * to read a number of versions of the image, including
+ * compressed and uncompressed versions.
+ *
+ * PARAMETERS: image - reference to the pointer to receive the address
+ * of the MetaRAM image.
+ *
+ * size - reference to the integer to receive the size of
+ * the MetaRAM image.
+ *
+ * RETURNED: True if the image was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadMetaRAMImage (void* image)
+{
+ Bool result = this->ReadChunk (kMetaRAMDataTag, image, kGzipCompression);
+
+ if (!result)
+ result = this->ReadChunk (kRLEMetaRAMDataTag, image, kRLECompression);
+
+ return result;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadMetaROMImage
+ *
+ * DESCRIPTION: Read the MetaROM image from the session file. Attempts
+ * to read a number of versions of the image, including
+ * compressed and uncompressed versions.
+ *
+ * PARAMETERS: image - reference to the pointer to receive the address
+ * of the MetaROM image.
+ *
+ * size - reference to the integer to receive the size of
+ * the MetaROM image.
+ *
+ * RETURNED: True if the image was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadMetaROMImage (void* image)
+{
+ Bool result = this->ReadChunk (kMetaROMDataTag, image, kGzipCompression);
+
+ return result;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadHwrDBallType
+ *
+ * DESCRIPTION: Read the Dragonball hardware registers from the
+ * session file.
+ *
+ * PARAMETERS: hwRegs - reference to the struct to receive the register
+ * data.
+ *
+ * RETURNED: True if the data was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadHwrDBallType (HwrM68328Type& hwRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kDBRegs, chunk))
+ {
+ memcpy (&hwRegs, chunk.GetPointer (), sizeof (hwRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadHwrDBallEZType
+ *
+ * DESCRIPTION: Read the DragonballEZ hardware registers from the
+ * session file.
+ *
+ * PARAMETERS: hwRegs - reference to the struct to receive the register
+ * data.
+ *
+ * RETURNED: True if the data was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadHwrDBallEZType (HwrM68EZ328Type& hwRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kDBEZRegs, chunk))
+ {
+ memcpy (&hwRegs, chunk.GetPointer (), sizeof (hwRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadHwrDBallVZType
+ *
+ * DESCRIPTION: Read the DragonballVZ hardware registers from the
+ * session file.
+ *
+ * PARAMETERS: hwRegs - reference to the struct to receive the register
+ * data.
+ *
+ * RETURNED: True if the data was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadHwrDBallVZType (HwrM68VZ328Type& hwRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kDBVZRegs, chunk))
+ {
+ memcpy (&hwRegs, chunk.GetPointer (), sizeof (hwRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadHwrDBallSZType
+ *
+ * DESCRIPTION: Read the DragonballSZ hardware registers from the
+ * session file.
+ *
+ * PARAMETERS: hwRegs - reference to the struct to receive the register
+ * data.
+ *
+ * RETURNED: True if the data was found and could be read in.
+ *
+ ***********************************************************************/
+
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadDBallRegs
+ *
+ * DESCRIPTION: Read the Dragonball CPU registers structure from the
+ * session file.
+ *
+ * PARAMETERS: cpuRegs - reference to the struct to receive the register
+ * data.
+ *
+ * RETURNED: True if the data was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadDBallRegs (regstruct& cpuRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kCPURegs, chunk))
+ {
+ memcpy (&cpuRegs, chunk.GetPointer (), sizeof (cpuRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadDeviceType
+ *
+ * DESCRIPTION: Read the id of the device to emulate. If the id can be
+ * read, it's recorded in the configuration record to be
+ * used the next time a new session is created.
+ *
+ * PARAMETERS: v - reference to the EmDevice to receive the read value.
+ *
+ * RETURNED: True if the value was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadDevice (EmDevice& v)
+{
+ v = EmDevice ();
+
+ // Look up the device by the string.
+
+ string deviceTypeString;
+
+ if (fFile.ReadString (kDeviceTypeString, deviceTypeString))
+ {
+ v = EmDevice (deviceTypeString);
+ }
+
+ return v.Supported ();
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadBugFixes
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: v - reference to the BugFixes to receive the read value.
+ *
+ * RETURNED: True if the value was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadBugFixes (BugFixes& v)
+{
+ uint32 bits;
+ Bool result = fFile.ReadInt (kBugsTag, bits);
+
+ if (result)
+ {
+ v = (BugFixes) bits;
+ }
+
+ return result;
+}
+
+
+Bool SessionFile::ReadSED1375RegsType (SED1375RegsType& sedRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kSED1375Regs, chunk))
+ {
+ memcpy (&sedRegs, chunk.GetPointer (), sizeof (sedRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+Bool SessionFile::ReadSED1375Image (void* image)
+{
+ Bool result = this->ReadChunk (kSED1375Image, image, kGzipCompression);
+
+ return result;
+}
+
+
+Bool SessionFile::ReadSED1375Palette (uint16 palette[256])
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kSED1375Palette, chunk))
+ {
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ memcpy (palette, chunk.GetPointer (), size);
+ return true;
+ }
+
+ return false;
+}
+
+
+Bool SessionFile::ReadSED1376RegsType (SED1376RegsType& sedRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kSED1376Regs, chunk))
+ {
+ memcpy (&sedRegs, chunk.GetPointer (), EmProxySED1376RegsType::GetSize ());
+ return true;
+ }
+
+ return false;
+}
+
+
+Bool SessionFile::ReadSED1376Palette (RGBType palette[256])
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kSED1376Palette, chunk))
+ {
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ memcpy (palette, chunk.GetPointer (), size);
+ return true;
+ }
+
+ return false;
+}
+
+
+// SessionFile::ReadMediaQRegsType is defined in SessionFile.h
+
+
+Bool SessionFile::ReadMediaQImage (void* image)
+{
+ Bool result = this->ReadChunk (kMediaQImage, image, kGzipCompression);
+
+ return result;
+}
+
+
+Bool SessionFile::ReadMediaQPalette (RGBType palette[256])
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kMediaQPalette, chunk))
+ {
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ memcpy (palette, chunk.GetPointer (), size);
+ return true;
+ }
+
+ return false;
+}
+
+
+Bool SessionFile::ReadPLDRegsType (HwrJerryPLDType& pldRegs)
+{
+ Chunk chunk;
+ if (fFile.ReadChunk (kPLDRegs, chunk))
+ {
+ memcpy (&pldRegs, chunk.GetPointer (), sizeof (pldRegs));
+ return true;
+ }
+
+ return false;
+}
+
+
+Bool SessionFile::ReadConfiguration (Configuration& cfg)
+{
+ if (!this->ReadDevice (cfg.fDevice))
+ return false;
+
+ if (!this->ReadROMFileReference (cfg.fROMFile))
+ return false;
+
+ cfg.fRAMSize = this->GetRAMImageSize ();
+ if (cfg.fRAMSize == ChunkFile::kChunkNotFound)
+ return false;
+
+ cfg.fRAMSize /= 1024;
+
+ return true;
+}
+
+
+long SessionFile::GetRAMImageSize (void)
+{
+ long numBytes;
+
+ Chunk chunk;
+ if (fFile.ReadChunk (kRAMDataTag, chunk) || fFile.ReadChunk (kRLERAMDataTag, chunk))
+ {
+ EmStreamChunk s (chunk);
+ s >> numBytes;
+ }
+ else
+ {
+ numBytes = fFile.FindChunk (kUncompRAMDataTag);
+ }
+
+ return numBytes;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteROMFileReference
+ *
+ * DESCRIPTION: Write a reference to the ROM file to use for this
+ * session. For robustness, the reference is written out
+ * in several different ways. Because the way the file is
+ * later looked up is platform-dependent, most of the work
+ * is off-loaded to the Platform sub-system.
+ *
+ * PARAMETERS: f - reference to the EmFileRef for the ROM file.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteROMFileReference (const EmFileRef& f)
+{
+ // Save a ROM reference using a platform-specific method.
+
+ Platform::WriteROMFileReference (fFile, f);
+
+ // Save the name of the ROM file.
+
+ string romFileName = f.GetName ();
+ fFile.WriteString (SessionFile::kROMNameTag, romFileName);
+
+ // Remember that we were using this ROM file most recently.
+
+ fCfg.fROMFile = f;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteRAMImage
+ *
+ * DESCRIPTION: Write the given data as the RAM image for the session
+ * file. The data is written using the default compression.
+ *
+ * PARAMETERS: image - pointer to the data to be written. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * size - number of bytes in the image.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteRAMImage (const void* image, uint32 size)
+{
+ this->WriteChunk (kRAMDataTag, size, image, kGzipCompression);
+ fCfg.fRAMSize = size / 1024;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteMetaRAMImage
+ *
+ * DESCRIPTION: Write the given data as the MetaRAM image for the session
+ * file. The data is written using the default compression.
+ *
+ * PARAMETERS: image - pointer to the data to be written. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * size - number of bytes in the image.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteMetaRAMImage (const void* image, uint32 size)
+{
+ this->WriteChunk (kMetaRAMDataTag, size, image, kGzipCompression);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteMetaROMImage
+ *
+ * DESCRIPTION: Write the given data as the MetaROM image for the session
+ * file. The data is written using the default compression.
+ *
+ * PARAMETERS: image - pointer to the data to be written. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * size - number of bytes in the image.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteMetaROMImage (const void* image, uint32 size)
+{
+ this->WriteChunk (kMetaROMDataTag, size, image, kGzipCompression);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteHwrDBallType
+ *
+ * DESCRIPTION: Write the Dragonball hardware registers to the session
+ * file.
+ *
+ * PARAMETERS: hwRegs - the DB registers to write to disk. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteHwrDBallType (const HwrM68328Type& hwRegs)
+{
+ fFile.WriteChunk (kDBRegs, sizeof (hwRegs), &hwRegs);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteHwrDBallEZType
+ *
+ * DESCRIPTION: Write the Dragonball EZ hardware registers to the session
+ * file.
+ *
+ * PARAMETERS: hwRegs - the DB registers to write to disk. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteHwrDBallEZType (const HwrM68EZ328Type& hwRegs)
+{
+ fFile.WriteChunk (kDBEZRegs, sizeof (hwRegs), &hwRegs);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteHwrDBallVZType
+ *
+ * DESCRIPTION: Write the Dragonball VZ hardware registers to the session
+ * file.
+ *
+ * PARAMETERS: hwRegs - the DB registers to write to disk. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteHwrDBallVZType (const HwrM68VZ328Type& hwRegs)
+{
+ fFile.WriteChunk (kDBVZRegs, sizeof (hwRegs), &hwRegs);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteHwrDBallSZType
+ *
+ * DESCRIPTION: Write the Dragonball SZ hardware registers to the session
+ * file.
+ *
+ * PARAMETERS: hwRegs - the DB registers to write to disk. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteDBallRegs
+ *
+ * DESCRIPTION: Write the Dragonball CPU registers to the session file.
+ *
+ * PARAMETERS: cpuRegs - the registers to write to disk. No munging
+ * of this data is performed; it is expected that any
+ * byteswapping has already taken place.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteDBallRegs (const regstruct& cpuRegs)
+{
+ fFile.WriteChunk (kCPURegs, sizeof (cpuRegs), &cpuRegs);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteDeviceType
+ *
+ * DESCRIPTION: Write the id of the device to emulate.
+ *
+ * PARAMETERS: v - id of the device to emulate.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteDevice (const EmDevice& v)
+{
+ fFile.WriteString (kDeviceTypeString, v.GetIDString ());
+
+ // Remember that we were using this device most recently.
+
+ fCfg.fDevice = v;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteBugFixes
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: v - flags of fixed bugs.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteBugFixes (const BugFixes& v)
+{
+ fFile.WriteInt (kBugsTag, (uint32) v);
+}
+
+
+void SessionFile::WriteSED1375RegsType (const SED1375RegsType& sedRegs)
+{
+ fFile.WriteChunk (kSED1375Regs, sizeof (sedRegs), &sedRegs);
+}
+
+void SessionFile::WriteSED1375Image (const void* image, uint32 size)
+{
+ this->WriteChunk (kSED1375Image, size, image, kGzipCompression);
+}
+
+void SessionFile::WriteSED1375Palette (const uint16 palette[256])
+{
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ fFile.WriteChunk (kSED1375Palette, size, palette);
+}
+
+void SessionFile::WriteSED1376RegsType (const SED1376RegsType& sedRegs)
+{
+ fFile.WriteChunk (kSED1376Regs, EmProxySED1376RegsType::GetSize (), &sedRegs);
+}
+
+void SessionFile::WriteSED1376Palette (const RGBType palette[256])
+{
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ fFile.WriteChunk (kSED1376Palette, size, palette);
+}
+
+// SessionFile::WriteMediaQRegsType is defined in SessionFile.h
+
+void SessionFile::WriteMediaQImage (const void* image, uint32 size)
+{
+ this->WriteChunk (kMediaQImage, size, image, kGzipCompression);
+}
+
+void SessionFile::WriteMediaQPalette (const RGBType palette[256])
+{
+ // Note: "sizeof (palette)" gives 4, not 512.
+ int size = 256 * sizeof (palette[0]);
+ fFile.WriteChunk (kMediaQPalette, size, palette);
+}
+
+void SessionFile::WritePLDRegsType (const HwrJerryPLDType& pldRegs)
+{
+ fFile.WriteChunk (kPLDRegs, sizeof (pldRegs), &pldRegs);
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::SetCanReload
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: None.
+ *
+ * RETURNED: Nothing.
+ *
+ ***********************************************************************/
+
+void SessionFile::SetCanReload (Bool val)
+{
+ fCanReload = val;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::GetCanReload
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: None.
+ *
+ * RETURNED: Nothing.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::GetCanReload (void)
+{
+ return fCanReload;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::FixBug
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: None.
+ *
+ * RETURNED: Nothing.
+ *
+ ***********************************************************************/
+
+void SessionFile::FixBug (BugFix val)
+{
+ fBugFixes |= val;
+ fChangedBugFixes = true;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::IncludesBugFix
+ *
+ * DESCRIPTION: .
+ *
+ * PARAMETERS: None.
+ *
+ * RETURNED: Nothing.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::IncludesBugFix (BugFix val)
+{
+ if (!fReadBugFixes)
+ {
+ this->ReadBugFixes (fBugFixes);
+ fReadBugFixes = true;
+ }
+
+ return (fBugFixes & val) != 0;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::ReadChunk
+ *
+ * DESCRIPTION: Read an arbitrary chunk of data, utilizing the given
+ * type of compression, returning a pointer to the read
+ * data and the size of the data.
+ *
+ * PARAMETERS: tag - marker identifying the data to be read.
+ *
+ * size - reference to the integer to receive the number
+ * of bytes in the data. This size may not be the same
+ * as the size of the chunk if the chunk is compressed.
+ *
+ * image - reference to the pointer to receive the address
+ * of the read data.
+ *
+ * compType - type of compression used for this chunk. The
+ * caller is expected to know what kind of compression
+ * is being used; the compression type is not stored
+ * along with the chunk.
+ *
+ * RETURNED: True if the image was found and could be read in.
+ *
+ ***********************************************************************/
+
+Bool SessionFile::ReadChunk (ChunkFile::Tag tag, void* image,
+ CompressionType compType)
+{
+ // Get the size of the chunk.
+
+ long chunkSize = fFile.FindChunk (tag);
+ if (chunkSize == ChunkFile::kChunkNotFound)
+ {
+ return false;
+ }
+
+ if (chunkSize)
+ {
+ // If no compression is being used, just read the data.
+
+ if (compType == kNoCompression)
+ {
+ fFile.ReadChunk (chunkSize, image);
+ }
+
+ // The data is compressed.
+
+ else
+ {
+ // Use the chunk size to create a buffer.
+
+ StMemory packedImage (chunkSize);
+
+ // Read the chunk into memory.
+
+ fFile.ReadChunk (chunkSize, packedImage.Get ());
+
+ // The size of the unpacked image is stored as the first 4 bytes
+ // of the chunk.
+
+ long unpackedSize = *(long*) packedImage.Get ();
+ Canonical (unpackedSize);
+
+ // Get pointers to the source (packed) data and
+ // destination (unpacked) data.
+
+ void* src = packedImage.Get () + sizeof (long);
+ void* dest = image;
+
+ // Decompress the data into the dest buffer.
+
+ if (compType == kGzipCompression)
+ ::GzipDecode (&src, &dest, chunkSize - sizeof (long), unpackedSize);
+ else
+ ::RunLengthDecode (&src, &dest, chunkSize - sizeof (long), unpackedSize);
+ }
+ }
+
+ return true;
+}
+
+
+Bool SessionFile::ReadChunk (ChunkFile::Tag tag, Chunk& chunk,
+ CompressionType compType)
+{
+ // Get the size of the chunk.
+
+ long chunkSize = fFile.FindChunk (tag);
+ if (chunkSize == ChunkFile::kChunkNotFound)
+ {
+ return false;
+ }
+
+ if (chunkSize)
+ {
+ // If no compression is being used, just read the data.
+
+ if (compType == kNoCompression)
+ {
+ chunk.SetLength (chunkSize);
+ fFile.ReadChunk (chunkSize, chunk.GetPointer ());
+ }
+
+ // The data is compressed.
+
+ else
+ {
+ // Use the chunk size to create a buffer.
+
+ StMemory packedImage (chunkSize);
+
+ // Read the chunk into memory.
+
+ fFile.ReadChunk (chunkSize, packedImage.Get ());
+
+ // The size of the unpacked image is stored as the first 4 bytes
+ // of the chunk.
+
+ long unpackedSize = *(long*) packedImage.Get ();
+ Canonical (unpackedSize);
+
+ chunk.SetLength (unpackedSize);
+
+ // Get pointers to the source (packed) data and
+ // destination (unpacked) data.
+
+ void* src = packedImage.Get () + sizeof (long);
+ void* dest = chunk.GetPointer ();
+
+ // Decompress the data into the dest buffer.
+
+ if (compType == kGzipCompression)
+ ::GzipDecode (&src, &dest, chunkSize - sizeof (long), unpackedSize);
+ else
+ ::RunLengthDecode (&src, &dest, chunkSize - sizeof (long), unpackedSize);
+ }
+ }
+
+ return true;
+}
+
+
+/***********************************************************************
+ *
+ * FUNCTION: SessionFile::WriteChunk
+ *
+ * DESCRIPTION: Write an arbitrary chunk of data, utilizing the given
+ * type of compression.
+ *
+ * PARAMETERS: tag - marker used to later retrieve the data.
+ *
+ * size - number of bytes in the image to write.
+ *
+ * image - pointer to the image to write.
+ *
+ * compType - type of compression to use.
+ *
+ * RETURNED: Nothing
+ *
+ ***********************************************************************/
+
+void SessionFile::WriteChunk (ChunkFile::Tag tag, uint32 size,
+ const void* image, CompressionType compType)
+{
+ // No compression to be used; just write the data out as-is.
+
+ if (compType == kNoCompression)
+ {
+ fFile.WriteChunk (tag, size, image);
+ }
+
+ // Use some form of compression.
+
+ else
+ {
+ // Get the worst-case size for the compressed data.
+
+ long worstPackedSize = sizeof (long) +
+ ((compType == kGzipCompression)
+ ? ::GzipWorstSize (size)
+ : ::RunLengthWorstSize (size));
+
+ // Create a new buffer to hold the compressed data.
+
+ StMemory packedImage (worstPackedSize);
+
+ // Write out the uncompressed size of the data as the first
+ // 4 bytes of the chunk.
+
+ Canonical (size);
+ *(long*) packedImage.Get () = size;
+ Canonical (size);
+
+ // Get pointers to the source (unpacked) data and
+ // destination (packed) data.
+
+ void* src = (void*) image;
+ void* dest = packedImage.Get () + sizeof (long);
+
+ // Compress the data.
+
+ if (compType == kGzipCompression)
+ ::GzipEncode (&src, &dest, size, worstPackedSize);
+ else
+ ::RunLengthEncode (&src, &dest, size, worstPackedSize);
+
+ // Calculate the compressed size of the data.
+
+ long packedSize = (char*) dest - (char*) packedImage;
+
+ // Write the compressed data to the file.
+
+ fFile.WriteChunk (tag, packedSize, packedImage.Get ());
+ }
+}
+
+void SessionFile::WriteChunk (ChunkFile::Tag tag, const Chunk& chunk, CompressionType compType)
+{
+ this->WriteChunk (tag, chunk.GetLength (), chunk.GetPointer (), compType);
+}