blob: caec98fe08fe5fe280f0b94929cae026bdd2bf47 [file] [log] [blame]
// LimitedStreams.h
#ifndef __LIMITED_STREAMS_H
#define __LIMITED_STREAMS_H
#include "../../Common/MyCom.h"
#include "../../Common/MyVector.h"
#include "../IStream.h"
class CLimitedSequentialInStream:
public ISequentialInStream,
public CMyUnknownImp
{
CMyComPtr<ISequentialInStream> _stream;
UInt64 _size;
UInt64 _pos;
bool _wasFinished;
public:
void SetStream(ISequentialInStream *stream) { _stream = stream; }
void ReleaseStream() { _stream.Release(); }
void Init(UInt64 streamSize)
{
_size = streamSize;
_pos = 0;
_wasFinished = false;
}
MY_UNKNOWN_IMP
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
UInt64 GetSize() const { return _pos; }
bool WasFinished() const { return _wasFinished; }
};
class CLimitedInStream:
public IInStream,
public CMyUnknownImp
{
CMyComPtr<IInStream> _stream;
UInt64 _virtPos;
UInt64 _physPos;
UInt64 _size;
UInt64 _startOffset;
HRESULT SeekToPhys() { return _stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
public:
void SetStream(IInStream *stream) { _stream = stream; }
HRESULT InitAndSeek(UInt64 startOffset, UInt64 size)
{
_startOffset = startOffset;
_physPos = startOffset;
_virtPos = 0;
_size = size;
return SeekToPhys();
}
MY_UNKNOWN_IMP1(IInStream)
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
HRESULT SeekToStart() { return Seek(0, STREAM_SEEK_SET, NULL); }
};
class CClusterInStream:
public IInStream,
public CMyUnknownImp
{
UInt64 _virtPos;
UInt64 _physPos;
UInt32 _curRem;
public:
CMyComPtr<IInStream> Stream;
UInt64 StartOffset;
UInt64 Size;
int BlockSizeLog;
CRecordVector<UInt32> Vector;
HRESULT SeekToPhys() { return Stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
HRESULT InitAndSeek()
{
_curRem = 0;
_virtPos = 0;
_physPos = StartOffset;
if (Vector.Size() > 0)
{
_physPos = StartOffset + (Vector[0] << BlockSizeLog);
return SeekToPhys();
}
return S_OK;
}
MY_UNKNOWN_IMP1(IInStream)
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
};
HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream);
class CLimitedSequentialOutStream:
public ISequentialOutStream,
public CMyUnknownImp
{
CMyComPtr<ISequentialOutStream> _stream;
UInt64 _size;
bool _overflow;
bool _overflowIsAllowed;
public:
MY_UNKNOWN_IMP
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
void SetStream(ISequentialOutStream *stream) { _stream = stream; }
void ReleaseStream() { _stream.Release(); }
void Init(UInt64 size, bool overflowIsAllowed = false)
{
_size = size;
_overflow = false;
_overflowIsAllowed = overflowIsAllowed;
}
bool IsFinishedOK() const { return (_size == 0 && !_overflow); }
UInt64 GetRem() const { return _size; }
};
#endif