1 // LzmaDecoder.h
2 
3 #ifndef __LZMA_DECODER_H
4 #define __LZMA_DECODER_H
5 
6 // #include "../../../C/Alloc.h"
7 #include "../../../C/LzmaDec.h"
8 
9 #include "../../Common/MyCom.h"
10 #include "../ICoder.h"
11 
12 namespace NCompress {
13 namespace NLzma {
14 
15 class CDecoder:
16   public ICompressCoder,
17   public ICompressSetDecoderProperties2,
18   public ICompressSetFinishMode,
19   public ICompressGetInStreamProcessedSize,
20   public ICompressSetBufSize,
21   #ifndef NO_READ_FROM_CODER
22   public ICompressSetInStream,
23   public ICompressSetOutStreamSize,
24   public ISequentialInStream,
25   #endif
26   public CMyUnknownImp
27 {
28   Byte *_inBuf;
29   UInt32 _inPos;
30   UInt32 _inLim;
31 
32   ELzmaStatus _lzmaStatus;
33 
34 public:
35   bool FinishStream; // set it before decoding, if you need to decode full LZMA stream
36 
37 private:
38   bool _propsWereSet;
39   bool _outSizeDefined;
40   UInt64 _outSize;
41   UInt64 _inProcessed;
42   UInt64 _outProcessed;
43 
44   UInt32 _outStep;
45   UInt32 _inBufSize;
46   UInt32 _inBufSizeNew;
47 
48   // CAlignOffsetAlloc _alloc;
49 
50   CLzmaDec _state;
51 
52   HRESULT CreateInputBuffer();
53   HRESULT CodeSpec(ISequentialInStream *inStream, ISequentialOutStream *outStream, ICompressProgressInfo *progress);
54   void SetOutStreamSizeResume(const UInt64 *outSize);
55 
56 public:
57   MY_QUERYINTERFACE_BEGIN2(ICompressCoder)
58   MY_QUERYINTERFACE_ENTRY(ICompressSetDecoderProperties2)
59   MY_QUERYINTERFACE_ENTRY(ICompressSetFinishMode)
60   MY_QUERYINTERFACE_ENTRY(ICompressGetInStreamProcessedSize)
61   MY_QUERYINTERFACE_ENTRY(ICompressSetBufSize)
62   #ifndef NO_READ_FROM_CODER
63   MY_QUERYINTERFACE_ENTRY(ICompressSetInStream)
64   MY_QUERYINTERFACE_ENTRY(ICompressSetOutStreamSize)
65   MY_QUERYINTERFACE_ENTRY(ISequentialInStream)
66   #endif
67   MY_QUERYINTERFACE_END
68   MY_ADDREF_RELEASE
69 
70   STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,
71       const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);
72   STDMETHOD(SetDecoderProperties2)(const Byte *data, UInt32 size);
73   STDMETHOD(SetFinishMode)(UInt32 finishMode);
74   STDMETHOD(GetInStreamProcessedSize)(UInt64 *value);
75   STDMETHOD(SetOutStreamSize)(const UInt64 *outSize);
76   STDMETHOD(SetInBufSize)(UInt32 streamIndex, UInt32 size);
77   STDMETHOD(SetOutBufSize)(UInt32 streamIndex, UInt32 size);
78 
79   #ifndef NO_READ_FROM_CODER
80 
81 private:
82   CMyComPtr<ISequentialInStream> _inStream;
83 public:
84 
85   STDMETHOD(SetInStream)(ISequentialInStream *inStream);
86   STDMETHOD(ReleaseInStream)();
87   STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);
88 
89   HRESULT CodeResume(ISequentialOutStream *outStream, const UInt64 *outSize, ICompressProgressInfo *progress);
90   HRESULT ReadFromInputStream(void *data, UInt32 size, UInt32 *processedSize);
91 
92   #endif
93 
GetInputProcessedSize()94   UInt64 GetInputProcessedSize() const { return _inProcessed; }
95 
96   CDecoder();
97   virtual ~CDecoder();
98 
GetOutputProcessedSize()99   UInt64 GetOutputProcessedSize() const { return _outProcessed; }
100 
NeedsMoreInput()101   bool NeedsMoreInput() const { return _lzmaStatus == LZMA_STATUS_NEEDS_MORE_INPUT; }
102 
CheckFinishStatus(bool withEndMark)103   bool CheckFinishStatus(bool withEndMark) const
104   {
105     return _lzmaStatus == (withEndMark ?
106         LZMA_STATUS_FINISHED_WITH_MARK :
107         LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK);
108   }
109 };
110 
111 }}
112 
113 #endif
114