Skip to content

Commit

Permalink
LASTEXPRESS: Implement savegame read compression
Browse files Browse the repository at this point in the history
  • Loading branch information
Templier committed Aug 1, 2012
1 parent 11cf614 commit eb6c60c
Show file tree
Hide file tree
Showing 2 changed files with 89 additions and 11 deletions.
97 changes: 87 additions & 10 deletions engines/lastexpress/game/savegame.cpp
Expand Up @@ -119,6 +119,18 @@ void SavegameStream::writeBuffer(uint8 value, bool onlyValue) {
}
}

uint8 SavegameStream::readBuffer() {
if (_bufferOffset == -1 || _bufferOffset >= 256) {
readUncompressed(_buffer, 256);
_bufferOffset = 0;
}

byte val = _buffer[_bufferOffset];
_bufferOffset++;

return val;
}

uint32 SavegameStream::process() {
_enableCompression = !_enableCompression;

Expand Down Expand Up @@ -148,24 +160,24 @@ uint32 SavegameStream::process() {

case 2:
if (_previousValue) {
writeBuffer(0xFF, true);
writeBuffer(_repeatCount, true);
writeBuffer(_previousValue, true);
writeBuffer(0xFF);
writeBuffer(_repeatCount);
writeBuffer(_previousValue);
break;
}

if (_repeatCount == 3) {
writeBuffer(0xFB, true);
writeBuffer(0xFB);
break;
}

if (_repeatCount == -1) {
writeBuffer(0xFC, true);
if (_repeatCount == 255) {
writeBuffer(0xFC);
break;
}

writeBuffer(0xFD, true);
writeBuffer(_repeatCount, true);
writeBuffer(0xFD);
writeBuffer(_repeatCount);
break;
}

Expand All @@ -190,7 +202,7 @@ uint32 SavegameStream::writeCompressed(const void *dataPtr, uint32 dataSize) {
error("[SavegameStream::writeCompressed] Error: Compression buffer is in read mode.");

_status = kStatusWriting;
byte *data = (byte *)dataPtr;
const byte *data = (const byte *)dataPtr;

while (dataSize) {
switch (_valueCount) {
Expand Down Expand Up @@ -264,7 +276,72 @@ uint32 SavegameStream::readCompressed(void *dataPtr, uint32 dataSize) {
if (_status == kStatusWriting)
error("[SavegameStream::writeCompressed] Error: Compression buffer is in write mode.");

error("[SavegameStream::readCompressed] Compression not implemented!");
_status = kStatusReady;
byte *data = (byte *)dataPtr;

while (dataSize) {
switch (_valueCount) {
default:
error("[SavegameStream::readCompressed] Invalid value count (%d)", _valueCount);

case 0:
case 1: {
// Read control code
byte control = readBuffer();

switch (control) {
default:
// Data value
*data++ = control;
break;

case 0xFB:
_repeatCount = 2;
_previousValue = 0;
*data++ = 0;
_valueCount = 2;
break;

case 0xFC:
_repeatCount = 254;
_previousValue = 0;
*data++ = 0;
_valueCount = 2;
break;

case 0xFD:
_repeatCount = readBuffer() - 1;
_previousValue = 0;
*data++ = 0;
_valueCount = 2;
break;

case 0xFE:
*data++ = readBuffer();
break;

case 0xFF:
_repeatCount = readBuffer() - 1;
_previousValue = readBuffer();
*data++ = _previousValue;
_valueCount = 2;
break;
}
}
break;

case 2:
*data++ = _previousValue;
_repeatCount--;
if (!_repeatCount)
_valueCount = 1;
break;
}

--dataSize;
}

return _offset;
}

//////////////////////////////////////////////////////////////////////////
Expand Down
3 changes: 2 additions & 1 deletion engines/lastexpress/game/savegame.h
Expand Up @@ -124,7 +124,8 @@ class SavegameStream : public Common::MemoryWriteStreamDynamic, public Common::S
uint32 writeCompressed(const void *dataPtr, uint32 dataSize);
uint32 readCompressed(void *dataPtr, uint32 dataSize);

void writeBuffer(uint8 value, bool onlyValue);
void writeBuffer(uint8 value, bool onlyValue = true);
uint8 readBuffer();

private:
bool _eos;
Expand Down

0 comments on commit eb6c60c

Please sign in to comment.