aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYotam Barnoy2010-08-25 09:14:41 +0000
committerYotam Barnoy2010-08-25 09:14:41 +0000
commit4368d3c5749faadb89262dfa869d9a9d3b60a4c8 (patch)
tree7db8f0ea43c120cbf033084dfeabf1942a961546
parentb2ebb62e117e50cb52db64983b5093b2b256867e (diff)
downloadscummvm-rg350-4368d3c5749faadb89262dfa869d9a9d3b60a4c8.tar.gz
scummvm-rg350-4368d3c5749faadb89262dfa869d9a9d3b60a4c8.tar.bz2
scummvm-rg350-4368d3c5749faadb89262dfa869d9a9d3b60a4c8.zip
COMMON: fixed EOS handling in BufferedReadStream and BufferedSeekableReadStream
EOS problem was causing Discworld to crash and zip files not to load on the PSP. svn-id: r52377
-rw-r--r--common/stream.cpp17
-rw-r--r--common/stream.h3
2 files changed, 15 insertions, 5 deletions
diff --git a/common/stream.cpp b/common/stream.cpp
index e4b6aab818..651cfaa3eb 100644
--- a/common/stream.cpp
+++ b/common/stream.cpp
@@ -226,6 +226,7 @@ BufferedReadStream::BufferedReadStream(ReadStream *parentStream, uint32 bufSize,
: _parentStream(parentStream),
_disposeParentStream(disposeParentStream),
_pos(0),
+ _eos(false),
_bufSize(0),
_realBufSize(bufSize) {
@@ -255,6 +256,7 @@ uint32 BufferedReadStream::read(void *dataPtr, uint32 dataSize) {
// Check whether the data left in the buffer suffices....
if (dataSize > bufBytesLeft) {
// Nope, we need to read more data
+ _eos = true; // we tried to read past the buffer
// First, flush the buffer, if it is non-empty
if (0 < bufBytesLeft) {
@@ -277,13 +279,17 @@ uint32 BufferedReadStream::read(void *dataPtr, uint32 dataSize) {
// return to the caller.
_bufSize = _parentStream->read(_buf, _realBufSize);
_pos = 0;
+ if (_bufSize)
+ _eos = false; // we've managed to replenish our buffer
if (dataSize > _bufSize)
dataSize = _bufSize;
}
- // Satisfy the request from the buffer
- memcpy(dataPtr, _buf + _pos, dataSize);
- _pos += dataSize;
+ if (dataSize) {
+ // Satisfy the request from the buffer
+ memcpy(dataPtr, _buf + _pos, dataSize);
+ _pos += dataSize;
+ }
return alreadyRead + dataSize;
}
@@ -297,8 +303,11 @@ bool BufferedSeekableReadStream::seek(int32 offset, int whence) {
// in the buffer only.
// Note: We could try to handle SEEK_END and SEEK_SET, too, but
// since they are rarely used, it seems not worth the effort.
+ _eos = false; // seeking always cancels EOS
+
if (whence == SEEK_CUR && (int)_pos + offset >= 0 && _pos + offset <= _bufSize) {
_pos += offset;
+
} else {
// Seek was not local enough, so we reset the buffer and
// just seeks normally in the parent stream.
@@ -308,7 +317,7 @@ bool BufferedSeekableReadStream::seek(int32 offset, int whence) {
_parentStream->seek(offset, whence);
}
- return true; // FIXME: STREAM REWRITE
+ return true;
}
BufferedWriteStream::BufferedWriteStream(WriteStream *parentStream, uint32 bufSize, DisposeAfterUse::Flag disposeParentStream)
diff --git a/common/stream.h b/common/stream.h
index ce02f90ca9..be52ca69cd 100644
--- a/common/stream.h
+++ b/common/stream.h
@@ -494,6 +494,7 @@ protected:
DisposeAfterUse::Flag _disposeParentStream;
byte *_buf;
uint32 _pos;
+ bool _eos; // in this context it means: have we tried to read beyond the end of the buffer
uint32 _bufSize;
uint32 _realBufSize;
virtual void allocBuf(uint32 bufSize); // virtual functions to allocate/deallocate the buffer
@@ -503,7 +504,7 @@ public:
BufferedReadStream(ReadStream *parentStream, uint32 bufSize, DisposeAfterUse::Flag disposeParentStream = DisposeAfterUse::NO);
virtual ~BufferedReadStream();
- virtual bool eos() const { return (_pos == _bufSize) && _parentStream->eos(); }
+ virtual bool eos() const { return _eos && _parentStream->eos(); }
virtual bool err() const { return _parentStream->err(); }
virtual void clearErr() { _parentStream->clearErr(); }