"Fossies" - the Fresh Open Source Software Archive  

Source code changes of the file "CPP/7zip/Compress/ShrinkDecoder.cpp" between
p7zip_15.14.1_src_all.tar.gz and p7zip_16.02_src_all.tar.gz

About: p7zip is a command-line file archiver with a high compression ratio (a port of the Windows program 7za.exe).

ShrinkDecoder.cpp  (p7zip_15.14.1_src_all):ShrinkDecoder.cpp  (p7zip_16.02_src_all)
// ShrinkDecoder.cpp // ShrinkDecoder.cpp
#include "StdAfx.h" #include "StdAfx.h"
#include <stdio.h>
#include "../../../C/Alloc.h" #include "../../../C/Alloc.h"
#include "../Common/InBuffer.h" #include "../Common/InBuffer.h"
#include "../Common/OutBuffer.h" #include "../Common/OutBuffer.h"
#include "BitlDecoder.h" #include "BitlDecoder.h"
#include "ShrinkDecoder.h" #include "ShrinkDecoder.h"
namespace NCompress { namespace NCompress {
namespace NShrink { namespace NShrink {
static const UInt32 kBufferSize = (1 << 20); static const UInt32 kBufferSize = (1 << 18);
static const int kNumMinBits = 9; static const unsigned kNumMinBits = 9;
HRESULT CDecoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream * outStream, HRESULT CDecoder::CodeReal(ISequentialInStream *inStream, ISequentialOutStream * outStream,
const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgress Info *progress) const UInt64 * /* inSize */, const UInt64 * /* outSize */, ICompressProgress Info *progress)
{ {
NBitl::CBaseDecoder<CInBuffer> inBuffer; NBitl::CBaseDecoder<CInBuffer> inBuffer;
COutBuffer outBuffer; COutBuffer outBuffer;
if (!inBuffer.Create(kBufferSize)) if (!inBuffer.Create(kBufferSize))
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
inBuffer.SetStream(inStream); inBuffer.SetStream(inStream);
inBuffer.Init(); inBuffer.Init();
if (!outBuffer.Create(kBufferSize)) if (!outBuffer.Create(kBufferSize))
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
outBuffer.SetStream(outStream); outBuffer.SetStream(outStream);
outBuffer.Init(); outBuffer.Init();
{
unsigned i;
for (i = 0; i < 257; i++)
_parents[i] = (UInt16)i;
for (; i < kNumItems; i++)
_parents[i] = kNumItems;
for (i = 0; i < kNumItems; i++)
_suffixes[i] = 0;
}
UInt64 prevPos = 0; UInt64 prevPos = 0;
int numBits = kNumMinBits; unsigned numBits = kNumMinBits;
UInt32 head = 257; unsigned head = 257;
bool needPrev = false; int lastSym = -1;
UInt32 lastSymbol = 0; Byte lastChar2 = 0;
int i;
for (i = 0; i < kNumItems; i++)
_parents[i] = 0;
for (i = 0; i < kNumItems; i++)
_suffixes[i] = 0;
for (i = 0; i < 257; i++)
_isFree[i] = false;
for (; i < kNumItems; i++)
_isFree[i] = true;
for (;;) for (;;)
{ {
UInt32 symbol = inBuffer.ReadBits(numBits); UInt32 sym = inBuffer.ReadBits(numBits);
if (inBuffer.ExtraBitsWereRead()) if (inBuffer.ExtraBitsWereRead())
break; break;
if (_isFree[symbol])
return S_FALSE; if (sym == 256)
if (symbol == 256)
{ {
UInt32 symbol = inBuffer.ReadBits(numBits); sym = inBuffer.ReadBits(numBits);
if (symbol == 1) if (sym == 1)
{ {
if (numBits < kNumMaxBits) if (numBits >= kNumMaxBits)
numBits++; return S_FALSE;
numBits++;
continue;
} }
else if (symbol == 2) if (sym != 2)
return S_FALSE;
{ {
if (needPrev) unsigned i;
_isFree[head - 1] = true;
for (i = 257; i < kNumItems; i++) for (i = 257; i < kNumItems; i++)
_isParent[i] = false; _stack[i] = 0;
for (i = 257; i < kNumItems; i++) for (i = 257; i < kNumItems; i++)
if (!_isFree[i]) {
_isParent[_parents[i]] = true; unsigned par = _parents[i];
if (par != kNumItems)
_stack[par] = 1;
}
for (i = 257; i < kNumItems; i++) for (i = 257; i < kNumItems; i++)
if (!_isParent[i]) if (_stack[i] == 0)
_isFree[i] = true; _parents[i] = kNumItems;
head = 257; head = 257;
while (head < kNumItems && !_isFree[head])
head++; continue;
if (head < kNumItems) }
}
bool needPrev = false;
if (head < kNumItems && lastSym >= 0)
{
while (head < kNumItems && _parents[head] != kNumItems)
head++;
if (head < kNumItems)
{
if (head == (unsigned)lastSym)
{ {
needPrev = true; // we need to fix the code for that case
_isFree[head] = false; // _parents[head] is not allowed to link to itself
_parents[head] = (UInt16)lastSymbol; return E_NOTIMPL;
head++;
} }
needPrev = true;
_parents[head] = (UInt16)lastSym;
_suffixes[head] = (Byte)lastChar2;
head++;
} }
else
return S_FALSE;
continue;
} }
UInt32 cur = symbol;
i = 0; if (_parents[sym] == kNumItems)
int corectionIndex = -1; return S_FALSE;
lastSym = sym;
unsigned cur = sym;
unsigned i = 0;
while (cur >= 256) while (cur >= 256)
{ {
if (cur == head - 1)
corectionIndex = i;
_stack[i++] = _suffixes[cur]; _stack[i++] = _suffixes[cur];
cur = _parents[cur]; cur = _parents[cur];
} }
_stack[i++] = (Byte)cur; _stack[i++] = (Byte)cur;
lastChar2 = (Byte)cur;
if (needPrev) if (needPrev)
{
_suffixes[head - 1] = (Byte)cur; _suffixes[head - 1] = (Byte)cur;
if (corectionIndex >= 0)
_stack[corectionIndex] = (Byte)cur;
}
while (i > 0)
outBuffer.WriteByte((_stack[--i]));
while (head < kNumItems && !_isFree[head])
head++;
if (head < kNumItems)
{
needPrev = true;
_isFree[head] = false;
_parents[head] = (UInt16)symbol;
head++;
}
else
needPrev = false;
lastSymbol = symbol;
UInt64 nowPos = outBuffer.GetProcessedSize(); do
if (progress != NULL && nowPos - prevPos > (1 << 18)) outBuffer.WriteByte(_stack[--i]);
while (i);
if (progress)
{ {
prevPos = nowPos; const UInt64 nowPos = outBuffer.GetProcessedSize();
UInt64 packSize = inBuffer.GetProcessedSize(); if (nowPos - prevPos >= (1 << 18))
RINOK(progress->SetRatioInfo(&packSize, &nowPos)); {
prevPos = nowPos;
const UInt64 packSize = inBuffer.GetProcessedSize();
RINOK(progress->SetRatioInfo(&packSize, &nowPos));
}
} }
} }
return outBuffer.Flush(); return outBuffer.Flush();
} }
STDMETHODIMP CDecoder ::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream, STDMETHODIMP CDecoder ::Code(ISequentialInStream *inStream, ISequentialOutStream *outStream,
const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progr ess) const UInt64 *inSize, const UInt64 *outSize, ICompressProgressInfo *progress )
{ {
try { return CodeReal(inStream, outStream, inSize, outSize, progress); } try { return CodeReal(inStream, outStream, inSize, outSize, progress); }
catch(const CInBufferException &e) { return e.ErrorCode; } catch(const CInBufferException &e) { return e.ErrorCode; }
catch(const COutBufferException &e) { return e.ErrorCode; } catch(const COutBufferException &e) { return e.ErrorCode; }
catch(...) { return S_FALSE; } catch(...) { return S_FALSE; }
} }
}} }}
 End of changes. 27 change blocks. 
71 lines changed or deleted 85 lines changed or added

Home  |  About  |  All  |  Newest  |  Fossies Dox  |  Screenshots  |  Comments  |  Imprint  |  Privacy  |  HTTPS