Imported Upstream version 9.20
[platform/upstream/7zip.git] / CPP / 7zip / Compress / BZip2Decoder.h
1 // Compress/BZip2Decoder.h\r
2 \r
3 #ifndef __COMPRESS_BZIP2_DECODER_H\r
4 #define __COMPRESS_BZIP2_DECODER_H\r
5 \r
6 #include "../../Common/MyCom.h"\r
7 \r
8 #ifndef _7ZIP_ST\r
9 #include "../../Windows/Synchronization.h"\r
10 #include "../../Windows/Thread.h"\r
11 #endif\r
12 \r
13 #include "../ICoder.h"\r
14 \r
15 #include "../Common/InBuffer.h"\r
16 #include "../Common/OutBuffer.h"\r
17 \r
18 #include "BitmDecoder.h"\r
19 #include "BZip2Const.h"\r
20 #include "BZip2Crc.h"\r
21 #include "HuffmanDecoder.h"\r
22 \r
23 namespace NCompress {\r
24 namespace NBZip2 {\r
25 \r
26 typedef NCompress::NHuffman::CDecoder<kMaxHuffmanLen, kMaxAlphaSize> CHuffmanDecoder;\r
27 \r
28 class CDecoder;\r
29 \r
30 struct CState\r
31 {\r
32   UInt32 *Counters;\r
33 \r
34   #ifndef _7ZIP_ST\r
35 \r
36   CDecoder *Decoder;\r
37   NWindows::CThread Thread;\r
38   bool m_OptimizeNumTables;\r
39 \r
40   NWindows::NSynchronization::CAutoResetEvent StreamWasFinishedEvent;\r
41   NWindows::NSynchronization::CAutoResetEvent WaitingWasStartedEvent;\r
42 \r
43   // it's not member of this thread. We just need one event per thread\r
44   NWindows::NSynchronization::CAutoResetEvent CanWriteEvent;\r
45 \r
46   Byte MtPad[1 << 8]; // It's pad for Multi-Threading. Must be >= Cache_Line_Size.\r
47 \r
48   HRESULT Create();\r
49   void FinishStream();\r
50   void ThreadFunc();\r
51 \r
52   #endif\r
53 \r
54   CState(): Counters(0) {}\r
55   ~CState() { Free(); }\r
56   bool Alloc();\r
57   void Free();\r
58 };\r
59 \r
60 class CDecoder :\r
61   public ICompressCoder,\r
62   #ifndef _7ZIP_ST\r
63   public ICompressSetCoderMt,\r
64   #endif\r
65   public CMyUnknownImp\r
66 {\r
67 public:\r
68   COutBuffer m_OutStream;\r
69   Byte MtPad[1 << 8]; // It's pad for Multi-Threading. Must be >= Cache_Line_Size.\r
70   NBitm::CDecoder<CInBuffer> m_InStream;\r
71   Byte m_Selectors[kNumSelectorsMax];\r
72   CHuffmanDecoder m_HuffmanDecoders[kNumTablesMax];\r
73   UInt64 _inStart;\r
74 \r
75 private:\r
76 \r
77   bool _needInStreamInit;\r
78 \r
79   UInt32 ReadBits(unsigned numBits);\r
80   Byte ReadByte();\r
81   bool ReadBit();\r
82   UInt32 ReadCrc();\r
83   HRESULT DecodeFile(bool &isBZ, ICompressProgressInfo *progress);\r
84   HRESULT CodeReal(ISequentialInStream *inStream, ISequentialOutStream *outStream,\r
85       bool &isBZ, ICompressProgressInfo *progress);\r
86   class CDecoderFlusher\r
87   {\r
88     CDecoder *_decoder;\r
89   public:\r
90     bool NeedFlush;\r
91     bool ReleaseInStream;\r
92     CDecoderFlusher(CDecoder *decoder, bool releaseInStream):\r
93       _decoder(decoder),\r
94       ReleaseInStream(releaseInStream),\r
95       NeedFlush(true) {}\r
96     ~CDecoderFlusher()\r
97     {\r
98       if (NeedFlush)\r
99         _decoder->Flush();\r
100       _decoder->ReleaseStreams(ReleaseInStream);\r
101     }\r
102   };\r
103 \r
104 public:\r
105   CBZip2CombinedCrc CombinedCrc;\r
106   ICompressProgressInfo *Progress;\r
107 \r
108   #ifndef _7ZIP_ST\r
109   CState *m_States;\r
110   UInt32 m_NumThreadsPrev;\r
111 \r
112   NWindows::NSynchronization::CManualResetEvent CanProcessEvent;\r
113   NWindows::NSynchronization::CCriticalSection CS;\r
114   UInt32 NumThreads;\r
115   bool MtMode;\r
116   UInt32 NextBlockIndex;\r
117   bool CloseThreads;\r
118   bool StreamWasFinished1;\r
119   bool StreamWasFinished2;\r
120   NWindows::NSynchronization::CManualResetEvent CanStartWaitingEvent;\r
121 \r
122   HRESULT Result1;\r
123   HRESULT Result2;\r
124 \r
125   UInt32 BlockSizeMax;\r
126   ~CDecoder();\r
127   HRESULT Create();\r
128   void Free();\r
129 \r
130   #else\r
131   CState m_States[1];\r
132   #endif\r
133 \r
134   CDecoder();\r
135 \r
136   HRESULT SetRatioProgress(UInt64 packSize);\r
137   HRESULT ReadSignatures(bool &wasFinished, UInt32 &crc);\r
138 \r
139   HRESULT Flush() { return m_OutStream.Flush(); }\r
140   void ReleaseStreams(bool releaseInStream)\r
141   {\r
142     if (releaseInStream)\r
143       m_InStream.ReleaseStream();\r
144     m_OutStream.ReleaseStream();\r
145   }\r
146 \r
147   MY_QUERYINTERFACE_BEGIN2(ICompressCoder)\r
148   #ifndef _7ZIP_ST\r
149   MY_QUERYINTERFACE_ENTRY(ICompressSetCoderMt)\r
150   #endif\r
151 \r
152   MY_QUERYINTERFACE_END\r
153   MY_ADDREF_RELEASE\r
154 \r
155   \r
156   STDMETHOD(Code)(ISequentialInStream *inStream, ISequentialOutStream *outStream,\r
157       const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress);\r
158 \r
159   STDMETHOD(SetInStream)(ISequentialInStream *inStream);\r
160   STDMETHOD(ReleaseInStream)();\r
161 \r
162   HRESULT CodeResume(ISequentialOutStream *outStream, bool &isBZ, ICompressProgressInfo *progress);\r
163   UInt64 GetInputProcessedSize() const { return m_InStream.GetProcessedSize(); }\r
164   \r
165   #ifndef _7ZIP_ST\r
166   STDMETHOD(SetNumberOfThreads)(UInt32 numThreads);\r
167   #endif\r
168 };\r
169 \r
170 \r
171 class CNsisDecoder :\r
172   public ISequentialInStream,\r
173   public ICompressSetInStream,\r
174   public ICompressSetOutStreamSize,\r
175   public CMyUnknownImp\r
176 {\r
177   NBitm::CDecoder<CInBuffer> m_InStream;\r
178   Byte m_Selectors[kNumSelectorsMax];\r
179   CHuffmanDecoder m_HuffmanDecoders[kNumTablesMax];\r
180   CState m_State;\r
181   \r
182   int _nsisState;\r
183   UInt32 _tPos;\r
184   unsigned _prevByte;\r
185   unsigned _repRem;\r
186   unsigned _numReps;\r
187   UInt32 _blockSize;\r
188 \r
189 public:\r
190 \r
191   MY_QUERYINTERFACE_BEGIN2(ISequentialInStream)\r
192   MY_QUERYINTERFACE_ENTRY(ICompressSetInStream)\r
193   MY_QUERYINTERFACE_ENTRY(ICompressSetOutStreamSize)\r
194   MY_QUERYINTERFACE_END\r
195   MY_ADDREF_RELEASE\r
196 \r
197   STDMETHOD(Read)(void *data, UInt32 size, UInt32 *processedSize);\r
198   STDMETHOD(SetInStream)(ISequentialInStream *inStream);\r
199   STDMETHOD(ReleaseInStream)();\r
200   STDMETHOD(SetOutStreamSize)(const UInt64 *outSize);\r
201 };\r
202 \r
203 }}\r
204 \r
205 #endif\r