⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ppmddecoder.cpp

📁 7-Zip 3.11的源码
💻 CPP
字号:
// PPMDDecoder.cpp

#include "StdAfx.h"

#include "Common/Defs.h"
#include "Windows/Defs.h"

#include "PPMDDecoder.h"

namespace NCompress {
namespace NPPMD {

STDMETHODIMP CDecoder::SetDecoderProperties(ISequentialInStream *inStream)
{
  UINT32 processedSize;
  RINOK(inStream->Read(&_order, 
      sizeof(_order), &processedSize));
  if (processedSize != sizeof(_order))
    return E_FAIL;
  RINOK(inStream->Read(&_usedMemorySize, 
      sizeof(_usedMemorySize), &processedSize));
  if (processedSize != sizeof(_usedMemorySize))
    return E_FAIL;
  return S_OK;
}

class CDecoderFlusher
{
  CDecoder *_coder;
public:
  CDecoderFlusher(CDecoder *coder): _coder(coder) {}
  ~CDecoderFlusher()
  {
    _coder->Flush();
    // _coder->ReleaseStreams();
  }
};

UINT32 GetMatchLen(const BYTE *pointer1, const BYTE *pointer2, 
    UINT32 limit)
{  
  UINT32 i;
  for(i = 0; i < limit && *pointer1 == *pointer2; 
      pointer1++, pointer2++, i++);
  return i;
}

STDMETHODIMP CDecoder::CodeReal(ISequentialInStream *inStream,
      ISequentialOutStream *outStream, const UINT64 *inSize, const UINT64 *outSize,
      ICompressProgressInfo *progress)
{
  _rangeDecoder.Init(inStream);
  _outStream.Init(outStream);

  CDecoderFlusher flusher(this);

  /*
  if (outSize == NULL)
    return E_INVALIDARG;
  */

  UINT64 progressPosValuePrev = 0, pos = 0;

  try
  {
    if (!_info.SubAllocator.StartSubAllocator(_usedMemorySize)) 
      return E_OUTOFMEMORY;
  }
  catch(...)
  {
    return E_OUTOFMEMORY;
  }

  // _info.Init();
  // _info.MaxOrder = _order; 
  _info.MaxOrder = 0;
  _info.StartModelRare(_order);

  UINT64 size = (outSize == NULL) ? (UINT64)(INT64)(-1) : *outSize;

  while(pos < size)
  {
    pos++;
    int symbol = _info.DecodeSymbol(&_rangeDecoder);
    if (symbol < 0)
      return S_OK;
    _outStream.WriteByte(symbol);
    if (pos - progressPosValuePrev >= (1 << 18) && progress != NULL)
    {
      UINT64 inSize = _rangeDecoder.GetProcessedSize();
      RINOK(progress->SetRatioInfo(&inSize, &pos));
      progressPosValuePrev = pos;
    }
  }
  return S_OK;
}

STDMETHODIMP CDecoder::Code(ISequentialInStream *inStream,
    ISequentialOutStream *outStream, const UINT64 *inSize, const UINT64 *outSize,
    ICompressProgressInfo *progress)
{
  try { return CodeReal(inStream, outStream, inSize, outSize, progress); }
  catch(const COutBufferException &e) { return e.ErrorCode; }
  catch(const CInBufferException &e) { return e.ErrorCode; }
  catch(...) { return E_FAIL; }
}


}}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -