Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/kornelski/7z.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp')
-rwxr-xr-xCPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp86
1 files changed, 86 insertions, 0 deletions
diff --git a/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp b/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp
new file mode 100755
index 00000000..d3450616
--- /dev/null
+++ b/CPP/7zip/Archive/Lzma/LzmaFiltersDecode.cpp
@@ -0,0 +1,86 @@
+// LzmaFiltersDecode.cpp
+
+#include "StdAfx.h"
+
+#include "LzmaFiltersDecode.h"
+
+namespace NArchive {
+namespace NLzma {
+
+static const UInt64 k_LZMA = 0x030101;
+static const UInt64 k_BCJ = 0x03030103;
+
+HRESULT CDecoder::Code(
+ DECL_EXTERNAL_CODECS_LOC_VARS
+ const CHeader &block,
+ ISequentialInStream *inStream, ISequentialOutStream *outStream,
+ UInt64 *inProcessedSize, ICompressProgressInfo *progress)
+{
+ *inProcessedSize = (UInt64)(Int64)-1;
+
+ if (block.FilterMethod > 1)
+ return E_NOTIMPL;
+
+ if (!_lzmaDecoder)
+ {
+ RINOK(CreateCoder(EXTERNAL_CODECS_LOC_VARS k_LZMA, _lzmaDecoder, false));
+ if (_lzmaDecoder == 0)
+ return E_NOTIMPL;
+ }
+
+ {
+ CMyComPtr<ICompressSetDecoderProperties2> setDecoderProperties;
+ _lzmaDecoder.QueryInterface(IID_ICompressSetDecoderProperties2, &setDecoderProperties);
+ if (!setDecoderProperties)
+ return E_NOTIMPL;
+ RINOK(setDecoderProperties->SetDecoderProperties2(block.LzmaProps, 5));
+ }
+
+ bool filteredMode = (block.FilterMethod == 1);
+
+ CMyComPtr<ICompressSetOutStream> setOutStream;
+
+ if (filteredMode)
+ {
+ if (!_bcjStream)
+ {
+ CMyComPtr<ICompressCoder> coder;
+ RINOK(CreateCoder(EXTERNAL_CODECS_LOC_VARS k_BCJ, coder, false));
+ if (!coder)
+ return E_NOTIMPL;
+ coder.QueryInterface(IID_ISequentialOutStream, &_bcjStream);
+ if (!_bcjStream)
+ return E_NOTIMPL;
+ }
+
+ _bcjStream.QueryInterface(IID_ICompressSetOutStream, &setOutStream);
+ if (!setOutStream)
+ return E_NOTIMPL;
+ RINOK(setOutStream->SetOutStream(outStream));
+ outStream = _bcjStream;
+ }
+
+ const UInt64 *unpackSize = block.HasUnpackSize() ? &block.UnpackSize : NULL;
+ RINOK(_lzmaDecoder->Code(inStream, outStream, NULL, unpackSize, progress));
+
+ if (filteredMode)
+ {
+ CMyComPtr<IOutStreamFlush> flush;
+ _bcjStream.QueryInterface(IID_IOutStreamFlush, &flush);
+ if (flush)
+ {
+ RINOK(flush->Flush());
+ }
+ RINOK(setOutStream->ReleaseOutStream());
+ }
+
+ CMyComPtr<ICompressGetInStreamProcessedSize> getInStreamProcessedSize;
+ _lzmaDecoder.QueryInterface(IID_ICompressGetInStreamProcessedSize, &getInStreamProcessedSize);
+ if (getInStreamProcessedSize)
+ {
+ RINOK(getInStreamProcessedSize->GetInStreamProcessedSize(inProcessedSize));
+ }
+ return S_OK;
+}
+
+}}