mirror of
https://github.com/Xevion/easy7zip.git
synced 2025-12-06 21:14:58 -06:00
9.34
This commit is contained in:
committed by
Kornel Lesiński
parent
83f8ddcc5b
commit
f08f4dcc3c
18
CPP/7zip/Common/CWrappers.cpp
Executable file → Normal file
18
CPP/7zip/Common/CWrappers.cpp
Executable file → Normal file
@@ -12,7 +12,7 @@
|
||||
|
||||
#define CONVERT_PR_VAL(x) (x == PROGRESS_UNKNOWN_VALUE ? NULL : &x)
|
||||
|
||||
static SRes CompressProgress(void *pp, UInt64 inSize, UInt64 outSize)
|
||||
static SRes CompressProgress(void *pp, UInt64 inSize, UInt64 outSize) throw()
|
||||
{
|
||||
CCompressProgressWrap *p = (CCompressProgressWrap *)pp;
|
||||
p->Res = p->Progress->SetRatioInfo(CONVERT_PR_VAL(inSize), CONVERT_PR_VAL(outSize));
|
||||
@@ -30,7 +30,7 @@ static const UInt32 kStreamStepSize = (UInt32)1 << 31;
|
||||
|
||||
SRes HRESULT_To_SRes(HRESULT res, SRes defaultRes)
|
||||
{
|
||||
switch(res)
|
||||
switch (res)
|
||||
{
|
||||
case S_OK: return SZ_OK;
|
||||
case E_OUTOFMEMORY: return SZ_ERROR_MEM;
|
||||
@@ -42,18 +42,19 @@ SRes HRESULT_To_SRes(HRESULT res, SRes defaultRes)
|
||||
return defaultRes;
|
||||
}
|
||||
|
||||
static SRes MyRead(void *object, void *data, size_t *size)
|
||||
static SRes MyRead(void *object, void *data, size_t *size) throw()
|
||||
{
|
||||
CSeqInStreamWrap *p = (CSeqInStreamWrap *)object;
|
||||
UInt32 curSize = ((*size < kStreamStepSize) ? (UInt32)*size : kStreamStepSize);
|
||||
p->Res = (p->Stream->Read(data, curSize, &curSize));
|
||||
*size = curSize;
|
||||
p->Processed += curSize;
|
||||
if (p->Res == S_OK)
|
||||
return SZ_OK;
|
||||
return HRESULT_To_SRes(p->Res, SZ_ERROR_READ);
|
||||
}
|
||||
|
||||
static size_t MyWrite(void *object, const void *data, size_t size)
|
||||
static size_t MyWrite(void *object, const void *data, size_t size) throw()
|
||||
{
|
||||
CSeqOutStreamWrap *p = (CSeqOutStreamWrap *)object;
|
||||
if (p->Stream)
|
||||
@@ -72,6 +73,7 @@ CSeqInStreamWrap::CSeqInStreamWrap(ISequentialInStream *stream)
|
||||
{
|
||||
p.Read = MyRead;
|
||||
Stream = stream;
|
||||
Processed = 0;
|
||||
}
|
||||
|
||||
CSeqOutStreamWrap::CSeqOutStreamWrap(ISequentialOutStream *stream)
|
||||
@@ -96,7 +98,7 @@ HRESULT SResToHRESULT(SRes res)
|
||||
return E_FAIL;
|
||||
}
|
||||
|
||||
static SRes InStreamWrap_Read(void *pp, void *data, size_t *size)
|
||||
static SRes InStreamWrap_Read(void *pp, void *data, size_t *size) throw()
|
||||
{
|
||||
CSeekInStreamWrap *p = (CSeekInStreamWrap *)pp;
|
||||
UInt32 curSize = ((*size < kStreamStepSize) ? (UInt32)*size : kStreamStepSize);
|
||||
@@ -105,7 +107,7 @@ static SRes InStreamWrap_Read(void *pp, void *data, size_t *size)
|
||||
return (p->Res == S_OK) ? SZ_OK : SZ_ERROR_READ;
|
||||
}
|
||||
|
||||
static SRes InStreamWrap_Seek(void *pp, Int64 *offset, ESzSeek origin)
|
||||
static SRes InStreamWrap_Seek(void *pp, Int64 *offset, ESzSeek origin) throw()
|
||||
{
|
||||
CSeekInStreamWrap *p = (CSeekInStreamWrap *)pp;
|
||||
UInt32 moveMethod;
|
||||
@@ -166,7 +168,7 @@ Byte CByteInBufWrap::ReadByteFromNewBlock()
|
||||
return 0;
|
||||
}
|
||||
|
||||
static Byte Wrap_ReadByte(void *pp)
|
||||
static Byte Wrap_ReadByte(void *pp) throw()
|
||||
{
|
||||
CByteInBufWrap *p = (CByteInBufWrap *)pp;
|
||||
if (p->Cur != p->Lim)
|
||||
@@ -212,7 +214,7 @@ HRESULT CByteOutBufWrap::Flush()
|
||||
return Res;
|
||||
}
|
||||
|
||||
static void Wrap_WriteByte(void *pp, Byte b)
|
||||
static void Wrap_WriteByte(void *pp, Byte b) throw()
|
||||
{
|
||||
CByteOutBufWrap *p = (CByteOutBufWrap *)pp;
|
||||
Byte *dest = p->Cur;
|
||||
|
||||
33
CPP/7zip/Common/CWrappers.h
Executable file → Normal file
33
CPP/7zip/Common/CWrappers.h
Executable file → Normal file
@@ -11,7 +11,8 @@ struct CCompressProgressWrap
|
||||
ICompressProgress p;
|
||||
ICompressProgressInfo *Progress;
|
||||
HRESULT Res;
|
||||
CCompressProgressWrap(ICompressProgressInfo *progress);
|
||||
|
||||
CCompressProgressWrap(ICompressProgressInfo *progress) throw();
|
||||
};
|
||||
|
||||
struct CSeqInStreamWrap
|
||||
@@ -19,7 +20,9 @@ struct CSeqInStreamWrap
|
||||
ISeqInStream p;
|
||||
ISequentialInStream *Stream;
|
||||
HRESULT Res;
|
||||
CSeqInStreamWrap(ISequentialInStream *stream);
|
||||
UInt64 Processed;
|
||||
|
||||
CSeqInStreamWrap(ISequentialInStream *stream) throw();
|
||||
};
|
||||
|
||||
struct CSeekInStreamWrap
|
||||
@@ -27,7 +30,8 @@ struct CSeekInStreamWrap
|
||||
ISeekInStream p;
|
||||
IInStream *Stream;
|
||||
HRESULT Res;
|
||||
CSeekInStreamWrap(IInStream *stream);
|
||||
|
||||
CSeekInStreamWrap(IInStream *stream) throw();
|
||||
};
|
||||
|
||||
struct CSeqOutStreamWrap
|
||||
@@ -36,10 +40,11 @@ struct CSeqOutStreamWrap
|
||||
ISequentialOutStream *Stream;
|
||||
HRESULT Res;
|
||||
UInt64 Processed;
|
||||
CSeqOutStreamWrap(ISequentialOutStream *stream);
|
||||
|
||||
CSeqOutStreamWrap(ISequentialOutStream *stream) throw();
|
||||
};
|
||||
|
||||
HRESULT SResToHRESULT(SRes res);
|
||||
HRESULT SResToHRESULT(SRes res) throw();
|
||||
|
||||
struct CByteInBufWrap
|
||||
{
|
||||
@@ -54,9 +59,9 @@ struct CByteInBufWrap
|
||||
HRESULT Res;
|
||||
|
||||
CByteInBufWrap();
|
||||
~CByteInBufWrap() { Free(); }
|
||||
void Free();
|
||||
bool Alloc(UInt32 size);
|
||||
~CByteInBufWrap() { Free(); }
|
||||
void Free() throw();
|
||||
bool Alloc(UInt32 size) throw();
|
||||
void Init()
|
||||
{
|
||||
Lim = Cur = Buf;
|
||||
@@ -65,7 +70,7 @@ struct CByteInBufWrap
|
||||
Res = S_OK;
|
||||
}
|
||||
UInt64 GetProcessed() const { return Processed + (Cur - Buf); }
|
||||
Byte ReadByteFromNewBlock();
|
||||
Byte ReadByteFromNewBlock() throw();
|
||||
Byte ReadByte()
|
||||
{
|
||||
if (Cur != Lim)
|
||||
@@ -85,10 +90,10 @@ struct CByteOutBufWrap
|
||||
UInt64 Processed;
|
||||
HRESULT Res;
|
||||
|
||||
CByteOutBufWrap();
|
||||
~CByteOutBufWrap() { Free(); }
|
||||
void Free();
|
||||
bool Alloc(size_t size);
|
||||
CByteOutBufWrap() throw();
|
||||
~CByteOutBufWrap() { Free(); }
|
||||
void Free() throw();
|
||||
bool Alloc(size_t size) throw();
|
||||
void Init()
|
||||
{
|
||||
Cur = Buf;
|
||||
@@ -97,7 +102,7 @@ struct CByteOutBufWrap
|
||||
Res = S_OK;
|
||||
}
|
||||
UInt64 GetProcessed() const { return Processed + (Cur - Buf); }
|
||||
HRESULT Flush();
|
||||
HRESULT Flush() throw();
|
||||
void WriteByte(Byte b)
|
||||
{
|
||||
*Cur++ = b;
|
||||
|
||||
215
CPP/7zip/Common/CreateCoder.cpp
Executable file → Normal file
215
CPP/7zip/Common/CreateCoder.cpp
Executable file → Normal file
@@ -13,12 +13,21 @@
|
||||
static const unsigned int kNumCodecsMax = 64;
|
||||
unsigned int g_NumCodecs = 0;
|
||||
const CCodecInfo *g_Codecs[kNumCodecsMax];
|
||||
void RegisterCodec(const CCodecInfo *codecInfo)
|
||||
void RegisterCodec(const CCodecInfo *codecInfo) throw()
|
||||
{
|
||||
if (g_NumCodecs < kNumCodecsMax)
|
||||
g_Codecs[g_NumCodecs++] = codecInfo;
|
||||
}
|
||||
|
||||
static const unsigned int kNumHashersMax = 16;
|
||||
unsigned int g_NumHashers = 0;
|
||||
const CHasherInfo *g_Hashers[kNumHashersMax];
|
||||
void RegisterHasher(const CHasherInfo *hashInfo) throw()
|
||||
{
|
||||
if (g_NumHashers < kNumHashersMax)
|
||||
g_Hashers[g_NumHashers++] = hashInfo;
|
||||
}
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
static HRESULT ReadNumberOfStreams(ICompressCodecsInfo *codecsInfo, UInt32 index, PROPID propID, UInt32 &res)
|
||||
{
|
||||
@@ -46,56 +55,74 @@ static HRESULT ReadIsAssignedProp(ICompressCodecsInfo *codecsInfo, UInt32 index,
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT LoadExternalCodecs(ICompressCodecsInfo *codecsInfo, CObjectVector<CCodecInfoEx> &externalCodecs)
|
||||
HRESULT CExternalCodecs::LoadCodecs()
|
||||
{
|
||||
UInt32 num;
|
||||
RINOK(codecsInfo->GetNumberOfMethods(&num));
|
||||
for (UInt32 i = 0; i < num; i++)
|
||||
if (GetCodecs)
|
||||
{
|
||||
CCodecInfoEx info;
|
||||
NWindows::NCOM::CPropVariant prop;
|
||||
RINOK(codecsInfo->GetProperty(i, NMethodPropID::kID, &prop));
|
||||
// if (prop.vt != VT_BSTR)
|
||||
// info.Id.IDSize = (Byte)SysStringByteLen(prop.bstrVal);
|
||||
// memmove(info.Id.ID, prop.bstrVal, info.Id.IDSize);
|
||||
if (prop.vt != VT_UI8)
|
||||
UInt32 num;
|
||||
RINOK(GetCodecs->GetNumberOfMethods(&num));
|
||||
for (UInt32 i = 0; i < num; i++)
|
||||
{
|
||||
continue; // old Interface
|
||||
// return E_INVALIDARG;
|
||||
CCodecInfoEx info;
|
||||
NWindows::NCOM::CPropVariant prop;
|
||||
RINOK(GetCodecs->GetProperty(i, NMethodPropID::kID, &prop));
|
||||
// if (prop.vt != VT_BSTR)
|
||||
// info.Id.IDSize = (Byte)SysStringByteLen(prop.bstrVal);
|
||||
// memcpy(info.Id.ID, prop.bstrVal, info.Id.IDSize);
|
||||
if (prop.vt != VT_UI8)
|
||||
continue; // old Interface
|
||||
info.Id = prop.uhVal.QuadPart;
|
||||
prop.Clear();
|
||||
|
||||
RINOK(GetCodecs->GetProperty(i, NMethodPropID::kName, &prop));
|
||||
if (prop.vt == VT_BSTR)
|
||||
info.Name = prop.bstrVal;
|
||||
else if (prop.vt != VT_EMPTY)
|
||||
return E_INVALIDARG;
|
||||
|
||||
RINOK(ReadNumberOfStreams(GetCodecs, i, NMethodPropID::kInStreams, info.NumInStreams));
|
||||
RINOK(ReadNumberOfStreams(GetCodecs, i, NMethodPropID::kOutStreams, info.NumOutStreams));
|
||||
RINOK(ReadIsAssignedProp(GetCodecs, i, NMethodPropID::kEncoderIsAssigned, info.EncoderIsAssigned));
|
||||
RINOK(ReadIsAssignedProp(GetCodecs, i, NMethodPropID::kDecoderIsAssigned, info.DecoderIsAssigned));
|
||||
|
||||
Codecs.Add(info);
|
||||
}
|
||||
}
|
||||
if (GetHashers)
|
||||
{
|
||||
UInt32 num = num = GetHashers->GetNumHashers();
|
||||
for (UInt32 i = 0; i < num; i++)
|
||||
{
|
||||
CHasherInfoEx info;
|
||||
NWindows::NCOM::CPropVariant prop;
|
||||
RINOK(GetHashers->GetHasherProp(i, NMethodPropID::kID, &prop));
|
||||
if (prop.vt != VT_UI8)
|
||||
continue;
|
||||
info.Id = prop.uhVal.QuadPart;
|
||||
prop.Clear();
|
||||
|
||||
RINOK(GetHashers->GetHasherProp(i, NMethodPropID::kName, &prop));
|
||||
if (prop.vt == VT_BSTR)
|
||||
info.Name = prop.bstrVal;
|
||||
else if (prop.vt != VT_EMPTY)
|
||||
return E_INVALIDARG;
|
||||
|
||||
Hashers.Add(info);
|
||||
}
|
||||
info.Id = prop.uhVal.QuadPart;
|
||||
prop.Clear();
|
||||
|
||||
RINOK(codecsInfo->GetProperty(i, NMethodPropID::kName, &prop));
|
||||
if (prop.vt == VT_BSTR)
|
||||
info.Name = prop.bstrVal;
|
||||
else if (prop.vt != VT_EMPTY)
|
||||
return E_INVALIDARG;;
|
||||
|
||||
RINOK(ReadNumberOfStreams(codecsInfo, i, NMethodPropID::kInStreams, info.NumInStreams));
|
||||
RINOK(ReadNumberOfStreams(codecsInfo, i, NMethodPropID::kOutStreams, info.NumOutStreams));
|
||||
RINOK(ReadIsAssignedProp(codecsInfo, i, NMethodPropID::kEncoderIsAssigned, info.EncoderIsAssigned));
|
||||
RINOK(ReadIsAssignedProp(codecsInfo, i, NMethodPropID::kDecoderIsAssigned, info.DecoderIsAssigned));
|
||||
|
||||
externalCodecs.Add(info);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
bool FindMethod(
|
||||
#ifdef EXTERNAL_CODECS
|
||||
ICompressCodecsInfo * /* codecsInfo */, const CObjectVector<CCodecInfoEx> *externalCodecs,
|
||||
#endif
|
||||
const UString &name,
|
||||
CMethodId &methodId, UInt32 &numInStreams, UInt32 &numOutStreams)
|
||||
bool FindMethod(DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
const UString &name, CMethodId &methodId, UInt32 &numInStreams, UInt32 &numOutStreams)
|
||||
{
|
||||
UInt32 i;
|
||||
for (i = 0; i < g_NumCodecs; i++)
|
||||
{
|
||||
const CCodecInfo &codec = *g_Codecs[i];
|
||||
if (name.CompareNoCase(codec.Name) == 0)
|
||||
if (name.IsEqualToNoCase(codec.Name))
|
||||
{
|
||||
methodId = codec.Id;
|
||||
numInStreams = codec.NumInStreams;
|
||||
@@ -104,11 +131,11 @@ bool FindMethod(
|
||||
}
|
||||
}
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (externalCodecs)
|
||||
for (i = 0; i < (UInt32)externalCodecs->Size(); i++)
|
||||
if (__externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Codecs.Size(); i++)
|
||||
{
|
||||
const CCodecInfoEx &codec = (*externalCodecs)[i];
|
||||
if (codec.Name.CompareNoCase(name) == 0)
|
||||
const CCodecInfoEx &codec = __externalCodecs->Codecs[i];
|
||||
if (codec.Name.IsEqualToNoCase(name))
|
||||
{
|
||||
methodId = codec.Id;
|
||||
numInStreams = codec.NumInStreams;
|
||||
@@ -120,11 +147,8 @@ bool FindMethod(
|
||||
return false;
|
||||
}
|
||||
|
||||
bool FindMethod(
|
||||
#ifdef EXTERNAL_CODECS
|
||||
ICompressCodecsInfo * /* codecsInfo */, const CObjectVector<CCodecInfoEx> *externalCodecs,
|
||||
#endif
|
||||
CMethodId methodId, UString &name)
|
||||
bool FindMethod(DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CMethodId methodId, UString &name)
|
||||
{
|
||||
UInt32 i;
|
||||
for (i = 0; i < g_NumCodecs; i++)
|
||||
@@ -137,10 +161,10 @@ bool FindMethod(
|
||||
}
|
||||
}
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (externalCodecs)
|
||||
for (i = 0; i < (UInt32)externalCodecs->Size(); i++)
|
||||
if (__externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Codecs.Size(); i++)
|
||||
{
|
||||
const CCodecInfoEx &codec = (*externalCodecs)[i];
|
||||
const CCodecInfoEx &codec = __externalCodecs->Codecs[i];
|
||||
if (methodId == codec.Id)
|
||||
{
|
||||
name = codec.Name;
|
||||
@@ -151,6 +175,49 @@ bool FindMethod(
|
||||
return false;
|
||||
}
|
||||
|
||||
bool FindHashMethod(DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
const UString &name,
|
||||
CMethodId &methodId)
|
||||
{
|
||||
UInt32 i;
|
||||
for (i = 0; i < g_NumHashers; i++)
|
||||
{
|
||||
const CHasherInfo &codec = *g_Hashers[i];
|
||||
if (name.IsEqualToNoCase(codec.Name))
|
||||
{
|
||||
methodId = codec.Id;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (__externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Hashers.Size(); i++)
|
||||
{
|
||||
const CHasherInfoEx &codec = __externalCodecs->Hashers[i];
|
||||
if (codec.Name.IsEqualToNoCase(name))
|
||||
{
|
||||
methodId = codec.Id;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
|
||||
void GetHashMethods(DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CRecordVector<CMethodId> &methods)
|
||||
{
|
||||
methods.ClearAndSetSize(g_NumHashers);
|
||||
UInt32 i;
|
||||
for (i = 0; i < g_NumHashers; i++)
|
||||
methods[i] = (*g_Hashers[i]).Id;
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (__externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Hashers.Size(); i++)
|
||||
methods.Add(__externalCodecs->Hashers[i].Id);
|
||||
#endif
|
||||
}
|
||||
|
||||
HRESULT CreateCoder(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CMethodId methodId,
|
||||
@@ -192,10 +259,10 @@ HRESULT CreateCoder(
|
||||
}
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (!created && externalCodecs)
|
||||
for (i = 0; i < (UInt32)externalCodecs->Size(); i++)
|
||||
if (!created && __externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Codecs.Size(); i++)
|
||||
{
|
||||
const CCodecInfoEx &codec = (*externalCodecs)[i];
|
||||
const CCodecInfoEx &codec = __externalCodecs->Codecs[i];
|
||||
if (codec.Id == methodId)
|
||||
{
|
||||
if (encode)
|
||||
@@ -204,17 +271,17 @@ HRESULT CreateCoder(
|
||||
{
|
||||
if (codec.IsSimpleCodec())
|
||||
{
|
||||
HRESULT result = codecsInfo->CreateEncoder(i, &IID_ICompressCoder, (void **)&coder);
|
||||
HRESULT result = __externalCodecs->GetCodecs->CreateEncoder(i, &IID_ICompressCoder, (void **)&coder);
|
||||
if (result != S_OK && result != E_NOINTERFACE && result != CLASS_E_CLASSNOTAVAILABLE)
|
||||
return result;
|
||||
if (!coder)
|
||||
{
|
||||
RINOK(codecsInfo->CreateEncoder(i, &IID_ICompressFilter, (void **)&filter));
|
||||
RINOK(__externalCodecs->GetCodecs->CreateEncoder(i, &IID_ICompressFilter, (void **)&filter));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
RINOK(codecsInfo->CreateEncoder(i, &IID_ICompressCoder2, (void **)&coder2));
|
||||
RINOK(__externalCodecs->GetCodecs->CreateEncoder(i, &IID_ICompressCoder2, (void **)&coder2));
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -224,17 +291,17 @@ HRESULT CreateCoder(
|
||||
{
|
||||
if (codec.IsSimpleCodec())
|
||||
{
|
||||
HRESULT result = codecsInfo->CreateDecoder(i, &IID_ICompressCoder, (void **)&coder);
|
||||
HRESULT result = __externalCodecs->GetCodecs->CreateDecoder(i, &IID_ICompressCoder, (void **)&coder);
|
||||
if (result != S_OK && result != E_NOINTERFACE && result != CLASS_E_CLASSNOTAVAILABLE)
|
||||
return result;
|
||||
if (!coder)
|
||||
{
|
||||
RINOK(codecsInfo->CreateDecoder(i, &IID_ICompressFilter, (void **)&filter));
|
||||
RINOK(__externalCodecs->GetCodecs->CreateDecoder(i, &IID_ICompressFilter, (void **)&filter));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
RINOK(codecsInfo->CreateDecoder(i, &IID_ICompressCoder2, (void **)&coder2));
|
||||
RINOK(__externalCodecs->GetCodecs->CreateDecoder(i, &IID_ICompressCoder2, (void **)&coder2));
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -291,3 +358,37 @@ HRESULT CreateFilter(
|
||||
methodId,
|
||||
filter, coder, coder2, encode, false);
|
||||
}
|
||||
|
||||
HRESULT CreateHasher(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CMethodId methodId,
|
||||
UString &name,
|
||||
CMyComPtr<IHasher> &hasher)
|
||||
{
|
||||
UInt32 i;
|
||||
for (i = 0; i < g_NumHashers; i++)
|
||||
{
|
||||
const CHasherInfo &codec = *g_Hashers[i];
|
||||
if (codec.Id == methodId)
|
||||
{
|
||||
hasher = (IHasher *)codec.CreateHasher();
|
||||
name = codec.Name;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (!hasher && __externalCodecs)
|
||||
for (i = 0; i < (UInt32)__externalCodecs->Hashers.Size(); i++)
|
||||
{
|
||||
const CHasherInfoEx &codec = __externalCodecs->Hashers[i];
|
||||
if (codec.Id == methodId)
|
||||
{
|
||||
name = codec.Name;
|
||||
return __externalCodecs->GetHashers->CreateHasher(i, &hasher);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
41
CPP/7zip/Common/CreateCoder.h
Executable file → Normal file
41
CPP/7zip/Common/CreateCoder.h
Executable file → Normal file
@@ -19,27 +19,43 @@ struct CCodecInfoEx
|
||||
UInt32 NumOutStreams;
|
||||
bool EncoderIsAssigned;
|
||||
bool DecoderIsAssigned;
|
||||
|
||||
bool IsSimpleCodec() const { return NumOutStreams == 1 && NumInStreams == 1; }
|
||||
CCodecInfoEx(): EncoderIsAssigned(false), DecoderIsAssigned(false) {}
|
||||
};
|
||||
|
||||
HRESULT LoadExternalCodecs(ICompressCodecsInfo *codecsInfo, CObjectVector<CCodecInfoEx> &externalCodecs);
|
||||
struct CHasherInfoEx
|
||||
{
|
||||
UString Name;
|
||||
CMethodId Id;
|
||||
};
|
||||
|
||||
#define PUBLIC_ISetCompressCodecsInfo public ISetCompressCodecsInfo,
|
||||
#define QUERY_ENTRY_ISetCompressCodecsInfo MY_QUERYINTERFACE_ENTRY(ISetCompressCodecsInfo)
|
||||
#define DECL_ISetCompressCodecsInfo STDMETHOD(SetCompressCodecsInfo)(ICompressCodecsInfo *compressCodecsInfo);
|
||||
#define IMPL_ISetCompressCodecsInfo2(x) \
|
||||
STDMETHODIMP x::SetCompressCodecsInfo(ICompressCodecsInfo *compressCodecsInfo) { \
|
||||
COM_TRY_BEGIN _codecsInfo = compressCodecsInfo; return LoadExternalCodecs(_codecsInfo, _externalCodecs); COM_TRY_END }
|
||||
COM_TRY_BEGIN __externalCodecs.GetCodecs = compressCodecsInfo; return __externalCodecs.LoadCodecs(); COM_TRY_END }
|
||||
#define IMPL_ISetCompressCodecsInfo IMPL_ISetCompressCodecsInfo2(CHandler)
|
||||
|
||||
#define EXTERNAL_CODECS_VARS2 _codecsInfo, &_externalCodecs
|
||||
struct CExternalCodecs
|
||||
{
|
||||
CMyComPtr<ICompressCodecsInfo> GetCodecs;
|
||||
CMyComPtr<IHashers> GetHashers;
|
||||
|
||||
#define DECL_EXTERNAL_CODECS_VARS CMyComPtr<ICompressCodecsInfo> _codecsInfo; CObjectVector<CCodecInfoEx> _externalCodecs;
|
||||
CObjectVector<CCodecInfoEx> Codecs;
|
||||
CObjectVector<CHasherInfoEx> Hashers;
|
||||
|
||||
HRESULT LoadCodecs();
|
||||
};
|
||||
|
||||
#define EXTERNAL_CODECS_VARS2 &__externalCodecs
|
||||
|
||||
#define DECL_EXTERNAL_CODECS_VARS CExternalCodecs __externalCodecs;
|
||||
#define EXTERNAL_CODECS_VARS EXTERNAL_CODECS_VARS2,
|
||||
|
||||
#define DECL_EXTERNAL_CODECS_LOC_VARS2 ICompressCodecsInfo *codecsInfo, const CObjectVector<CCodecInfoEx> *externalCodecs
|
||||
#define EXTERNAL_CODECS_LOC_VARS2 codecsInfo, externalCodecs
|
||||
#define DECL_EXTERNAL_CODECS_LOC_VARS2 const CExternalCodecs *__externalCodecs
|
||||
#define EXTERNAL_CODECS_LOC_VARS2 __externalCodecs
|
||||
|
||||
#define DECL_EXTERNAL_CODECS_LOC_VARS DECL_EXTERNAL_CODECS_LOC_VARS2,
|
||||
#define EXTERNAL_CODECS_LOC_VARS EXTERNAL_CODECS_LOC_VARS2,
|
||||
@@ -68,6 +84,13 @@ bool FindMethod(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CMethodId methodId, UString &name);
|
||||
|
||||
bool FindHashMethod(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
const UString &name, CMethodId &methodId);
|
||||
|
||||
void GetHashMethods(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CRecordVector<CMethodId> &methods);
|
||||
|
||||
HRESULT CreateCoder(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
@@ -95,4 +118,10 @@ HRESULT CreateFilter(
|
||||
CMyComPtr<ICompressFilter> &filter,
|
||||
bool encode);
|
||||
|
||||
HRESULT CreateHasher(
|
||||
DECL_EXTERNAL_CODECS_LOC_VARS
|
||||
CMethodId methodId,
|
||||
UString &name,
|
||||
CMyComPtr<IHasher> &hacher);
|
||||
|
||||
#endif
|
||||
|
||||
10
CPP/7zip/Common/FilePathAutoRename.cpp
Executable file → Normal file
10
CPP/7zip/Common/FilePathAutoRename.cpp
Executable file → Normal file
@@ -2,10 +2,10 @@
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#include "Common/Defs.h"
|
||||
#include "Common/IntToString.h"
|
||||
#include "../../Common/Defs.h"
|
||||
#include "../../Common/IntToString.h"
|
||||
|
||||
#include "Windows/FileFind.h"
|
||||
#include "../../Windows/FileFind.h"
|
||||
|
||||
#include "FilePathAutoRename.h"
|
||||
|
||||
@@ -36,8 +36,8 @@ bool AutoRenamePath(FString &fullProcessedPath)
|
||||
FString name, extension;
|
||||
if (dotPos > slashPos && dotPos > 0)
|
||||
{
|
||||
name = fullProcessedPath.Left(dotPos);
|
||||
extension = fullProcessedPath.Mid(dotPos);
|
||||
name.SetFrom(fullProcessedPath, dotPos);
|
||||
extension = fullProcessedPath.Ptr(dotPos);
|
||||
}
|
||||
else
|
||||
name = fullProcessedPath;
|
||||
|
||||
2
CPP/7zip/Common/FilePathAutoRename.h
Executable file → Normal file
2
CPP/7zip/Common/FilePathAutoRename.h
Executable file → Normal file
@@ -3,7 +3,7 @@
|
||||
#ifndef __FILE_PATH_AUTO_RENAME_H
|
||||
#define __FILE_PATH_AUTO_RENAME_H
|
||||
|
||||
#include "Common/MyString.h"
|
||||
#include "../../Common/MyString.h"
|
||||
|
||||
bool AutoRenamePath(FString &fullProcessedPath);
|
||||
|
||||
|
||||
157
CPP/7zip/Common/FileStreams.cpp
Executable file → Normal file
157
CPP/7zip/Common/FileStreams.cpp
Executable file → Normal file
@@ -1,4 +1,4 @@
|
||||
// FileStreams.cpp
|
||||
/ FileStreams.cpp
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
@@ -35,8 +35,9 @@ static const UInt32 kClusterSize = 1 << 18;
|
||||
CInFileStream::CInFileStream():
|
||||
VirtPos(0),
|
||||
PhyPos(0),
|
||||
Buffer(0),
|
||||
BufferSize(0)
|
||||
Buf(0),
|
||||
BufSize(0),
|
||||
SupportHardLinks(false)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -45,7 +46,7 @@ CInFileStream::CInFileStream():
|
||||
CInFileStream::~CInFileStream()
|
||||
{
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
MidFree(Buffer);
|
||||
MidFree(Buf);
|
||||
#endif
|
||||
}
|
||||
|
||||
@@ -54,41 +55,41 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
#ifdef USE_WIN_FILE
|
||||
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (size == 0)
|
||||
return S_OK;
|
||||
if (File.IsDeviceFile)
|
||||
{
|
||||
if (File.LengthDefined)
|
||||
if (File.SizeDefined)
|
||||
{
|
||||
if (VirtPos >= File.Length)
|
||||
return VirtPos == File.Length ? S_OK : E_FAIL;
|
||||
UInt64 rem = File.Length - VirtPos;
|
||||
if (VirtPos >= File.Size)
|
||||
return VirtPos == File.Size ? S_OK : E_FAIL;
|
||||
UInt64 rem = File.Size - VirtPos;
|
||||
if (size > rem)
|
||||
size = (UInt32)rem;
|
||||
}
|
||||
for (;;)
|
||||
{
|
||||
const UInt32 mask = kClusterSize - 1;
|
||||
UInt64 mask2 = ~(UInt64)mask;
|
||||
const UInt64 mask2 = ~(UInt64)mask;
|
||||
UInt64 alignedPos = VirtPos & mask2;
|
||||
if (BufferSize > 0 && BufferStartPos == alignedPos)
|
||||
if (BufSize > 0 && BufStartPos == alignedPos)
|
||||
{
|
||||
UInt32 pos = (UInt32)VirtPos & mask;
|
||||
if (pos >= BufferSize)
|
||||
if (pos >= BufSize)
|
||||
return S_OK;
|
||||
UInt32 rem = MyMin(BufferSize - pos, size);
|
||||
memcpy(data, Buffer + pos, rem);
|
||||
UInt32 rem = MyMin(BufSize - pos, size);
|
||||
memcpy(data, Buf + pos, rem);
|
||||
VirtPos += rem;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize += rem;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
bool useBuffer = false;
|
||||
bool useBuf = false;
|
||||
if ((VirtPos & mask) != 0 || ((ptrdiff_t)data & mask) != 0 )
|
||||
useBuffer = true;
|
||||
useBuf = true;
|
||||
else
|
||||
{
|
||||
UInt64 end = VirtPos + size;
|
||||
@@ -96,12 +97,12 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
end &= mask2;
|
||||
if (end <= VirtPos)
|
||||
useBuffer = true;
|
||||
useBuf = true;
|
||||
else
|
||||
size = (UInt32)(end - VirtPos);
|
||||
}
|
||||
}
|
||||
if (!useBuffer)
|
||||
if (!useBuf)
|
||||
break;
|
||||
if (alignedPos != PhyPos)
|
||||
{
|
||||
@@ -112,24 +113,24 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
PhyPos = realNewPosition;
|
||||
}
|
||||
|
||||
BufferStartPos = alignedPos;
|
||||
BufStartPos = alignedPos;
|
||||
UInt32 readSize = kClusterSize;
|
||||
if (File.LengthDefined)
|
||||
readSize = (UInt32)MyMin(File.Length - PhyPos, (UInt64)kClusterSize);
|
||||
if (File.SizeDefined)
|
||||
readSize = (UInt32)MyMin(File.Size - PhyPos, (UInt64)kClusterSize);
|
||||
|
||||
if (Buffer == 0)
|
||||
if (!Buf)
|
||||
{
|
||||
Buffer = (Byte *)MidAlloc(kClusterSize);
|
||||
if (Buffer == 0)
|
||||
Buf = (Byte *)MidAlloc(kClusterSize);
|
||||
if (!Buf)
|
||||
return E_OUTOFMEMORY;
|
||||
}
|
||||
bool result = File.Read1(Buffer, readSize, BufferSize);
|
||||
bool result = File.Read1(Buf, readSize, BufSize);
|
||||
if (!result)
|
||||
return ConvertBoolToHRESULT(result);
|
||||
|
||||
if (BufferSize == 0)
|
||||
if (BufSize == 0)
|
||||
return S_OK;
|
||||
PhyPos += BufferSize;
|
||||
PhyPos += BufSize;
|
||||
}
|
||||
|
||||
if (VirtPos != PhyPos)
|
||||
@@ -145,7 +146,7 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
|
||||
UInt32 realProcessedSize;
|
||||
bool result = File.ReadPart(data, size, realProcessedSize);
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = realProcessedSize;
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
VirtPos += realProcessedSize;
|
||||
@@ -155,12 +156,12 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
|
||||
#else
|
||||
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
ssize_t res = File.Read(data, (size_t)size);
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = (UInt32)res;
|
||||
return S_OK;
|
||||
|
||||
@@ -170,10 +171,13 @@ STDMETHODIMP CInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
#ifdef UNDER_CE
|
||||
STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
size_t s2 = fread(data, 1, size, stdout);
|
||||
if (processedSize != 0)
|
||||
size_t s2 = fread(data, 1, size, stdin);
|
||||
int error = ferror(stdin);
|
||||
if (processedSize)
|
||||
*processedSize = s2;
|
||||
return (s2 = size) ? S_OK : E_FAIL;
|
||||
if (s2 <= size && error == 0)
|
||||
return S_OK;
|
||||
return E_FAIL;
|
||||
}
|
||||
#else
|
||||
STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
@@ -185,7 +189,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
if (sizeTemp > size)
|
||||
sizeTemp = size;
|
||||
BOOL res = ::ReadFile(GetStdHandle(STD_INPUT_HANDLE), data, sizeTemp, &realProcessedSize, NULL);
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = realProcessedSize;
|
||||
if (res == FALSE && GetLastError() == ERROR_BROKEN_PIPE)
|
||||
return S_OK;
|
||||
@@ -193,7 +197,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
|
||||
#else
|
||||
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
ssize_t res;
|
||||
do
|
||||
@@ -203,7 +207,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
while (res < 0 && (errno == EINTR));
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = (UInt32)res;
|
||||
return S_OK;
|
||||
|
||||
@@ -212,8 +216,7 @@ STDMETHODIMP CStdInFileStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
|
||||
#endif
|
||||
|
||||
STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
|
||||
UInt64 *newPosition)
|
||||
STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
if (seekOrigin >= 3)
|
||||
return STG_E_INVALIDFUNCTION;
|
||||
@@ -221,19 +224,20 @@ STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
|
||||
#ifdef USE_WIN_FILE
|
||||
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
if (File.IsDeviceFile)
|
||||
if (File.IsDeviceFile && (File.SizeDefined || seekOrigin != STREAM_SEEK_END))
|
||||
{
|
||||
UInt64 newVirtPos = offset;
|
||||
switch(seekOrigin)
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: newVirtPos += VirtPos; break;
|
||||
case STREAM_SEEK_END: newVirtPos += File.Length; break;
|
||||
case STREAM_SEEK_CUR: offset += VirtPos; break;
|
||||
case STREAM_SEEK_END: offset += File.Size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
VirtPos = newVirtPos;
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
VirtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = newVirtPos;
|
||||
*newPosition = offset;
|
||||
return S_OK;
|
||||
}
|
||||
#endif
|
||||
@@ -245,7 +249,7 @@ STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
|
||||
PhyPos = VirtPos = realNewPosition;
|
||||
#endif
|
||||
|
||||
if (newPosition != NULL)
|
||||
if (newPosition)
|
||||
*newPosition = realNewPosition;
|
||||
return ConvertBoolToHRESULT(result);
|
||||
|
||||
@@ -254,7 +258,7 @@ STDMETHODIMP CInFileStream::Seek(Int64 offset, UInt32 seekOrigin,
|
||||
off_t res = File.Seek((off_t)offset, seekOrigin);
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (newPosition != NULL)
|
||||
if (newPosition)
|
||||
*newPosition = (UInt64)res;
|
||||
return S_OK;
|
||||
|
||||
@@ -266,6 +270,43 @@ STDMETHODIMP CInFileStream::GetSize(UInt64 *size)
|
||||
return ConvertBoolToHRESULT(File.GetLength(*size));
|
||||
}
|
||||
|
||||
#ifdef USE_WIN_FILE
|
||||
|
||||
STDMETHODIMP CInFileStream::GetProps(UInt64 *size, FILETIME *cTime, FILETIME *aTime, FILETIME *mTime, UInt32 *attrib)
|
||||
{
|
||||
BY_HANDLE_FILE_INFORMATION info;
|
||||
if (File.GetFileInformation(&info))
|
||||
{
|
||||
if (size) *size = (((UInt64)info.nFileSizeHigh) << 32) + info.nFileSizeLow;
|
||||
if (cTime) *cTime = info.ftCreationTime;
|
||||
if (aTime) *aTime = info.ftLastAccessTime;
|
||||
if (mTime) *mTime = info.ftLastWriteTime;
|
||||
if (attrib) *attrib = info.dwFileAttributes;
|
||||
return S_OK;
|
||||
}
|
||||
return GetLastError();
|
||||
}
|
||||
|
||||
STDMETHODIMP CInFileStream::GetProps2(CStreamFileProps *props)
|
||||
{
|
||||
BY_HANDLE_FILE_INFORMATION info;
|
||||
if (File.GetFileInformation(&info))
|
||||
{
|
||||
props->Size = (((UInt64)info.nFileSizeHigh) << 32) + info.nFileSizeLow;
|
||||
props->VolID = info.dwVolumeSerialNumber;
|
||||
props->FileID_Low = (((UInt64)info.nFileIndexHigh) << 32) + info.nFileIndexLow;
|
||||
props->FileID_High = 0;
|
||||
props->NumLinks = SupportHardLinks ? info.nNumberOfLinks : 1;
|
||||
props->Attrib = info.dwFileAttributes;
|
||||
props->CTime = info.ftCreationTime;
|
||||
props->ATime = info.ftLastAccessTime;
|
||||
props->MTime = info.ftLastWriteTime;
|
||||
return S_OK;
|
||||
}
|
||||
return GetLastError();
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
//////////////////////////
|
||||
// COutFileStream
|
||||
@@ -282,18 +323,18 @@ STDMETHODIMP COutFileStream::Write(const void *data, UInt32 size, UInt32 *proces
|
||||
UInt32 realProcessedSize;
|
||||
bool result = File.WritePart(data, size, realProcessedSize);
|
||||
ProcessedSize += realProcessedSize;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = realProcessedSize;
|
||||
return ConvertBoolToHRESULT(result);
|
||||
|
||||
#else
|
||||
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
ssize_t res = File.Write(data, (size_t)size);
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = (UInt32)res;
|
||||
ProcessedSize += res;
|
||||
return S_OK;
|
||||
@@ -309,7 +350,7 @@ STDMETHODIMP COutFileStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPo
|
||||
|
||||
UInt64 realNewPosition;
|
||||
bool result = File.Seek(offset, seekOrigin, realNewPosition);
|
||||
if (newPosition != NULL)
|
||||
if (newPosition)
|
||||
*newPosition = realNewPosition;
|
||||
return ConvertBoolToHRESULT(result);
|
||||
|
||||
@@ -318,7 +359,7 @@ STDMETHODIMP COutFileStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPo
|
||||
off_t res = File.Seek((off_t)offset, seekOrigin);
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (newPosition != NULL)
|
||||
if (newPosition)
|
||||
*newPosition = (UInt64)res;
|
||||
return S_OK;
|
||||
|
||||
@@ -344,14 +385,14 @@ STDMETHODIMP COutFileStream::SetSize(UInt64 newSize)
|
||||
STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
size_t s2 = fwrite(data, 1, size, stdout);
|
||||
if (processedSize != 0)
|
||||
if (processedSize)
|
||||
*processedSize = s2;
|
||||
return (s2 = size) ? S_OK : E_FAIL;
|
||||
return (s2 == size) ? S_OK : E_FAIL;
|
||||
}
|
||||
#else
|
||||
STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
|
||||
#ifdef _WIN32
|
||||
@@ -368,7 +409,7 @@ STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *pro
|
||||
data, sizeTemp, (DWORD *)&realProcessedSize, NULL);
|
||||
size -= realProcessedSize;
|
||||
data = (const void *)((const Byte *)data + realProcessedSize);
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize += realProcessedSize;
|
||||
}
|
||||
return ConvertBoolToHRESULT(res != FALSE);
|
||||
@@ -383,7 +424,7 @@ STDMETHODIMP CStdOutFileStream::Write(const void *data, UInt32 size, UInt32 *pro
|
||||
while (res < 0 && (errno == EINTR));
|
||||
if (res == -1)
|
||||
return E_FAIL;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = (UInt32)res;
|
||||
return S_OK;
|
||||
|
||||
|
||||
28
CPP/7zip/Common/FileStreams.h
Executable file → Normal file
28
CPP/7zip/Common/FileStreams.h
Executable file → Normal file
@@ -22,21 +22,30 @@
|
||||
class CInFileStream:
|
||||
public IInStream,
|
||||
public IStreamGetSize,
|
||||
#ifdef USE_WIN_FILE
|
||||
public IStreamGetProps,
|
||||
public IStreamGetProps2,
|
||||
#endif
|
||||
public CMyUnknownImp
|
||||
{
|
||||
public:
|
||||
#ifdef USE_WIN_FILE
|
||||
NWindows::NFile::NIO::CInFile File;
|
||||
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
UInt64 VirtPos;
|
||||
UInt64 PhyPos;
|
||||
UInt64 BufferStartPos;
|
||||
Byte *Buffer;
|
||||
UInt32 BufferSize;
|
||||
UInt64 BufStartPos;
|
||||
Byte *Buf;
|
||||
UInt32 BufSize;
|
||||
#endif
|
||||
|
||||
#else
|
||||
NC::NFile::NIO::CInFile File;
|
||||
#endif
|
||||
|
||||
bool SupportHardLinks;
|
||||
|
||||
virtual ~CInFileStream();
|
||||
|
||||
#ifdef SUPPORT_DEVICE_FILE
|
||||
@@ -53,12 +62,23 @@ public:
|
||||
return File.OpenShared(fileName, shareForWrite);
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP2(IInStream, IStreamGetSize)
|
||||
MY_QUERYINTERFACE_BEGIN2(IInStream)
|
||||
MY_QUERYINTERFACE_ENTRY(IStreamGetSize)
|
||||
#ifdef USE_WIN_FILE
|
||||
MY_QUERYINTERFACE_ENTRY(IStreamGetProps)
|
||||
MY_QUERYINTERFACE_ENTRY(IStreamGetProps2)
|
||||
#endif
|
||||
MY_QUERYINTERFACE_END
|
||||
MY_ADDREF_RELEASE
|
||||
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
|
||||
STDMETHOD(GetSize)(UInt64 *size);
|
||||
#ifdef USE_WIN_FILE
|
||||
STDMETHOD(GetProps)(UInt64 *size, FILETIME *cTime, FILETIME *aTime, FILETIME *mTime, UInt32 *attrib);
|
||||
STDMETHOD(GetProps2)(CStreamFileProps *props);
|
||||
#endif
|
||||
};
|
||||
|
||||
class CStdInFileStream:
|
||||
|
||||
20
CPP/7zip/Common/FilterCoder.cpp
Executable file → Normal file
20
CPP/7zip/Common/FilterCoder.cpp
Executable file → Normal file
@@ -153,10 +153,16 @@ STDMETHODIMP CFilterCoder::Flush()
|
||||
}
|
||||
|
||||
|
||||
STDMETHODIMP CFilterCoder::SetInStream(ISequentialInStream *inStream)
|
||||
void CFilterCoder::SetInStream_NoSubFilterInit(ISequentialInStream *inStream)
|
||||
{
|
||||
_convertedPosBegin = _convertedPosEnd = _bufferPos = 0;
|
||||
_inStream = inStream;
|
||||
Init2();
|
||||
}
|
||||
|
||||
STDMETHODIMP CFilterCoder::SetInStream(ISequentialInStream *inStream)
|
||||
{
|
||||
SetInStream_NoSubFilterInit(inStream);
|
||||
return Init();
|
||||
}
|
||||
|
||||
@@ -210,10 +216,22 @@ STDMETHODIMP CFilterCoder::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
}
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
|
||||
STDMETHODIMP CFilterCoder::CryptoSetPassword(const Byte *data, UInt32 size)
|
||||
{
|
||||
return _setPassword->CryptoSetPassword(data, size);
|
||||
}
|
||||
|
||||
STDMETHODIMP CFilterCoder::SetKey(const Byte *data, UInt32 size)
|
||||
{
|
||||
return _cryptoProperties->SetKey(data, size);
|
||||
}
|
||||
|
||||
STDMETHODIMP CFilterCoder::SetInitVector(const Byte *data, UInt32 size)
|
||||
{
|
||||
return _cryptoProperties->SetInitVector(data, size);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef EXTRACT_ONLY
|
||||
|
||||
22
CPP/7zip/Common/FilterCoder.h
Executable file → Normal file
22
CPP/7zip/Common/FilterCoder.h
Executable file → Normal file
@@ -7,9 +7,9 @@
|
||||
#include "../ICoder.h"
|
||||
#include "../IPassword.h"
|
||||
|
||||
#define MY_QUERYINTERFACE_ENTRY_AG(i, sub0, sub) if (iid == IID_ ## i) \
|
||||
{ if (!sub) RINOK(sub0->QueryInterface(IID_ ## i, (void **)&sub)) \
|
||||
*outObject = (void *)(i *)this; AddRef(); return S_OK; }
|
||||
#define MY_QUERYINTERFACE_ENTRY_AG(i, sub0, sub) else if (iid == IID_ ## i) \
|
||||
{ if (!sub) RINOK(sub0->QueryInterface(IID_ ## i, (void **)&sub)) \
|
||||
*outObject = (void *)(i *)this; }
|
||||
|
||||
class CFilterCoder:
|
||||
public ICompressCoder,
|
||||
@@ -21,6 +21,7 @@ class CFilterCoder:
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
public ICryptoSetPassword,
|
||||
public ICryptoProperties,
|
||||
#endif
|
||||
#ifndef EXTRACT_ONLY
|
||||
public ICompressSetCoderProperties,
|
||||
@@ -42,14 +43,20 @@ protected:
|
||||
UInt64 _outSize;
|
||||
UInt64 _nowPos64;
|
||||
|
||||
HRESULT Init()
|
||||
void Init2()
|
||||
{
|
||||
_nowPos64 = 0;
|
||||
_outSizeIsDefined = false;
|
||||
}
|
||||
|
||||
HRESULT Init()
|
||||
{
|
||||
Init2();
|
||||
return Filter->Init();
|
||||
}
|
||||
|
||||
CMyComPtr<ICryptoSetPassword> _setPassword;
|
||||
CMyComPtr<ICryptoProperties> _cryptoProperties;
|
||||
#ifndef EXTRACT_ONLY
|
||||
CMyComPtr<ICompressSetCoderProperties> _SetCoderProperties;
|
||||
CMyComPtr<ICompressWriteCoderProperties> _writeCoderProperties;
|
||||
@@ -74,6 +81,7 @@ public:
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
MY_QUERYINTERFACE_ENTRY_AG(ICryptoSetPassword, Filter, _setPassword)
|
||||
MY_QUERYINTERFACE_ENTRY_AG(ICryptoProperties, Filter, _cryptoProperties)
|
||||
#endif
|
||||
|
||||
#ifndef EXTRACT_ONLY
|
||||
@@ -98,6 +106,9 @@ public:
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
STDMETHOD(CryptoSetPassword)(const Byte *data, UInt32 size);
|
||||
|
||||
STDMETHOD(SetKey)(const Byte *data, UInt32 size);
|
||||
STDMETHOD(SetInitVector)(const Byte *data, UInt32 size);
|
||||
#endif
|
||||
#ifndef EXTRACT_ONLY
|
||||
STDMETHOD(SetCoderProperties)(const PROPID *propIDs,
|
||||
@@ -107,6 +118,9 @@ public:
|
||||
STDMETHOD(ResetInitVector)();
|
||||
#endif
|
||||
STDMETHOD(SetDecoderProperties2)(const Byte *data, UInt32 size);
|
||||
|
||||
void SetInStream_NoSubFilterInit(ISequentialInStream *inStream);
|
||||
|
||||
};
|
||||
|
||||
class CInStreamReleaser
|
||||
|
||||
120
CPP/7zip/Common/InBuffer.cpp
Executable file → Normal file
120
CPP/7zip/Common/InBuffer.cpp
Executable file → Normal file
@@ -6,50 +6,49 @@
|
||||
|
||||
#include "InBuffer.h"
|
||||
|
||||
CInBuffer::CInBuffer():
|
||||
_buffer(0),
|
||||
_bufferLimit(0),
|
||||
_bufferBase(0),
|
||||
CInBufferBase::CInBufferBase():
|
||||
_buf(0),
|
||||
_bufLim(0),
|
||||
_bufBase(0),
|
||||
_stream(0),
|
||||
_bufferSize(0)
|
||||
_processedSize(0),
|
||||
_bufSize(0),
|
||||
_wasFinished(false),
|
||||
NumExtraBytes(0)
|
||||
{}
|
||||
|
||||
bool CInBuffer::Create(UInt32 bufferSize)
|
||||
bool CInBuffer::Create(size_t bufSize)
|
||||
{
|
||||
const UInt32 kMinBlockSize = 1;
|
||||
if (bufferSize < kMinBlockSize)
|
||||
bufferSize = kMinBlockSize;
|
||||
if (_bufferBase != 0 && _bufferSize == bufferSize)
|
||||
const unsigned kMinBlockSize = 1;
|
||||
if (bufSize < kMinBlockSize)
|
||||
bufSize = kMinBlockSize;
|
||||
if (_bufBase != 0 && _bufSize == bufSize)
|
||||
return true;
|
||||
Free();
|
||||
_bufferSize = bufferSize;
|
||||
_bufferBase = (Byte *)::MidAlloc(bufferSize);
|
||||
return (_bufferBase != 0);
|
||||
_bufSize = bufSize;
|
||||
_bufBase = (Byte *)::MidAlloc(bufSize);
|
||||
return (_bufBase != 0);
|
||||
}
|
||||
|
||||
void CInBuffer::Free()
|
||||
{
|
||||
::MidFree(_bufferBase);
|
||||
_bufferBase = 0;
|
||||
::MidFree(_bufBase);
|
||||
_bufBase = 0;
|
||||
}
|
||||
|
||||
void CInBuffer::SetStream(ISequentialInStream *stream)
|
||||
{
|
||||
_stream = stream;
|
||||
}
|
||||
|
||||
void CInBuffer::Init()
|
||||
void CInBufferBase::Init()
|
||||
{
|
||||
_processedSize = 0;
|
||||
_buffer = _bufferBase;
|
||||
_bufferLimit = _buffer;
|
||||
_buf = _bufBase;
|
||||
_bufLim = _buf;
|
||||
_wasFinished = false;
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
ErrorCode = S_OK;
|
||||
#endif
|
||||
NumExtraBytes = 0;
|
||||
}
|
||||
|
||||
bool CInBuffer::ReadBlock()
|
||||
bool CInBufferBase::ReadBlock()
|
||||
{
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
if (ErrorCode != S_OK)
|
||||
@@ -57,27 +56,80 @@ bool CInBuffer::ReadBlock()
|
||||
#endif
|
||||
if (_wasFinished)
|
||||
return false;
|
||||
_processedSize += (_buffer - _bufferBase);
|
||||
UInt32 numProcessedBytes;
|
||||
HRESULT result = _stream->Read(_bufferBase, _bufferSize, &numProcessedBytes);
|
||||
_processedSize += (_buf - _bufBase);
|
||||
_buf = _bufBase;
|
||||
_bufLim = _bufBase;
|
||||
UInt32 processed;
|
||||
// FIX_ME: we can improve it to support (_bufSize >= (1 << 32))
|
||||
HRESULT result = _stream->Read(_bufBase, (UInt32)_bufSize, &processed);
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
ErrorCode = result;
|
||||
#else
|
||||
if (result != S_OK)
|
||||
throw CInBufferException(result);
|
||||
#endif
|
||||
_buffer = _bufferBase;
|
||||
_bufferLimit = _buffer + numProcessedBytes;
|
||||
_wasFinished = (numProcessedBytes == 0);
|
||||
return (!_wasFinished);
|
||||
_bufLim = _buf + processed;
|
||||
_wasFinished = (processed == 0);
|
||||
return !_wasFinished;
|
||||
}
|
||||
|
||||
Byte CInBuffer::ReadBlock2()
|
||||
bool CInBufferBase::ReadByte_FromNewBlock(Byte &b)
|
||||
{
|
||||
if (!ReadBlock())
|
||||
{
|
||||
_processedSize++;
|
||||
NumExtraBytes++;
|
||||
b = 0xFF;
|
||||
return false;
|
||||
}
|
||||
b = *_buf++;
|
||||
return true;
|
||||
}
|
||||
|
||||
Byte CInBufferBase::ReadByte_FromNewBlock()
|
||||
{
|
||||
if (!ReadBlock())
|
||||
{
|
||||
NumExtraBytes++;
|
||||
return 0xFF;
|
||||
}
|
||||
return *_buffer++;
|
||||
return *_buf++;
|
||||
}
|
||||
|
||||
size_t CInBufferBase::ReadBytes(Byte *buf, size_t size)
|
||||
{
|
||||
if ((size_t)(_bufLim - _buf) >= size)
|
||||
{
|
||||
const Byte *src = _buf;
|
||||
for (size_t i = 0; i < size; i++)
|
||||
buf[i] = src[i];
|
||||
_buf += size;
|
||||
return size;
|
||||
}
|
||||
for (size_t i = 0; i < size; i++)
|
||||
{
|
||||
if (_buf >= _bufLim)
|
||||
if (!ReadBlock())
|
||||
return i;
|
||||
buf[i] = *_buf++;
|
||||
}
|
||||
return size;
|
||||
}
|
||||
|
||||
size_t CInBufferBase::Skip(size_t size)
|
||||
{
|
||||
size_t processed = 0;
|
||||
for (;;)
|
||||
{
|
||||
size_t rem = (_bufLim - _buf);
|
||||
if (rem >= size)
|
||||
{
|
||||
_buf += size;
|
||||
return processed + size;
|
||||
}
|
||||
_buf += rem;
|
||||
processed += rem;
|
||||
size -= rem;
|
||||
if (!ReadBlock())
|
||||
return processed;
|
||||
}
|
||||
}
|
||||
|
||||
99
CPP/7zip/Common/InBuffer.h
Executable file → Normal file
99
CPP/7zip/Common/InBuffer.h
Executable file → Normal file
@@ -1,11 +1,10 @@
|
||||
// InBuffer.h
|
||||
|
||||
#ifndef __INBUFFER_H
|
||||
#define __INBUFFER_H
|
||||
#ifndef __IN_BUFFER_H
|
||||
#define __IN_BUFFER_H
|
||||
|
||||
#include "../IStream.h"
|
||||
#include "../../Common/MyCom.h"
|
||||
#include "../../Common/MyException.h"
|
||||
#include "../IStream.h"
|
||||
|
||||
#ifndef _NO_EXCEPTIONS
|
||||
struct CInBufferException: public CSystemException
|
||||
@@ -14,68 +13,78 @@ struct CInBufferException: public CSystemException
|
||||
};
|
||||
#endif
|
||||
|
||||
class CInBuffer
|
||||
class CInBufferBase
|
||||
{
|
||||
Byte *_buffer;
|
||||
Byte *_bufferLimit;
|
||||
Byte *_bufferBase;
|
||||
CMyComPtr<ISequentialInStream> _stream;
|
||||
protected:
|
||||
Byte *_buf;
|
||||
Byte *_bufLim;
|
||||
Byte *_bufBase;
|
||||
|
||||
ISequentialInStream *_stream;
|
||||
UInt64 _processedSize;
|
||||
UInt32 _bufferSize;
|
||||
size_t _bufSize; // actually it's number of Bytes for next read. The buf can be larger
|
||||
// only up to 32-bits values now are supported!
|
||||
bool _wasFinished;
|
||||
|
||||
bool ReadBlock();
|
||||
Byte ReadBlock2();
|
||||
bool ReadByte_FromNewBlock(Byte &b);
|
||||
Byte ReadByte_FromNewBlock();
|
||||
|
||||
public:
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
HRESULT ErrorCode;
|
||||
#endif
|
||||
UInt32 NumExtraBytes;
|
||||
|
||||
CInBuffer();
|
||||
~CInBuffer() { Free(); }
|
||||
CInBufferBase() throw();
|
||||
|
||||
bool Create(UInt32 bufferSize);
|
||||
void Free();
|
||||
UInt64 GetStreamSize() const { return _processedSize + (_buf - _bufBase); }
|
||||
UInt64 GetProcessedSize() const { return _processedSize + NumExtraBytes + (_buf - _bufBase); }
|
||||
bool WasFinished() const { return _wasFinished; }
|
||||
|
||||
void SetStream(ISequentialInStream *stream) { _stream = stream; }
|
||||
|
||||
void SetStream(ISequentialInStream *stream);
|
||||
void Init();
|
||||
void ReleaseStream() { _stream.Release(); }
|
||||
void SetBuf(Byte *buf, size_t bufSize, size_t end, size_t pos)
|
||||
{
|
||||
_bufBase = buf;
|
||||
_bufSize = bufSize;
|
||||
_processedSize = 0;
|
||||
_buf = buf + pos;
|
||||
_bufLim = buf + end;
|
||||
_wasFinished = false;
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
ErrorCode = S_OK;
|
||||
#endif
|
||||
NumExtraBytes = 0;
|
||||
}
|
||||
|
||||
void Init() throw();
|
||||
|
||||
bool ReadByte(Byte &b)
|
||||
{
|
||||
if (_buffer >= _bufferLimit)
|
||||
if (!ReadBlock())
|
||||
return false;
|
||||
b = *_buffer++;
|
||||
if (_buf >= _bufLim)
|
||||
return ReadByte_FromNewBlock(b);
|
||||
b = *_buf++;
|
||||
return true;
|
||||
}
|
||||
|
||||
Byte ReadByte()
|
||||
{
|
||||
if (_buffer >= _bufferLimit)
|
||||
return ReadBlock2();
|
||||
return *_buffer++;
|
||||
if (_buf >= _bufLim)
|
||||
return ReadByte_FromNewBlock();
|
||||
return *_buf++;
|
||||
}
|
||||
UInt32 ReadBytes(Byte *buf, UInt32 size)
|
||||
{
|
||||
if ((UInt32)(_bufferLimit - _buffer) >= size)
|
||||
{
|
||||
for (UInt32 i = 0; i < size; i++)
|
||||
buf[i] = _buffer[i];
|
||||
_buffer += size;
|
||||
return size;
|
||||
}
|
||||
for (UInt32 i = 0; i < size; i++)
|
||||
{
|
||||
if (_buffer >= _bufferLimit)
|
||||
if (!ReadBlock())
|
||||
return i;
|
||||
buf[i] = *_buffer++;
|
||||
}
|
||||
return size;
|
||||
}
|
||||
UInt64 GetProcessedSize() const { return _processedSize + (_buffer - _bufferBase); }
|
||||
bool WasFinished() const { return _wasFinished; }
|
||||
|
||||
size_t ReadBytes(Byte *buf, size_t size);
|
||||
size_t Skip(size_t size);
|
||||
};
|
||||
|
||||
class CInBuffer: public CInBufferBase
|
||||
{
|
||||
public:
|
||||
~CInBuffer() { Free(); }
|
||||
bool Create(size_t bufSize) throw(); // only up to 32-bits values now are supported!
|
||||
void Free() throw();
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
2
CPP/7zip/Common/InMemStream.cpp
Executable file → Normal file
2
CPP/7zip/Common/InMemStream.cpp
Executable file → Normal file
@@ -178,7 +178,7 @@ HRESULT CInMemStreamMt::ReadSubStream(int subStreamIndex, void *data, UInt32 siz
|
||||
if (curSize > size)
|
||||
curSize = size;
|
||||
void *p = blocks.Blocks[blocks.CurBlockIndex];
|
||||
memmove(data, (const Byte *)p + curPos, curSize);
|
||||
memcpy(data, (const Byte *)p + curPos, curSize);
|
||||
data = (void *)((Byte *)data + curSize);
|
||||
size -= curSize;
|
||||
if (processedSize != NULL)
|
||||
|
||||
0
CPP/7zip/Common/InMemStream.h
Executable file → Normal file
0
CPP/7zip/Common/InMemStream.h
Executable file → Normal file
4
CPP/7zip/Common/InOutTempBuffer.cpp
Executable file → Normal file
4
CPP/7zip/Common/InOutTempBuffer.cpp
Executable file → Normal file
@@ -4,12 +4,14 @@
|
||||
|
||||
#include "../../../C/7zCrc.h"
|
||||
|
||||
#include "../../Common/Defs.h"
|
||||
|
||||
#include "InOutTempBuffer.h"
|
||||
#include "StreamUtils.h"
|
||||
|
||||
using namespace NWindows;
|
||||
using namespace NFile;
|
||||
using namespace NDirectory;
|
||||
using namespace NDir;
|
||||
|
||||
static const UInt32 kTempBufSize = (1 << 20);
|
||||
|
||||
|
||||
2
CPP/7zip/Common/InOutTempBuffer.h
Executable file → Normal file
2
CPP/7zip/Common/InOutTempBuffer.h
Executable file → Normal file
@@ -10,7 +10,7 @@
|
||||
|
||||
class CInOutTempBuffer
|
||||
{
|
||||
NWindows::NFile::NDirectory::CTempFile _tempFile;
|
||||
NWindows::NFile::NDir::CTempFile _tempFile;
|
||||
NWindows::NFile::NIO::COutFile _outFile;
|
||||
Byte *_buf;
|
||||
UInt32 _bufPos;
|
||||
|
||||
253
CPP/7zip/Common/LimitedStreams.cpp
Executable file → Normal file
253
CPP/7zip/Common/LimitedStreams.cpp
Executable file → Normal file
@@ -17,17 +17,21 @@ STDMETHODIMP CLimitedSequentialInStream::Read(void *data, UInt32 size, UInt32 *p
|
||||
if (realProcessedSize == 0)
|
||||
_wasFinished = true;
|
||||
}
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = realProcessedSize;
|
||||
return result;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLimitedInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (_virtPos >= _size)
|
||||
return (_virtPos == _size) ? S_OK: E_FAIL;
|
||||
{
|
||||
// 9.31: Fixed. Windows doesn't return error in ReadFile and IStream->Read in that case.
|
||||
return S_OK;
|
||||
// return (_virtPos == _size) ? S_OK: E_FAIL; // ERROR_HANDLE_EOF
|
||||
}
|
||||
UInt64 rem = _size - _virtPos;
|
||||
if (rem < size)
|
||||
size = (UInt32)rem;
|
||||
@@ -38,7 +42,7 @@ STDMETHODIMP CLimitedInStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
RINOK(SeekToPhys());
|
||||
}
|
||||
HRESULT res = _stream->Read(data, size, &size);
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
_physPos += size;
|
||||
_virtPos += size;
|
||||
@@ -47,24 +51,39 @@ STDMETHODIMP CLimitedInStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
|
||||
STDMETHODIMP CLimitedInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch(seekOrigin)
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: _virtPos = offset; break;
|
||||
case STREAM_SEEK_CUR: _virtPos += offset; break;
|
||||
case STREAM_SEEK_END: _virtPos = _size + offset; break;
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END: offset += _size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream)
|
||||
{
|
||||
*resStream = 0;
|
||||
CLimitedInStream *streamSpec = new CLimitedInStream;
|
||||
CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
|
||||
streamSpec->SetStream(inStream);
|
||||
RINOK(streamSpec->InitAndSeek(pos, size));
|
||||
streamSpec->SeekToStart();
|
||||
*resStream = streamTemp.Detach();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CClusterInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (_virtPos >= Size)
|
||||
return (_virtPos == Size) ? S_OK: E_FAIL;
|
||||
return S_OK;
|
||||
|
||||
if (_curRem == 0)
|
||||
{
|
||||
@@ -88,7 +107,7 @@ STDMETHODIMP CClusterInStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
if (size > _curRem)
|
||||
size = _curRem;
|
||||
HRESULT res = Stream->Read(data, size, &size);
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
_physPos += size;
|
||||
_virtPos += size;
|
||||
@@ -98,39 +117,88 @@ STDMETHODIMP CClusterInStream::Read(void *data, UInt32 size, UInt32 *processedSi
|
||||
|
||||
STDMETHODIMP CClusterInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
UInt64 newVirtPos = offset;
|
||||
switch(seekOrigin)
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: newVirtPos += _virtPos; break;
|
||||
case STREAM_SEEK_END: newVirtPos += Size; break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END: offset += Size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (_virtPos != newVirtPos)
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
if (_virtPos != (UInt64)offset)
|
||||
_curRem = 0;
|
||||
_virtPos = newVirtPos;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = newVirtPos;
|
||||
*newPosition = offset;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream)
|
||||
STDMETHODIMP CExtentsStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
*resStream = 0;
|
||||
CLimitedInStream *streamSpec = new CLimitedInStream;
|
||||
CMyComPtr<ISequentialInStream> streamTemp = streamSpec;
|
||||
streamSpec->SetStream(inStream);
|
||||
RINOK(streamSpec->InitAndSeek(pos, size));
|
||||
streamSpec->SeekToStart();
|
||||
*resStream = streamTemp.Detach();
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (_virtPos >= Extents.Back().Virt)
|
||||
return S_OK;
|
||||
if (size == 0)
|
||||
return S_OK;
|
||||
|
||||
unsigned left = 0, right = Extents.Size() - 1;
|
||||
for (;;)
|
||||
{
|
||||
unsigned mid = (left + right) / 2;
|
||||
if (mid == left)
|
||||
break;
|
||||
if (_virtPos < Extents[mid].Virt)
|
||||
right = mid;
|
||||
else
|
||||
left = mid;
|
||||
}
|
||||
|
||||
const CSeekExtent &extent = Extents[left];
|
||||
UInt64 phyPos = extent.Phy + (_virtPos - extent.Virt);
|
||||
if (_needStartSeek || _phyPos != phyPos)
|
||||
{
|
||||
_needStartSeek = false;
|
||||
_phyPos = phyPos;
|
||||
RINOK(SeekToPhys());
|
||||
}
|
||||
|
||||
UInt64 rem = Extents[left + 1].Virt - _virtPos;
|
||||
if (size > rem)
|
||||
size = (UInt32)rem;
|
||||
|
||||
HRESULT res = Stream->Read(data, size, &size);
|
||||
_phyPos += size;
|
||||
_virtPos += size;
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
return res;
|
||||
}
|
||||
|
||||
STDMETHODIMP CExtentsStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END: offset += Extents.Back().Virt; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
STDMETHODIMP CLimitedSequentialOutStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
HRESULT result = S_OK;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (size > _size)
|
||||
{
|
||||
@@ -139,7 +207,7 @@ STDMETHODIMP CLimitedSequentialOutStream::Write(const void *data, UInt32 size, U
|
||||
_overflow = true;
|
||||
if (!_overflowIsAllowed)
|
||||
return E_FAIL;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
return S_OK;
|
||||
}
|
||||
@@ -148,7 +216,134 @@ STDMETHODIMP CLimitedSequentialOutStream::Write(const void *data, UInt32 size, U
|
||||
if (_stream)
|
||||
result = _stream->Write(data, size, &size);
|
||||
_size -= size;
|
||||
if (processedSize != NULL)
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
STDMETHODIMP CTailInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
UInt32 cur;
|
||||
HRESULT res = Stream->Read(data, size, &cur);
|
||||
if (processedSize)
|
||||
*processedSize = cur;
|
||||
_virtPos += cur;
|
||||
return res;
|
||||
}
|
||||
|
||||
STDMETHODIMP CTailInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END:
|
||||
{
|
||||
UInt64 pos = 0;
|
||||
RINOK(Stream->Seek(offset, STREAM_SEEK_END, &pos));
|
||||
if (pos < Offset)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = pos - Offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return S_OK;
|
||||
}
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return Stream->Seek(Offset + _virtPos, STREAM_SEEK_SET, NULL);
|
||||
}
|
||||
|
||||
STDMETHODIMP CLimitedCachedInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
if (processedSize)
|
||||
*processedSize = 0;
|
||||
if (_virtPos >= _size)
|
||||
{
|
||||
// 9.31: Fixed. Windows doesn't return error in ReadFile and IStream->Read in that case.
|
||||
return S_OK;
|
||||
// return (_virtPos == _size) ? S_OK: E_FAIL; // ERROR_HANDLE_EOF
|
||||
}
|
||||
UInt64 rem = _size - _virtPos;
|
||||
if (rem < size)
|
||||
size = (UInt32)rem;
|
||||
|
||||
UInt64 newPos = _startOffset + _virtPos;
|
||||
UInt64 offsetInCache = newPos - _cachePhyPos;
|
||||
HRESULT res = S_OK;
|
||||
if (newPos >= _cachePhyPos &&
|
||||
offsetInCache <= _cacheSize &&
|
||||
size <= _cacheSize - (size_t)offsetInCache)
|
||||
memcpy(data, _cache + (size_t)offsetInCache, size);
|
||||
else
|
||||
{
|
||||
if (newPos != _physPos)
|
||||
{
|
||||
_physPos = newPos;
|
||||
RINOK(SeekToPhys());
|
||||
}
|
||||
res = _stream->Read(data, size, &size);
|
||||
_physPos += size;
|
||||
}
|
||||
if (processedSize)
|
||||
*processedSize = size;
|
||||
_virtPos += size;
|
||||
return res;
|
||||
}
|
||||
|
||||
STDMETHODIMP CLimitedCachedInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END: offset += _size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP CTailOutStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
UInt32 cur;
|
||||
HRESULT res = Stream->Write(data, size, &cur);
|
||||
if (processedSize)
|
||||
*processedSize = cur;
|
||||
_virtPos += cur;
|
||||
if (_virtSize < _virtPos)
|
||||
_virtSize = _virtPos;
|
||||
return res;
|
||||
}
|
||||
|
||||
STDMETHODIMP CTailOutStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _virtPos; break;
|
||||
case STREAM_SEEK_END: offset += _virtSize; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_virtPos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _virtPos;
|
||||
return Stream->Seek(Offset + _virtPos, STREAM_SEEK_SET, NULL);
|
||||
}
|
||||
|
||||
STDMETHODIMP CTailOutStream::SetSize(UInt64 newSize)
|
||||
{
|
||||
_virtSize = newSize;
|
||||
return Stream->SetSize(Offset + newSize);
|
||||
}
|
||||
|
||||
138
CPP/7zip/Common/LimitedStreams.h
Executable file → Normal file
138
CPP/7zip/Common/LimitedStreams.h
Executable file → Normal file
@@ -3,6 +3,7 @@
|
||||
#ifndef __LIMITED_STREAMS_H
|
||||
#define __LIMITED_STREAMS_H
|
||||
|
||||
#include "../../Common/MyBuffer.h"
|
||||
#include "../../Common/MyCom.h"
|
||||
#include "../../Common/MyVector.h"
|
||||
#include "../IStream.h"
|
||||
@@ -25,7 +26,7 @@ public:
|
||||
_wasFinished = false;
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP
|
||||
MY_UNKNOWN_IMP1(ISequentialInStream)
|
||||
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
UInt64 GetSize() const { return _pos; }
|
||||
@@ -54,7 +55,7 @@ public:
|
||||
return SeekToPhys();
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP1(IInStream)
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, IInStream)
|
||||
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
@@ -62,6 +63,8 @@ public:
|
||||
HRESULT SeekToStart() { return Seek(0, STREAM_SEEK_SET, NULL); }
|
||||
};
|
||||
|
||||
HRESULT CreateLimitedInStream(IInStream *inStream, UInt64 pos, UInt64 size, ISequentialInStream **resStream);
|
||||
|
||||
class CClusterInStream:
|
||||
public IInStream,
|
||||
public CMyUnknownImp
|
||||
@@ -73,7 +76,7 @@ public:
|
||||
CMyComPtr<IInStream> Stream;
|
||||
UInt64 StartOffset;
|
||||
UInt64 Size;
|
||||
int BlockSizeLog;
|
||||
unsigned BlockSizeLog;
|
||||
CRecordVector<UInt32> Vector;
|
||||
|
||||
HRESULT SeekToPhys() { return Stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
|
||||
@@ -91,13 +94,44 @@ public:
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP1(IInStream)
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, 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);
|
||||
struct CSeekExtent
|
||||
{
|
||||
UInt64 Phy;
|
||||
UInt64 Virt;
|
||||
};
|
||||
|
||||
class CExtentsStream:
|
||||
public IInStream,
|
||||
public CMyUnknownImp
|
||||
{
|
||||
UInt64 _phyPos;
|
||||
UInt64 _virtPos;
|
||||
bool _needStartSeek;
|
||||
|
||||
HRESULT SeekToPhys() { return Stream->Seek(_phyPos, STREAM_SEEK_SET, NULL); }
|
||||
|
||||
public:
|
||||
CMyComPtr<IInStream> Stream;
|
||||
CRecordVector<CSeekExtent> Extents;
|
||||
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, IInStream)
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
void ReleaseStream() { Stream.Release(); }
|
||||
|
||||
void Init()
|
||||
{
|
||||
_virtPos = 0;
|
||||
_phyPos = 0;
|
||||
_needStartSeek = true;
|
||||
}
|
||||
};
|
||||
|
||||
class CLimitedSequentialOutStream:
|
||||
public ISequentialOutStream,
|
||||
@@ -108,7 +142,7 @@ class CLimitedSequentialOutStream:
|
||||
bool _overflow;
|
||||
bool _overflowIsAllowed;
|
||||
public:
|
||||
MY_UNKNOWN_IMP
|
||||
MY_UNKNOWN_IMP1(ISequentialOutStream)
|
||||
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
|
||||
void SetStream(ISequentialOutStream *stream) { _stream = stream; }
|
||||
void ReleaseStream() { _stream.Release(); }
|
||||
@@ -122,4 +156,96 @@ public:
|
||||
UInt64 GetRem() const { return _size; }
|
||||
};
|
||||
|
||||
|
||||
class CTailInStream:
|
||||
public IInStream,
|
||||
public CMyUnknownImp
|
||||
{
|
||||
UInt64 _virtPos;
|
||||
public:
|
||||
CMyComPtr<IInStream> Stream;
|
||||
UInt64 Offset;
|
||||
|
||||
void Init()
|
||||
{
|
||||
_virtPos = 0;
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, IInStream)
|
||||
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
|
||||
HRESULT SeekToStart() { return Stream->Seek(Offset, STREAM_SEEK_SET, NULL); }
|
||||
};
|
||||
|
||||
class CLimitedCachedInStream:
|
||||
public IInStream,
|
||||
public CMyUnknownImp
|
||||
{
|
||||
CMyComPtr<IInStream> _stream;
|
||||
UInt64 _virtPos;
|
||||
UInt64 _physPos;
|
||||
UInt64 _size;
|
||||
UInt64 _startOffset;
|
||||
|
||||
const Byte *_cache;
|
||||
size_t _cacheSize;
|
||||
size_t _cachePhyPos;
|
||||
|
||||
|
||||
HRESULT SeekToPhys() { return _stream->Seek(_physPos, STREAM_SEEK_SET, NULL); }
|
||||
public:
|
||||
CByteBuffer Buffer;
|
||||
|
||||
void SetStream(IInStream *stream) { _stream = stream; }
|
||||
void SetCache(size_t cacheSize, size_t cachePos)
|
||||
{
|
||||
_cache = Buffer;
|
||||
_cacheSize = cacheSize;
|
||||
_cachePhyPos = cachePos;
|
||||
}
|
||||
|
||||
HRESULT InitAndSeek(UInt64 startOffset, UInt64 size)
|
||||
{
|
||||
_startOffset = startOffset;
|
||||
_physPos = startOffset;
|
||||
_virtPos = 0;
|
||||
_size = size;
|
||||
return SeekToPhys();
|
||||
}
|
||||
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, 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 CTailOutStream:
|
||||
public IOutStream,
|
||||
public CMyUnknownImp
|
||||
{
|
||||
UInt64 _virtPos;
|
||||
UInt64 _virtSize;
|
||||
public:
|
||||
CMyComPtr<IOutStream> Stream;
|
||||
UInt64 Offset;
|
||||
|
||||
virtual ~CTailOutStream() {}
|
||||
|
||||
MY_UNKNOWN_IMP2(ISequentialOutStream, IOutStream)
|
||||
|
||||
void Init()
|
||||
{
|
||||
_virtPos = 0;
|
||||
_virtSize = 0;
|
||||
}
|
||||
|
||||
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
STDMETHOD(SetSize)(UInt64 newSize);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
0
CPP/7zip/Common/LockedStream.cpp
Executable file → Normal file
0
CPP/7zip/Common/LockedStream.cpp
Executable file → Normal file
0
CPP/7zip/Common/LockedStream.h
Executable file → Normal file
0
CPP/7zip/Common/LockedStream.h
Executable file → Normal file
4
CPP/7zip/Common/MemBlocks.cpp
Executable file → Normal file
4
CPP/7zip/Common/MemBlocks.cpp
Executable file → Normal file
@@ -120,7 +120,7 @@ void CMemBlocks::FreeOpt(CMemBlockManagerMt *manager)
|
||||
HRESULT CMemBlocks::WriteToStream(size_t blockSize, ISequentialOutStream *outStream) const
|
||||
{
|
||||
UInt64 totalSize = TotalSize;
|
||||
for (int blockIndex = 0; totalSize > 0; blockIndex++)
|
||||
for (unsigned blockIndex = 0; totalSize > 0; blockIndex++)
|
||||
{
|
||||
UInt32 curSize = (UInt32)blockSize;
|
||||
if (totalSize < curSize)
|
||||
@@ -169,7 +169,7 @@ void CMemLockBlocks::Detach(CMemLockBlocks &blocks, CMemBlockManagerMt *memManag
|
||||
blocks.LockMode = LockMode;
|
||||
UInt64 totalSize = 0;
|
||||
size_t blockSize = memManager->GetBlockSize();
|
||||
for (int i = 0; i < Blocks.Size(); i++)
|
||||
FOR_VECTOR (i, Blocks)
|
||||
{
|
||||
if (totalSize < TotalSize)
|
||||
blocks.Blocks.Add(Blocks[i]);
|
||||
|
||||
4
CPP/7zip/Common/MemBlocks.h
Executable file → Normal file
4
CPP/7zip/Common/MemBlocks.h
Executable file → Normal file
@@ -3,9 +3,9 @@
|
||||
#ifndef __MEM_BLOCKS_H
|
||||
#define __MEM_BLOCKS_H
|
||||
|
||||
#include "Common/MyVector.h"
|
||||
#include "../../Common/MyVector.h"
|
||||
|
||||
#include "Windows/Synchronization.h"
|
||||
#include "../../Windows/Synchronization.h"
|
||||
|
||||
#include "../IStream.h"
|
||||
|
||||
|
||||
0
CPP/7zip/Common/MethodId.cpp
Executable file → Normal file
0
CPP/7zip/Common/MethodId.cpp
Executable file → Normal file
2
CPP/7zip/Common/MethodId.h
Executable file → Normal file
2
CPP/7zip/Common/MethodId.h
Executable file → Normal file
@@ -3,7 +3,7 @@
|
||||
#ifndef __7Z_METHOD_ID_H
|
||||
#define __7Z_METHOD_ID_H
|
||||
|
||||
#include "../../Common/Types.h"
|
||||
#include "../../Common/MyTypes.h"
|
||||
|
||||
typedef UInt64 CMethodId;
|
||||
|
||||
|
||||
131
CPP/7zip/Common/MethodProps.cpp
Executable file → Normal file
131
CPP/7zip/Common/MethodProps.cpp
Executable file → Normal file
@@ -10,12 +10,12 @@ using namespace NWindows;
|
||||
|
||||
bool StringToBool(const UString &s, bool &res)
|
||||
{
|
||||
if (s.IsEmpty() || s.CompareNoCase(L"ON") == 0 || s.Compare(L"+") == 0)
|
||||
if (s.IsEmpty() || s == L"+" || StringsAreEqualNoCase_Ascii(s, "ON"))
|
||||
{
|
||||
res = true;
|
||||
return true;
|
||||
}
|
||||
if (s.CompareNoCase(L"OFF") == 0 || s.Compare(L"-") == 0)
|
||||
if (s == L"-" || StringsAreEqualNoCase_Ascii(s, "OFF"))
|
||||
{
|
||||
res = false;
|
||||
return true;
|
||||
@@ -34,18 +34,12 @@ HRESULT PROPVARIANT_to_bool(const PROPVARIANT &prop, bool &dest)
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
int ParseStringToUInt32(const UString &srcString, UInt32 &number)
|
||||
unsigned ParseStringToUInt32(const UString &srcString, UInt32 &number)
|
||||
{
|
||||
const wchar_t *start = srcString;
|
||||
const wchar_t *end;
|
||||
UInt64 number64 = ConvertStringToUInt64(start, &end);
|
||||
if (number64 > (UInt32)0xFFFFFFFF)
|
||||
{
|
||||
number = 0;
|
||||
return 0;
|
||||
}
|
||||
number = (UInt32)number64;
|
||||
return (int)(end - start);
|
||||
number = ConvertStringToUInt32(start, &end);
|
||||
return (unsigned)(end - start);
|
||||
}
|
||||
|
||||
HRESULT ParsePropToUInt32(const UString &name, const PROPVARIANT &prop, UInt32 &resValue)
|
||||
@@ -66,7 +60,7 @@ HRESULT ParsePropToUInt32(const UString &name, const PROPVARIANT &prop, UInt32 &
|
||||
if (name.IsEmpty())
|
||||
return S_OK;
|
||||
UInt32 v;
|
||||
if (ParseStringToUInt32(name, v) != name.Length())
|
||||
if (ParseStringToUInt32(name, v) != name.Len())
|
||||
return E_INVALIDARG;
|
||||
resValue = v;
|
||||
return S_OK;
|
||||
@@ -96,36 +90,33 @@ HRESULT ParseMtProp(const UString &name, const PROPVARIANT &prop, UInt32 default
|
||||
return ParsePropToUInt32(name, prop, numThreads);
|
||||
}
|
||||
|
||||
static HRESULT StringToDictSize(const UString &srcStringSpec, UInt32 &dicSize)
|
||||
static HRESULT StringToDictSize(const UString &s, UInt32 &dicSize)
|
||||
{
|
||||
UString srcString = srcStringSpec;
|
||||
srcString.MakeUpper();
|
||||
const wchar_t *start = srcString;
|
||||
const wchar_t *end;
|
||||
UInt64 number = ConvertStringToUInt64(start, &end);
|
||||
int numDigits = (int)(end - start);
|
||||
if (numDigits == 0 || srcString.Length() > numDigits + 1)
|
||||
UInt32 number = ConvertStringToUInt32(s, &end);
|
||||
unsigned numDigits = (unsigned)(end - s);
|
||||
if (numDigits == 0 || s.Len() > numDigits + 1)
|
||||
return E_INVALIDARG;
|
||||
const unsigned kLogDictSizeLimit = 32;
|
||||
if (srcString.Length() == numDigits)
|
||||
if (s.Len() == numDigits)
|
||||
{
|
||||
if (number >= kLogDictSizeLimit)
|
||||
return E_INVALIDARG;
|
||||
dicSize = (UInt32)1 << (int)number;
|
||||
dicSize = (UInt32)1 << (unsigned)number;
|
||||
return S_OK;
|
||||
}
|
||||
unsigned numBits;
|
||||
switch (srcString[numDigits])
|
||||
switch (MyCharLower_Ascii(s[numDigits]))
|
||||
{
|
||||
case 'B': numBits = 0; break;
|
||||
case 'K': numBits = 10; break;
|
||||
case 'M': numBits = 20; break;
|
||||
case 'G': numBits = 30; break;
|
||||
case 'b': dicSize = number; return S_OK;
|
||||
case 'k': numBits = 10; break;
|
||||
case 'm': numBits = 20; break;
|
||||
case 'g': numBits = 30; break;
|
||||
default: return E_INVALIDARG;
|
||||
}
|
||||
if (number >= ((UInt64)1 << (kLogDictSizeLimit - numBits)))
|
||||
if (number >= ((UInt32)1 << (kLogDictSizeLimit - numBits)))
|
||||
return E_INVALIDARG;
|
||||
dicSize = (UInt32)number << numBits;
|
||||
dicSize = number << numBits;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -191,7 +182,7 @@ void CCoderProps::AddProp(const CProp &prop)
|
||||
HRESULT CProps::SetCoderProps(ICompressSetCoderProperties *scp, const UInt64 *dataSizeReduce) const
|
||||
{
|
||||
CCoderProps coderProps(Props.Size() + (dataSizeReduce ? 1 : 0));
|
||||
for (int i = 0; i < Props.Size(); i++)
|
||||
FOR_VECTOR (i, Props)
|
||||
coderProps.AddProp(Props[i]);
|
||||
if (dataSizeReduce)
|
||||
{
|
||||
@@ -226,34 +217,34 @@ int CMethodProps::GetLevel() const
|
||||
struct CNameToPropID
|
||||
{
|
||||
VARTYPE VarType;
|
||||
const wchar_t *Name;
|
||||
const char *Name;
|
||||
};
|
||||
|
||||
static const CNameToPropID g_NameToPropID[] =
|
||||
{
|
||||
{ VT_UI4, L"" },
|
||||
{ VT_UI4, L"d" },
|
||||
{ VT_UI4, L"mem" },
|
||||
{ VT_UI4, L"o" },
|
||||
{ VT_UI4, L"c" },
|
||||
{ VT_UI4, L"pb" },
|
||||
{ VT_UI4, L"lc" },
|
||||
{ VT_UI4, L"lp" },
|
||||
{ VT_UI4, L"fb" },
|
||||
{ VT_BSTR, L"mf" },
|
||||
{ VT_UI4, L"mc" },
|
||||
{ VT_UI4, L"pass" },
|
||||
{ VT_UI4, L"a" },
|
||||
{ VT_UI4, L"mt" },
|
||||
{ VT_BOOL, L"eos" },
|
||||
{ VT_UI4, L"x" },
|
||||
{ VT_UI4, L"reduceSize" }
|
||||
{ VT_UI4, "" },
|
||||
{ VT_UI4, "d" },
|
||||
{ VT_UI4, "mem" },
|
||||
{ VT_UI4, "o" },
|
||||
{ VT_UI4, "c" },
|
||||
{ VT_UI4, "pb" },
|
||||
{ VT_UI4, "lc" },
|
||||
{ VT_UI4, "lp" },
|
||||
{ VT_UI4, "fb" },
|
||||
{ VT_BSTR, "mf" },
|
||||
{ VT_UI4, "mc" },
|
||||
{ VT_UI4, "pass" },
|
||||
{ VT_UI4, "a" },
|
||||
{ VT_UI4, "mt" },
|
||||
{ VT_BOOL, "eos" },
|
||||
{ VT_UI4, "x" },
|
||||
{ VT_UI4, "reduceSize" }
|
||||
};
|
||||
|
||||
static int FindPropIdExact(const UString &name)
|
||||
{
|
||||
for (unsigned i = 0; i < sizeof(g_NameToPropID) / sizeof(g_NameToPropID[0]); i++)
|
||||
if (name.CompareNoCase(g_NameToPropID[i].Name) == 0)
|
||||
for (unsigned i = 0; i < ARRAY_SIZE(g_NameToPropID); i++)
|
||||
if (StringsAreEqualNoCase_Ascii(name, g_NameToPropID[i].Name))
|
||||
return i;
|
||||
return -1;
|
||||
}
|
||||
@@ -285,7 +276,7 @@ static void SplitParams(const UString &srcString, UStringVector &subStrings)
|
||||
{
|
||||
subStrings.Clear();
|
||||
UString s;
|
||||
int len = srcString.Length();
|
||||
int len = srcString.Len();
|
||||
if (len == 0)
|
||||
return;
|
||||
for (int i = 0; i < len; i++)
|
||||
@@ -307,19 +298,19 @@ static void SplitParam(const UString ¶m, UString &name, UString &value)
|
||||
int eqPos = param.Find(L'=');
|
||||
if (eqPos >= 0)
|
||||
{
|
||||
name = param.Left(eqPos);
|
||||
value = param.Mid(eqPos + 1);
|
||||
name.SetFrom(param, eqPos);
|
||||
value = param.Ptr(eqPos + 1);
|
||||
return;
|
||||
}
|
||||
int i;
|
||||
for (i = 0; i < param.Length(); i++)
|
||||
unsigned i;
|
||||
for (i = 0; i < param.Len(); i++)
|
||||
{
|
||||
wchar_t c = param[i];
|
||||
if (c >= L'0' && c <= L'9')
|
||||
break;
|
||||
}
|
||||
name = param.Left(i);
|
||||
value = param.Mid(i);
|
||||
name.SetFrom(param, i);
|
||||
value = param.Ptr(i);
|
||||
}
|
||||
|
||||
static bool IsLogSizeProp(PROPID propid)
|
||||
@@ -365,7 +356,7 @@ HRESULT CMethodProps::SetParam(const UString &name, const UString &value)
|
||||
else if (!value.IsEmpty())
|
||||
{
|
||||
UInt32 number;
|
||||
if (ParseStringToUInt32(value, number) == value.Length())
|
||||
if (ParseStringToUInt32(value, number) == value.Len())
|
||||
propValue = number;
|
||||
else
|
||||
propValue = value;
|
||||
@@ -381,7 +372,7 @@ HRESULT CMethodProps::ParseParamsFromString(const UString &srcString)
|
||||
{
|
||||
UStringVector params;
|
||||
SplitParams(srcString, params);
|
||||
for (int i = 0; i < params.Size(); i++)
|
||||
FOR_VECTOR (i, params)
|
||||
{
|
||||
const UString ¶m = params[i];
|
||||
UString name, value;
|
||||
@@ -393,7 +384,7 @@ HRESULT CMethodProps::ParseParamsFromString(const UString &srcString)
|
||||
|
||||
HRESULT CMethodProps::ParseParamsFromPROPVARIANT(const UString &realName, const PROPVARIANT &value)
|
||||
{
|
||||
if (realName.Length() == 0)
|
||||
if (realName.Len() == 0)
|
||||
{
|
||||
// [empty]=method
|
||||
return E_INVALIDARG;
|
||||
@@ -429,20 +420,22 @@ HRESULT CMethodProps::ParseParamsFromPROPVARIANT(const UString &realName, const
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT COneMethodInfo::ParseMethodFromString(const UString &s)
|
||||
{
|
||||
int splitPos = s.Find(':');
|
||||
MethodName = s;
|
||||
if (splitPos < 0)
|
||||
return S_OK;
|
||||
MethodName.DeleteFrom(splitPos);
|
||||
return ParseParamsFromString(s.Ptr(splitPos + 1));
|
||||
}
|
||||
|
||||
HRESULT COneMethodInfo::ParseMethodFromPROPVARIANT(const UString &realName, const PROPVARIANT &value)
|
||||
{
|
||||
if (!realName.IsEmpty() && realName.CompareNoCase(L"m") != 0)
|
||||
if (!realName.IsEmpty() && !StringsAreEqualNoCase_Ascii(realName, "m"))
|
||||
return ParseParamsFromPROPVARIANT(realName, value);
|
||||
// -m{N}=method
|
||||
if (value.vt != VT_BSTR)
|
||||
return E_INVALIDARG;
|
||||
const UString s = value.bstrVal;
|
||||
int splitPos = s.Find(':');
|
||||
if (splitPos < 0)
|
||||
{
|
||||
MethodName = s;
|
||||
return S_OK;
|
||||
}
|
||||
MethodName = s.Left(splitPos);
|
||||
return ParseParamsFromString(s.Mid(splitPos + 1));
|
||||
return ParseMethodFromString(value.bstrVal);
|
||||
}
|
||||
|
||||
5
CPP/7zip/Common/MethodProps.h
Executable file → Normal file
5
CPP/7zip/Common/MethodProps.h
Executable file → Normal file
@@ -11,7 +11,7 @@
|
||||
|
||||
bool StringToBool(const UString &s, bool &res);
|
||||
HRESULT PROPVARIANT_to_bool(const PROPVARIANT &prop, bool &dest);
|
||||
int ParseStringToUInt32(const UString &srcString, UInt32 &number);
|
||||
unsigned ParseStringToUInt32(const UString &srcString, UInt32 &number);
|
||||
HRESULT ParsePropToUInt32(const UString &name, const PROPVARIANT &prop, UInt32 &resValue);
|
||||
|
||||
HRESULT ParseMtProp(const UString &name, const PROPVARIANT &prop, UInt32 defaultNumThreads, UInt32 &numThreads);
|
||||
@@ -32,7 +32,7 @@ struct CProps
|
||||
|
||||
bool AreThereNonOptionalProps() const
|
||||
{
|
||||
for (int i = 0; i < Props.Size(); i++)
|
||||
FOR_VECTOR (i, Props)
|
||||
if (!Props[i].IsOptional)
|
||||
return true;
|
||||
return false;
|
||||
@@ -179,6 +179,7 @@ public:
|
||||
}
|
||||
bool IsEmpty() const { return MethodName.IsEmpty() && Props.IsEmpty(); }
|
||||
HRESULT ParseMethodFromPROPVARIANT(const UString &realName, const PROPVARIANT &value);
|
||||
HRESULT ParseMethodFromString(const UString &s);
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
12
CPP/7zip/Common/OffsetStream.cpp
Executable file → Normal file
12
CPP/7zip/Common/OffsetStream.cpp
Executable file → Normal file
@@ -2,7 +2,8 @@
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#include "Common/Defs.h"
|
||||
#include "../../Common/Defs.h"
|
||||
|
||||
#include "OffsetStream.h"
|
||||
|
||||
HRESULT COffsetOutStream::Init(IOutStream *stream, UInt64 offset)
|
||||
@@ -17,14 +18,17 @@ STDMETHODIMP COffsetOutStream::Write(const void *data, UInt32 size, UInt32 *proc
|
||||
return _stream->Write(data, size, processedSize);
|
||||
}
|
||||
|
||||
STDMETHODIMP COffsetOutStream::Seek(Int64 offset, UInt32 seekOrigin,
|
||||
UInt64 *newPosition)
|
||||
STDMETHODIMP COffsetOutStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
UInt64 absoluteNewPosition;
|
||||
if (seekOrigin == STREAM_SEEK_SET)
|
||||
{
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
offset += _offset;
|
||||
}
|
||||
HRESULT result = _stream->Seek(offset, seekOrigin, &absoluteNewPosition);
|
||||
if (newPosition != NULL)
|
||||
if (newPosition)
|
||||
*newPosition = absoluteNewPosition - _offset;
|
||||
return result;
|
||||
}
|
||||
|
||||
7
CPP/7zip/Common/OffsetStream.h
Executable file → Normal file
7
CPP/7zip/Common/OffsetStream.h
Executable file → Normal file
@@ -1,9 +1,10 @@
|
||||
// OffsetStream.h
|
||||
|
||||
#ifndef __OFFSETSTREAM_H
|
||||
#define __OFFSETSTREAM_H
|
||||
#ifndef __OFFSET_STREAM_H
|
||||
#define __OFFSET_STREAM_H
|
||||
|
||||
#include "../../Common/MyCom.h"
|
||||
|
||||
#include "Common/MyCom.h"
|
||||
#include "../IStream.h"
|
||||
|
||||
class COffsetOutStream:
|
||||
|
||||
47
CPP/7zip/Common/OutBuffer.cpp
Executable file → Normal file
47
CPP/7zip/Common/OutBuffer.cpp
Executable file → Normal file
@@ -6,34 +6,29 @@
|
||||
|
||||
#include "OutBuffer.h"
|
||||
|
||||
bool COutBuffer::Create(UInt32 bufferSize)
|
||||
bool COutBuffer::Create(UInt32 bufSize)
|
||||
{
|
||||
const UInt32 kMinBlockSize = 1;
|
||||
if (bufferSize < kMinBlockSize)
|
||||
bufferSize = kMinBlockSize;
|
||||
if (_buffer != 0 && _bufferSize == bufferSize)
|
||||
if (bufSize < kMinBlockSize)
|
||||
bufSize = kMinBlockSize;
|
||||
if (_buf != 0 && _bufSize == bufSize)
|
||||
return true;
|
||||
Free();
|
||||
_bufferSize = bufferSize;
|
||||
_buffer = (Byte *)::MidAlloc(bufferSize);
|
||||
return (_buffer != 0);
|
||||
_bufSize = bufSize;
|
||||
_buf = (Byte *)::MidAlloc(bufSize);
|
||||
return (_buf != 0);
|
||||
}
|
||||
|
||||
void COutBuffer::Free()
|
||||
{
|
||||
::MidFree(_buffer);
|
||||
_buffer = 0;
|
||||
}
|
||||
|
||||
void COutBuffer::SetStream(ISequentialOutStream *stream)
|
||||
{
|
||||
_stream = stream;
|
||||
::MidFree(_buf);
|
||||
_buf = 0;
|
||||
}
|
||||
|
||||
void COutBuffer::Init()
|
||||
{
|
||||
_streamPos = 0;
|
||||
_limitPos = _bufferSize;
|
||||
_limitPos = _bufSize;
|
||||
_pos = 0;
|
||||
_processedSize = 0;
|
||||
_overDict = false;
|
||||
@@ -46,23 +41,23 @@ UInt64 COutBuffer::GetProcessedSize() const
|
||||
{
|
||||
UInt64 res = _processedSize + _pos - _streamPos;
|
||||
if (_streamPos > _pos)
|
||||
res += _bufferSize;
|
||||
res += _bufSize;
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
HRESULT COutBuffer::FlushPart()
|
||||
{
|
||||
// _streamPos < _bufferSize
|
||||
UInt32 size = (_streamPos >= _pos) ? (_bufferSize - _streamPos) : (_pos - _streamPos);
|
||||
// _streamPos < _bufSize
|
||||
UInt32 size = (_streamPos >= _pos) ? (_bufSize - _streamPos) : (_pos - _streamPos);
|
||||
HRESULT result = S_OK;
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
result = ErrorCode;
|
||||
#endif
|
||||
if (_buffer2 != 0)
|
||||
if (_buf2 != 0)
|
||||
{
|
||||
memmove(_buffer2, _buffer + _streamPos, size);
|
||||
_buffer2 += size;
|
||||
memcpy(_buf2, _buf + _streamPos, size);
|
||||
_buf2 += size;
|
||||
}
|
||||
|
||||
if (_stream != 0
|
||||
@@ -72,18 +67,18 @@ HRESULT COutBuffer::FlushPart()
|
||||
)
|
||||
{
|
||||
UInt32 processedSize = 0;
|
||||
result = _stream->Write(_buffer + _streamPos, size, &processedSize);
|
||||
result = _stream->Write(_buf + _streamPos, size, &processedSize);
|
||||
size = processedSize;
|
||||
}
|
||||
_streamPos += size;
|
||||
if (_streamPos == _bufferSize)
|
||||
if (_streamPos == _bufSize)
|
||||
_streamPos = 0;
|
||||
if (_pos == _bufferSize)
|
||||
if (_pos == _bufSize)
|
||||
{
|
||||
_overDict = true;
|
||||
_pos = 0;
|
||||
}
|
||||
_limitPos = (_streamPos > _pos) ? _streamPos : _bufferSize;
|
||||
_limitPos = (_streamPos > _pos) ? _streamPos : _bufSize;
|
||||
_processedSize += size;
|
||||
return result;
|
||||
}
|
||||
@@ -95,7 +90,7 @@ HRESULT COutBuffer::Flush()
|
||||
return ErrorCode;
|
||||
#endif
|
||||
|
||||
while(_streamPos != _pos)
|
||||
while (_streamPos != _pos)
|
||||
{
|
||||
HRESULT result = FlushPart();
|
||||
if (result != S_OK)
|
||||
|
||||
35
CPP/7zip/Common/OutBuffer.h
Executable file → Normal file
35
CPP/7zip/Common/OutBuffer.h
Executable file → Normal file
@@ -1,7 +1,7 @@
|
||||
// OutBuffer.h
|
||||
|
||||
#ifndef __OUTBUFFER_H
|
||||
#define __OUTBUFFER_H
|
||||
#ifndef __OUT_BUFFER_H
|
||||
#define __OUT_BUFFER_H
|
||||
|
||||
#include "../IStream.h"
|
||||
#include "../../Common/MyCom.h"
|
||||
@@ -17,39 +17,38 @@ struct COutBufferException: public CSystemException
|
||||
class COutBuffer
|
||||
{
|
||||
protected:
|
||||
Byte *_buffer;
|
||||
Byte *_buf;
|
||||
UInt32 _pos;
|
||||
UInt32 _limitPos;
|
||||
UInt32 _streamPos;
|
||||
UInt32 _bufferSize;
|
||||
CMyComPtr<ISequentialOutStream> _stream;
|
||||
UInt32 _bufSize;
|
||||
ISequentialOutStream *_stream;
|
||||
UInt64 _processedSize;
|
||||
Byte *_buffer2;
|
||||
Byte *_buf2;
|
||||
bool _overDict;
|
||||
|
||||
HRESULT FlushPart();
|
||||
HRESULT FlushPart() throw();
|
||||
public:
|
||||
#ifdef _NO_EXCEPTIONS
|
||||
HRESULT ErrorCode;
|
||||
#endif
|
||||
|
||||
COutBuffer(): _buffer(0), _pos(0), _stream(0), _buffer2(0) {}
|
||||
COutBuffer(): _buf(0), _pos(0), _stream(0), _buf2(0) {}
|
||||
~COutBuffer() { Free(); }
|
||||
|
||||
bool Create(UInt32 bufferSize);
|
||||
void Free();
|
||||
bool Create(UInt32 bufSize) throw();
|
||||
void Free() throw();
|
||||
|
||||
void SetMemStream(Byte *buffer) { _buffer2 = buffer; }
|
||||
void SetStream(ISequentialOutStream *stream);
|
||||
void Init();
|
||||
HRESULT Flush();
|
||||
void SetMemStream(Byte *buf) { _buf2 = buf; }
|
||||
void SetStream(ISequentialOutStream *stream) { _stream = stream; }
|
||||
void Init() throw();
|
||||
HRESULT Flush() throw();
|
||||
void FlushWithCheck();
|
||||
void ReleaseStream() { _stream.Release(); }
|
||||
|
||||
void WriteByte(Byte b)
|
||||
{
|
||||
_buffer[_pos++] = b;
|
||||
if(_pos == _limitPos)
|
||||
_buf[_pos++] = b;
|
||||
if (_pos == _limitPos)
|
||||
FlushWithCheck();
|
||||
}
|
||||
void WriteBytes(const void *data, size_t size)
|
||||
@@ -58,7 +57,7 @@ public:
|
||||
WriteByte(((const Byte *)data)[i]);
|
||||
}
|
||||
|
||||
UInt64 GetProcessedSize() const;
|
||||
UInt64 GetProcessedSize() const throw();
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
10
CPP/7zip/Common/OutMemStream.cpp
Executable file → Normal file
10
CPP/7zip/Common/OutMemStream.cpp
Executable file → Normal file
@@ -40,15 +40,15 @@ STDMETHODIMP COutMemStream::Write(const void *data, UInt32 size, UInt32 *process
|
||||
return OutSeqStream->Write(data, size, processedSize);
|
||||
if (processedSize != 0)
|
||||
*processedSize = 0;
|
||||
while(size != 0)
|
||||
while (size != 0)
|
||||
{
|
||||
if ((int)_curBlockIndex < Blocks.Blocks.Size())
|
||||
if (_curBlockIndex < Blocks.Blocks.Size())
|
||||
{
|
||||
Byte *p = (Byte *)Blocks.Blocks[(int)_curBlockIndex] + _curBlockPos;
|
||||
Byte *p = (Byte *)Blocks.Blocks[_curBlockIndex] + _curBlockPos;
|
||||
size_t curSize = _memManager->GetBlockSize() - _curBlockPos;
|
||||
if (size < curSize)
|
||||
curSize = size;
|
||||
memmove(p, data, curSize);
|
||||
memcpy(p, data, curSize);
|
||||
if (processedSize != 0)
|
||||
*processedSize += (UInt32)curSize;
|
||||
data = (const void *)((const Byte *)data + curSize);
|
||||
@@ -124,7 +124,7 @@ STDMETHODIMP COutMemStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPos
|
||||
}
|
||||
else
|
||||
return E_NOTIMPL;
|
||||
if (newPosition != 0)
|
||||
if (newPosition)
|
||||
*newPosition = GetPos();
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
9
CPP/7zip/Common/OutMemStream.h
Executable file → Normal file
9
CPP/7zip/Common/OutMemStream.h
Executable file → Normal file
@@ -1,9 +1,10 @@
|
||||
// OutMemStream.h
|
||||
|
||||
#ifndef __OUTMEMSTREAM_H
|
||||
#define __OUTMEMSTREAM_H
|
||||
#ifndef __OUT_MEM_STREAM_H
|
||||
#define __OUT_MEM_STREAM_H
|
||||
|
||||
#include "../../Common/MyCom.h"
|
||||
|
||||
#include "Common/MyCom.h"
|
||||
#include "MemBlocks.h"
|
||||
|
||||
class COutMemStream:
|
||||
@@ -11,7 +12,7 @@ class COutMemStream:
|
||||
public CMyUnknownImp
|
||||
{
|
||||
CMemBlockManagerMt *_memManager;
|
||||
size_t _curBlockIndex;
|
||||
unsigned _curBlockIndex;
|
||||
size_t _curBlockPos;
|
||||
bool _realStreamMode;
|
||||
|
||||
|
||||
0
CPP/7zip/Common/ProgressMt.cpp
Executable file → Normal file
0
CPP/7zip/Common/ProgressMt.cpp
Executable file → Normal file
0
CPP/7zip/Common/ProgressMt.h
Executable file → Normal file
0
CPP/7zip/Common/ProgressMt.h
Executable file → Normal file
2
CPP/7zip/Common/ProgressUtils.cpp
Executable file → Normal file
2
CPP/7zip/Common/ProgressUtils.cpp
Executable file → Normal file
@@ -1,4 +1,4 @@
|
||||
// ProgressUtils.h
|
||||
// ProgressUtils.cpp
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
|
||||
0
CPP/7zip/Common/ProgressUtils.h
Executable file → Normal file
0
CPP/7zip/Common/ProgressUtils.h
Executable file → Normal file
99
CPP/7zip/Common/PropId.cpp
Normal file
99
CPP/7zip/Common/PropId.cpp
Normal file
@@ -0,0 +1,99 @@
|
||||
// PropId.cpp
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#include "../PropID.h"
|
||||
|
||||
// VARTYPE
|
||||
Byte k7z_PROPID_To_VARTYPE[kpid_NUM_DEFINED] =
|
||||
{
|
||||
VT_EMPTY,
|
||||
VT_UI4,
|
||||
VT_UI4,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BOOL,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI4,
|
||||
VT_FILETIME,
|
||||
VT_FILETIME,
|
||||
VT_FILETIME,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_UI4,
|
||||
VT_UI4,
|
||||
VT_BSTR,
|
||||
VT_BOOL,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_BSTR, // or VT_UI8 kpidUnpackVer
|
||||
VT_UI4, // or VT_UI8 kpidVolume
|
||||
VT_BOOL,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI4,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI4, // kpidChecksum
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_BSTR, // or VT_UI8 kpidId
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_UI4,
|
||||
VT_UI4,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI4,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR, // kpidNtSecure
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BSTR, // SHA-1
|
||||
VT_BSTR, // SHA-256
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_UI4,
|
||||
VT_UI4,
|
||||
VT_BSTR,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_UI8,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BSTR,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_BOOL,
|
||||
VT_UI8,
|
||||
VT_UI8
|
||||
};
|
||||
47
CPP/7zip/Common/RegisterArc.h
Executable file → Normal file
47
CPP/7zip/Common/RegisterArc.h
Executable file → Normal file
@@ -5,23 +5,28 @@
|
||||
|
||||
#include "../Archive/IArchive.h"
|
||||
|
||||
typedef IInArchive * (*CreateInArchiveP)();
|
||||
typedef IOutArchive * (*CreateOutArchiveP)();
|
||||
|
||||
struct CArcInfo
|
||||
{
|
||||
const wchar_t *Name;
|
||||
const wchar_t *Ext;
|
||||
const wchar_t *AddExt;
|
||||
const char *Name;
|
||||
const char *Ext;
|
||||
const char *AddExt;
|
||||
|
||||
Byte ClassId;
|
||||
Byte Signature[16];
|
||||
int SignatureSize;
|
||||
bool KeepName;
|
||||
CreateInArchiveP CreateInArchive;
|
||||
CreateOutArchiveP CreateOutArchive;
|
||||
|
||||
Byte SignatureSize;
|
||||
Byte Signature[20];
|
||||
UInt16 SignatureOffset;
|
||||
|
||||
UInt16 Flags;
|
||||
|
||||
Func_CreateInArchive CreateInArchive;
|
||||
Func_CreateOutArchive CreateOutArchive;
|
||||
Func_IsArc IsArc;
|
||||
|
||||
bool IsMultiSignature() const { return (Flags & NArcInfoFlags::kMultiSignature) != 0; }
|
||||
};
|
||||
|
||||
void RegisterArc(const CArcInfo *arcInfo);
|
||||
void RegisterArc(const CArcInfo *arcInfo) throw();
|
||||
|
||||
#define REGISTER_ARC_NAME(x) CRegister ## x
|
||||
|
||||
@@ -29,4 +34,22 @@ void RegisterArc(const CArcInfo *arcInfo);
|
||||
REGISTER_ARC_NAME(x)() { RegisterArc(&g_ArcInfo); }}; \
|
||||
static REGISTER_ARC_NAME(x) g_RegisterArc;
|
||||
|
||||
#define REGISTER_ARC_DEC_SIG(x) struct REGISTER_ARC_NAME(x) { \
|
||||
REGISTER_ARC_NAME(x)() { g_ArcInfo.Signature[0]--; RegisterArc(&g_ArcInfo); }}; \
|
||||
static REGISTER_ARC_NAME(x) g_RegisterArc;
|
||||
|
||||
|
||||
#define IMP_CreateArcIn_2(c) \
|
||||
static IInArchive *CreateArc() { return new c; }
|
||||
|
||||
#define IMP_CreateArcIn IMP_CreateArcIn_2(CHandler)
|
||||
|
||||
#ifdef EXTRACT_ONLY
|
||||
#define IMP_CreateArcOut
|
||||
#define REF_CreateArc_Pair CreateArc, NULL
|
||||
#else
|
||||
#define IMP_CreateArcOut static IOutArchive *CreateArcOut() { return new CHandler; }
|
||||
#define REF_CreateArc_Pair CreateArc, CreateArcOut
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
26
CPP/7zip/Common/RegisterCodec.h
Executable file → Normal file
26
CPP/7zip/Common/RegisterCodec.h
Executable file → Normal file
@@ -1,9 +1,10 @@
|
||||
// RegisterCodec.h
|
||||
|
||||
#ifndef __REGISTERCODEC_H
|
||||
#define __REGISTERCODEC_H
|
||||
#ifndef __REGISTER_CODEC_H
|
||||
#define __REGISTER_CODEC_H
|
||||
|
||||
#include "../Common/MethodId.h"
|
||||
#include "../ICoder.h"
|
||||
|
||||
typedef void * (*CreateCodecP)();
|
||||
struct CCodecInfo
|
||||
@@ -16,7 +17,7 @@ struct CCodecInfo
|
||||
bool IsFilter;
|
||||
};
|
||||
|
||||
void RegisterCodec(const CCodecInfo *codecInfo);
|
||||
void RegisterCodec(const CCodecInfo *codecInfo) throw();
|
||||
|
||||
#define REGISTER_CODEC_NAME(x) CRegisterCodec ## x
|
||||
|
||||
@@ -26,8 +27,25 @@ void RegisterCodec(const CCodecInfo *codecInfo);
|
||||
|
||||
#define REGISTER_CODECS_NAME(x) CRegisterCodecs ## x
|
||||
#define REGISTER_CODECS(x) struct REGISTER_CODECS_NAME(x) { \
|
||||
REGISTER_CODECS_NAME(x)() { for (int i = 0; i < sizeof(g_CodecsInfo) / sizeof(g_CodecsInfo[0]); i++) \
|
||||
REGISTER_CODECS_NAME(x)() { for (unsigned i = 0; i < ARRAY_SIZE(g_CodecsInfo); i++) \
|
||||
RegisterCodec(&g_CodecsInfo[i]); }}; \
|
||||
static REGISTER_CODECS_NAME(x) g_RegisterCodecs;
|
||||
|
||||
|
||||
struct CHasherInfo
|
||||
{
|
||||
IHasher * (*CreateHasher)();
|
||||
CMethodId Id;
|
||||
const wchar_t *Name;
|
||||
UInt32 DigestSize;
|
||||
};
|
||||
|
||||
void RegisterHasher(const CHasherInfo *hasher) throw();
|
||||
|
||||
#define REGISTER_HASHER_NAME(x) CRegisterHasher ## x
|
||||
|
||||
#define REGISTER_HASHER(x) struct REGISTER_HASHER_NAME(x) { \
|
||||
REGISTER_HASHER_NAME(x)() { RegisterHasher(&g_HasherInfo); }}; \
|
||||
static REGISTER_HASHER_NAME(x) g_RegisterHasher;
|
||||
|
||||
#endif
|
||||
|
||||
3
CPP/7zip/Common/StdAfx.h
Executable file → Normal file
3
CPP/7zip/Common/StdAfx.h
Executable file → Normal file
@@ -3,7 +3,6 @@
|
||||
#ifndef __STDAFX_H
|
||||
#define __STDAFX_H
|
||||
|
||||
#include "../../Common/MyWindows.h"
|
||||
#include "../../Common/NewHandler.h"
|
||||
#include "../../Common/Common.h"
|
||||
|
||||
#endif
|
||||
|
||||
0
CPP/7zip/Common/StreamBinder.cpp
Executable file → Normal file
0
CPP/7zip/Common/StreamBinder.cpp
Executable file → Normal file
0
CPP/7zip/Common/StreamBinder.h
Executable file → Normal file
0
CPP/7zip/Common/StreamBinder.h
Executable file → Normal file
61
CPP/7zip/Common/StreamObjects.cpp
Executable file → Normal file
61
CPP/7zip/Common/StreamObjects.cpp
Executable file → Normal file
@@ -14,8 +14,8 @@ STDMETHODIMP CBufInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
*processedSize = 0;
|
||||
if (size == 0)
|
||||
return S_OK;
|
||||
if (_pos > _size)
|
||||
return E_FAIL;
|
||||
if (_pos >= _size)
|
||||
return S_OK;
|
||||
size_t rem = _size - (size_t)_pos;
|
||||
if (rem > size)
|
||||
rem = (size_t)size;
|
||||
@@ -28,18 +28,43 @@ STDMETHODIMP CBufInStream::Read(void *data, UInt32 size, UInt32 *processedSize)
|
||||
|
||||
STDMETHODIMP CBufInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch(seekOrigin)
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: _pos = offset; break;
|
||||
case STREAM_SEEK_CUR: _pos += offset; break;
|
||||
case STREAM_SEEK_END: _pos = _size + offset; break;
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _pos; break;
|
||||
case STREAM_SEEK_END: offset += _size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_pos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = _pos;
|
||||
*newPosition = offset;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
void Create_BufInStream_WithReference(const void *data, size_t size, ISequentialInStream **stream)
|
||||
{
|
||||
CBufInStream *inStreamSpec = new CBufInStream;
|
||||
CMyComPtr<ISequentialInStream> streamTemp = inStreamSpec;
|
||||
inStreamSpec->Init((const Byte *)data, size);
|
||||
*stream = streamTemp.Detach();
|
||||
}
|
||||
*/
|
||||
|
||||
void Create_BufInStream_WithNewBuf(const void *data, size_t size, ISequentialInStream **stream)
|
||||
{
|
||||
CReferenceBuf *referenceBuf = new CReferenceBuf;
|
||||
CMyComPtr<IUnknown> ref = referenceBuf;
|
||||
referenceBuf->Buf.CopyFrom((const Byte *)data, size);
|
||||
|
||||
CBufInStream *inStreamSpec = new CBufInStream;
|
||||
CMyComPtr<ISequentialInStream> streamTemp = inStreamSpec;
|
||||
inStreamSpec->Init(referenceBuf);
|
||||
*stream = streamTemp.Detach();
|
||||
}
|
||||
|
||||
void CByteDynBuffer::Free()
|
||||
{
|
||||
free(_buf);
|
||||
@@ -79,8 +104,7 @@ Byte *CDynBufSeqOutStream::GetBufPtrForWriting(size_t addSize)
|
||||
|
||||
void CDynBufSeqOutStream::CopyToBuffer(CByteBuffer &dest) const
|
||||
{
|
||||
dest.SetCapacity(_size);
|
||||
memcpy(dest, (const Byte *)_buffer, _size);
|
||||
dest.CopyFrom((const Byte *)_buffer, _size);
|
||||
}
|
||||
|
||||
STDMETHODIMP CDynBufSeqOutStream::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
@@ -172,8 +196,8 @@ STDMETHODIMP CCachedInStream::Read(void *data, UInt32 size, UInt32 *processedSiz
|
||||
*processedSize = 0;
|
||||
if (size == 0)
|
||||
return S_OK;
|
||||
if (_pos > _size)
|
||||
return E_FAIL;
|
||||
if (_pos >= _size)
|
||||
return S_OK;
|
||||
|
||||
{
|
||||
UInt64 rem = _size - _pos;
|
||||
@@ -210,14 +234,17 @@ STDMETHODIMP CCachedInStream::Read(void *data, UInt32 size, UInt32 *processedSiz
|
||||
|
||||
STDMETHODIMP CCachedInStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition)
|
||||
{
|
||||
switch(seekOrigin)
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: _pos = offset; break;
|
||||
case STREAM_SEEK_CUR: _pos = _pos + offset; break;
|
||||
case STREAM_SEEK_END: _pos = _size + offset; break;
|
||||
case STREAM_SEEK_SET: break;
|
||||
case STREAM_SEEK_CUR: offset += _pos; break;
|
||||
case STREAM_SEEK_END: offset += _size; break;
|
||||
default: return STG_E_INVALIDFUNCTION;
|
||||
}
|
||||
if (newPosition != 0)
|
||||
*newPosition = _pos;
|
||||
if (offset < 0)
|
||||
return HRESULT_WIN32_ERROR_NEGATIVE_SEEK;
|
||||
_pos = offset;
|
||||
if (newPosition)
|
||||
*newPosition = offset;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
29
CPP/7zip/Common/StreamObjects.h
Executable file → Normal file
29
CPP/7zip/Common/StreamObjects.h
Executable file → Normal file
@@ -3,8 +3,10 @@
|
||||
#ifndef __STREAM_OBJECTS_H
|
||||
#define __STREAM_OBJECTS_H
|
||||
|
||||
#include "../../Common/Buffer.h"
|
||||
#include "../../Common/MyBuffer.h"
|
||||
#include "../../Common/MyCom.h"
|
||||
#include "../../Common/MyVector.h"
|
||||
|
||||
#include "../IStream.h"
|
||||
|
||||
struct CReferenceBuf:
|
||||
@@ -31,13 +33,16 @@ public:
|
||||
_pos = 0;
|
||||
_ref = ref;
|
||||
}
|
||||
void Init(CReferenceBuf *ref) { Init(ref->Buf, ref->Buf.GetCapacity(), ref); }
|
||||
void Init(CReferenceBuf *ref) { Init(ref->Buf, ref->Buf.Size(), ref); }
|
||||
|
||||
MY_UNKNOWN_IMP1(IInStream)
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, IInStream)
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
STDMETHOD(Seek)(Int64 offset, UInt32 seekOrigin, UInt64 *newPosition);
|
||||
};
|
||||
|
||||
// void Create_BufInStream_WithReference(const void *data, size_t size, ISequentialInStream **stream);
|
||||
void Create_BufInStream_WithNewBuf(const void *data, size_t size, ISequentialInStream **stream);
|
||||
|
||||
class CByteDynBuffer
|
||||
{
|
||||
size_t _capacity;
|
||||
@@ -46,11 +51,11 @@ public:
|
||||
CByteDynBuffer(): _capacity(0), _buf(0) {};
|
||||
// there is no copy constructor. So don't copy this object.
|
||||
~CByteDynBuffer() { Free(); }
|
||||
void Free();
|
||||
size_t GetCapacity() const { return _capacity; }
|
||||
void Free() throw();
|
||||
size_t GetCapacity() const { return _capacity; }
|
||||
operator Byte*() const { return _buf; };
|
||||
operator const Byte*() const { return _buf; };
|
||||
bool EnsureCapacity(size_t capacity);
|
||||
bool EnsureCapacity(size_t capacity) throw();
|
||||
};
|
||||
|
||||
class CDynBufSeqOutStream:
|
||||
@@ -68,7 +73,7 @@ public:
|
||||
Byte *GetBufPtrForWriting(size_t addSize);
|
||||
void UpdateSize(size_t addSize) { _size += addSize; }
|
||||
|
||||
MY_UNKNOWN_IMP
|
||||
MY_UNKNOWN_IMP1(ISequentialOutStream)
|
||||
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
|
||||
};
|
||||
|
||||
@@ -88,7 +93,7 @@ public:
|
||||
}
|
||||
size_t GetPos() const { return _pos; }
|
||||
|
||||
MY_UNKNOWN_IMP
|
||||
MY_UNKNOWN_IMP1(ISequentialOutStream)
|
||||
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
|
||||
};
|
||||
|
||||
@@ -103,7 +108,7 @@ public:
|
||||
void Init() { _size = 0; }
|
||||
UInt64 GetSize() const { return _size; }
|
||||
|
||||
MY_UNKNOWN_IMP
|
||||
MY_UNKNOWN_IMP1(ISequentialOutStream)
|
||||
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize);
|
||||
};
|
||||
|
||||
@@ -123,9 +128,9 @@ protected:
|
||||
public:
|
||||
CCachedInStream(): _tags(0), _data(0) {}
|
||||
virtual ~CCachedInStream() { Free(); } // the destructor must be virtual (release calls it) !!!
|
||||
void Free();
|
||||
bool Alloc(unsigned blockSizeLog, unsigned numBlocksLog);
|
||||
void Init(UInt64 size);
|
||||
void Free() throw();
|
||||
bool Alloc(unsigned blockSizeLog, unsigned numBlocksLog) throw();
|
||||
void Init(UInt64 size) throw();
|
||||
|
||||
MY_UNKNOWN_IMP2(ISequentialInStream, IInStream)
|
||||
STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
|
||||
|
||||
0
CPP/7zip/Common/StreamUtils.cpp
Executable file → Normal file
0
CPP/7zip/Common/StreamUtils.cpp
Executable file → Normal file
12
CPP/7zip/Common/StreamUtils.h
Executable file → Normal file
12
CPP/7zip/Common/StreamUtils.h
Executable file → Normal file
@@ -1,13 +1,13 @@
|
||||
// StreamUtils.h
|
||||
|
||||
#ifndef __STREAMUTILS_H
|
||||
#define __STREAMUTILS_H
|
||||
#ifndef __STREAM_UTILS_H
|
||||
#define __STREAM_UTILS_H
|
||||
|
||||
#include "../IStream.h"
|
||||
|
||||
HRESULT ReadStream(ISequentialInStream *stream, void *data, size_t *size);
|
||||
HRESULT ReadStream_FALSE(ISequentialInStream *stream, void *data, size_t size);
|
||||
HRESULT ReadStream_FAIL(ISequentialInStream *stream, void *data, size_t size);
|
||||
HRESULT WriteStream(ISequentialOutStream *stream, const void *data, size_t size);
|
||||
HRESULT ReadStream(ISequentialInStream *stream, void *data, size_t *size) throw();
|
||||
HRESULT ReadStream_FALSE(ISequentialInStream *stream, void *data, size_t size) throw();
|
||||
HRESULT ReadStream_FAIL(ISequentialInStream *stream, void *data, size_t size) throw();
|
||||
HRESULT WriteStream(ISequentialOutStream *stream, const void *data, size_t size) throw();
|
||||
|
||||
#endif
|
||||
|
||||
56
CPP/7zip/Common/UniqBlocks.cpp
Normal file
56
CPP/7zip/Common/UniqBlocks.cpp
Normal file
@@ -0,0 +1,56 @@
|
||||
// UniqBlocks.cpp
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#include "UniqBlocks.h"
|
||||
|
||||
int CUniqBlocks::AddUniq(const Byte *data, size_t size)
|
||||
{
|
||||
unsigned left = 0, right = Sorted.Size();
|
||||
while (left != right)
|
||||
{
|
||||
unsigned mid = (left + right) / 2;
|
||||
int index = Sorted[mid];
|
||||
const CByteBuffer &buf = Bufs[index];
|
||||
size_t sizeMid = buf.Size();
|
||||
if (size < sizeMid)
|
||||
right = mid;
|
||||
else if (size > sizeMid)
|
||||
left = mid + 1;
|
||||
else
|
||||
{
|
||||
int cmp = memcmp(data, buf, size);
|
||||
if (cmp == 0)
|
||||
return index;
|
||||
if (cmp < 0)
|
||||
right = mid;
|
||||
else
|
||||
left = mid + 1;
|
||||
}
|
||||
}
|
||||
int index = Bufs.Size();
|
||||
Sorted.Insert(left, index);
|
||||
CByteBuffer &buf = Bufs.AddNew();
|
||||
buf.CopyFrom(data, size);
|
||||
return index;
|
||||
}
|
||||
|
||||
UInt64 CUniqBlocks::GetTotalSizeInBytes() const
|
||||
{
|
||||
UInt64 size = 0;
|
||||
FOR_VECTOR (i, Bufs)
|
||||
size += Bufs[i].Size();
|
||||
return size;
|
||||
}
|
||||
|
||||
void CUniqBlocks::GetReverseMap()
|
||||
{
|
||||
unsigned num = Sorted.Size();
|
||||
BufIndexToSortedIndex.ClearAndSetSize(num);
|
||||
int *p = &BufIndexToSortedIndex[0];
|
||||
unsigned i;
|
||||
for (i = 0; i < num; i++)
|
||||
p[i] = 0;
|
||||
for (i = 0; i < num; i++)
|
||||
p[Sorted[i]] = i;
|
||||
}
|
||||
30
CPP/7zip/Common/UniqBlocks.h
Normal file
30
CPP/7zip/Common/UniqBlocks.h
Normal file
@@ -0,0 +1,30 @@
|
||||
// UniqBlocks.h
|
||||
|
||||
#ifndef __UNIQ_BLOCKS_H
|
||||
#define __UNIQ_BLOCKS_H
|
||||
|
||||
#include "../../Common/MyTypes.h"
|
||||
#include "../../Common/MyBuffer.h"
|
||||
#include "../../Common/MyVector.h"
|
||||
|
||||
struct CUniqBlocks
|
||||
{
|
||||
CObjectVector<CByteBuffer> Bufs;
|
||||
CIntVector Sorted;
|
||||
CIntVector BufIndexToSortedIndex;
|
||||
|
||||
int AddUniq(const Byte *data, size_t size);
|
||||
UInt64 GetTotalSizeInBytes() const;
|
||||
void GetReverseMap();
|
||||
|
||||
bool IsOnlyEmpty() const
|
||||
{
|
||||
if (Bufs.Size() == 0)
|
||||
return true;
|
||||
if (Bufs.Size() > 1)
|
||||
return false;
|
||||
return Bufs[0].Size() == 0;
|
||||
}
|
||||
};
|
||||
|
||||
#endif
|
||||
0
CPP/7zip/Common/VirtThread.cpp
Executable file → Normal file
0
CPP/7zip/Common/VirtThread.cpp
Executable file → Normal file
0
CPP/7zip/Common/VirtThread.h
Executable file → Normal file
0
CPP/7zip/Common/VirtThread.h
Executable file → Normal file
Reference in New Issue
Block a user