// ArchiveExtractCallback.h | |
#ifndef __ARCHIVE_EXTRACT_CALLBACK_H | |
#define __ARCHIVE_EXTRACT_CALLBACK_H | |
#include "../../../Common/MyCom.h" | |
#include "../../../Common/Wildcard.h" | |
#include "../../IPassword.h" | |
#include "../../Common/FileStreams.h" | |
#include "../../Common/ProgressUtils.h" | |
#include "../../Archive/IArchive.h" | |
#include "ExtractMode.h" | |
#include "IFileExtractCallback.h" | |
#include "OpenArchive.h" | |
#include "HashCalc.h" | |
#ifndef _SFX | |
class COutStreamWithHash: | |
public ISequentialOutStream, | |
public CMyUnknownImp | |
{ | |
CMyComPtr<ISequentialOutStream> _stream; | |
UInt64 _size; | |
bool _calculate; | |
public: | |
IHashCalc *_hash; | |
MY_UNKNOWN_IMP | |
STDMETHOD(Write)(const void *data, UInt32 size, UInt32 *processedSize); | |
void SetStream(ISequentialOutStream *stream) { _stream = stream; } | |
void ReleaseStream() { _stream.Release(); } | |
void Init(bool calculate = true) | |
{ | |
InitCRC(); | |
_size = 0; | |
_calculate = calculate; | |
} | |
void EnableCalc(bool calculate) { _calculate = calculate; } | |
void InitCRC() { _hash->InitForNewFile(); } | |
UInt64 GetSize() const { return _size; } | |
}; | |
#endif | |
struct CExtractNtOptions | |
{ | |
CBoolPair NtSecurity; | |
CBoolPair SymLinks; | |
CBoolPair HardLinks; | |
CBoolPair AltStreams; | |
bool ReplaceColonForAltStream; | |
bool WriteToAltStreamIfColon; | |
CExtractNtOptions(): | |
ReplaceColonForAltStream(false), | |
WriteToAltStreamIfColon(false) | |
{ | |
SymLinks.Val = true; | |
HardLinks.Val = true; | |
AltStreams.Val = true; | |
} | |
}; | |
#ifndef _SFX | |
class CGetProp: | |
public IGetProp, | |
public CMyUnknownImp | |
{ | |
public: | |
const CArc *Arc; | |
UInt32 IndexInArc; | |
UString Name; // relative path | |
MY_UNKNOWN_IMP1(IGetProp) | |
INTERFACE_IGetProp(;) | |
}; | |
#endif | |
#ifndef _SFX | |
#ifndef UNDER_CE | |
#define SUPPORT_LINKS | |
#endif | |
#endif | |
#ifdef SUPPORT_LINKS | |
struct CHardLinkNode | |
{ | |
UInt64 StreamId; | |
UInt64 INode; | |
int Compare(const CHardLinkNode &a) const; | |
}; | |
class CHardLinks | |
{ | |
public: | |
CRecordVector<CHardLinkNode> IDs; | |
CObjectVector<FString> Links; | |
void Clear() | |
{ | |
IDs.Clear(); | |
Links.Clear(); | |
} | |
void PrepareLinks() | |
{ | |
while (Links.Size() < IDs.Size()) | |
Links.AddNew(); | |
} | |
}; | |
#endif | |
class CArchiveExtractCallback: | |
public IArchiveExtractCallback, | |
// public IArchiveVolumeExtractCallback, | |
public ICryptoGetTextPassword, | |
public ICompressProgressInfo, | |
public CMyUnknownImp | |
{ | |
const CArc *_arc; | |
CExtractNtOptions _ntOptions; | |
const NWildcard::CCensorNode *_wildcardCensor; | |
CMyComPtr<IFolderArchiveExtractCallback> _extractCallback2; | |
CMyComPtr<ICompressProgressInfo> _compressProgress; | |
CMyComPtr<ICryptoGetTextPassword> _cryptoGetTextPassword; | |
FString _directoryPath; | |
FString _directoryPathFull; | |
NExtract::NPathMode::EEnum _pathMode; | |
NExtract::NOverwriteMode::EEnum _overwriteMode; | |
#ifndef _SFX | |
CMyComPtr<IFolderExtractToStreamCallback> ExtractToStreamCallback; | |
CGetProp *GetProp_Spec; | |
CMyComPtr<IGetProp> GetProp; | |
#endif | |
FString _diskFilePath; | |
UString _filePath; | |
UInt64 _position; | |
bool _isSplit; | |
bool _isAltStream; | |
bool _extractMode; | |
bool WriteCTime; | |
bool WriteATime; | |
bool WriteMTime; | |
bool _encrypted; | |
struct CProcessedFileInfo | |
{ | |
FILETIME CTime; | |
FILETIME ATime; | |
FILETIME MTime; | |
UInt32 Attrib; | |
bool CTimeDefined; | |
bool ATimeDefined; | |
bool MTimeDefined; | |
bool AttribDefined; | |
bool IsDir; | |
} _fi; | |
UInt32 _index; | |
UInt64 _curSize; | |
bool _curSizeDefined; | |
COutFileStream *_outFileStreamSpec; | |
CMyComPtr<ISequentialOutStream> _outFileStream; | |
#ifndef _SFX | |
COutStreamWithHash *_hashStreamSpec; | |
CMyComPtr<ISequentialOutStream> _hashStream; | |
bool _hashStreamWasUsed; | |
#endif | |
UStringVector _removePathParts; | |
bool _use_baseParentFolder_mode; | |
UInt32 _baseParentFolder; | |
bool _stdOutMode; | |
bool _testMode; | |
bool _multiArchives; | |
CMyComPtr<ICompressProgressInfo> _localProgress; | |
UInt64 _packTotal; | |
UInt64 _unpTotal; | |
FStringVector _extractedFolderPaths; | |
CRecordVector<UInt32> _extractedFolderIndices; | |
#if defined(_WIN32) && !defined(UNDER_CE) && !defined(_SFX) | |
bool _saclEnabled; | |
#endif | |
void CreateComplexDirectory(const UStringVector &dirPathParts, FString &fullPath); | |
HRESULT GetTime(int index, PROPID propID, FILETIME &filetime, bool &filetimeIsDefined); | |
HRESULT GetUnpackSize(); | |
HRESULT SendMessageError(const char *message, const FString &path); | |
HRESULT SendMessageError2(const char *message, const FString &path1, const FString &path2); | |
public: | |
CLocalProgress *LocalProgressSpec; | |
UInt64 NumFolders; | |
UInt64 NumFiles; | |
UInt64 NumAltStreams; | |
UInt64 UnpackSize; | |
UInt64 AltStreams_UnpackSize; | |
MY_UNKNOWN_IMP2(ICryptoGetTextPassword, ICompressProgressInfo) | |
// COM_INTERFACE_ENTRY(IArchiveVolumeExtractCallback) | |
INTERFACE_IArchiveExtractCallback(;) | |
STDMETHOD(SetRatioInfo)(const UInt64 *inSize, const UInt64 *outSize); | |
// IArchiveVolumeExtractCallback | |
// STDMETHOD(GetInStream)(const wchar_t *name, ISequentialInStream **inStream); | |
STDMETHOD(CryptoGetTextPassword)(BSTR *password); | |
CArchiveExtractCallback(); | |
void InitForMulti(bool multiArchives, | |
NExtract::NPathMode::EEnum pathMode, | |
NExtract::NOverwriteMode::EEnum overwriteMode) | |
{ | |
_multiArchives = multiArchives; | |
_pathMode = pathMode; | |
_overwriteMode = overwriteMode; | |
NumFolders = NumFiles = NumAltStreams = UnpackSize = AltStreams_UnpackSize = 0; | |
} | |
#ifndef _SFX | |
void SetHashMethods(IHashCalc *hash) | |
{ | |
if (!hash) | |
return; | |
_hashStreamSpec = new COutStreamWithHash; | |
_hashStream = _hashStreamSpec; | |
_hashStreamSpec->_hash = hash; | |
} | |
#endif | |
void Init( | |
const CExtractNtOptions &ntOptions, | |
const NWildcard::CCensorNode *wildcardCensor, | |
const CArc *arc, | |
IFolderArchiveExtractCallback *extractCallback2, | |
bool stdOutMode, bool testMode, | |
const FString &directoryPath, | |
const UStringVector &removePathParts, | |
UInt64 packSize); | |
#ifdef SUPPORT_LINKS | |
private: | |
CHardLinks _hardLinks; | |
public: | |
// call PrepareHardLinks() after Init() | |
HRESULT PrepareHardLinks(const CRecordVector<UInt32> *realIndices); // NULL means all items | |
#endif | |
// call it after Init() | |
void SetBaseParentFolderIndex(UInt32 indexInArc) | |
{ | |
_use_baseParentFolder_mode = true; | |
_baseParentFolder = indexInArc; | |
} | |
HRESULT SetDirsTimes(); | |
}; | |
#endif |