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

📄 gziphandlerout.cpp

📁 由7-zip提供的压缩、解压缩程序
💻 CPP
字号:
// Archive/GZip/OutHandler.cpp#include "StdAfx.h"#include "GZipHandler.h"#include "GZipUpdate.h"#include "Common/StringConvert.h"#include "Common/StringToInt.h"#include "Windows/Time.h"#include "Windows/FileFind.h"#include "Windows/PropVariant.h"#include "../../Compress/Copy/CopyCoder.h"#include "../Common/ParseProperties.h"using namespace NWindows;using namespace NTime;namespace NArchive {namespace NGZip {static const UInt32 kNumPassesX1  = 1;static const UInt32 kNumPassesX7  = 3;static const UInt32 kNumPassesX9  = 10;static const UInt32 kNumFastBytesX1 = 32;static const UInt32 kNumFastBytesX7 = 64;static const UInt32 kNumFastBytesX9 = 128;STDMETHODIMP CHandler::GetFileTimeType(UInt32 *timeType){  *timeType = NFileTimeType::kUnix;  return S_OK;}static HRESULT CopyStreams(ISequentialInStream *inStream,     ISequentialOutStream *outStream, IArchiveUpdateCallback *updateCallback){  CMyComPtr<ICompressCoder> copyCoder = new NCompress::CCopyCoder;  return copyCoder->Code(inStream, outStream, NULL, NULL, NULL);}STDMETHODIMP CHandler::UpdateItems(ISequentialOutStream *outStream, UInt32 numItems,    IArchiveUpdateCallback *updateCallback){  if (numItems != 1)    return E_INVALIDARG;  UInt64 size;  Int32 newData;  Int32 newProperties;  UInt32 indexInArchive;  UInt32 itemIndex = 0;  if (!updateCallback)    return E_FAIL;  RINOK(updateCallback->GetUpdateItemInfo(0,       &newData, &newProperties, &indexInArchive));  CItem newItem = m_Item;  newItem.ExtraFlags = 0;  newItem.Flags = 0;  if (IntToBool(newProperties))  {    UInt32 attributes;    FILETIME utcTime;    UString name;    bool isDirectory;    {      NCOM::CPropVariant propVariant;      RINOK(updateCallback->GetProperty(itemIndex, kpidAttributes, &propVariant));      if (propVariant.vt == VT_EMPTY)        attributes = 0;      else if (propVariant.vt != VT_UI4)        return E_INVALIDARG;      else        attributes = propVariant.ulVal;    }    {      NCOM::CPropVariant propVariant;      RINOK(updateCallback->GetProperty(itemIndex, kpidLastWriteTime, &propVariant));      if (propVariant.vt != VT_FILETIME)        return E_INVALIDARG;      utcTime = propVariant.filetime;    }    {      NCOM::CPropVariant propVariant;      RINOK(updateCallback->GetProperty(itemIndex, kpidPath, &propVariant));      if (propVariant.vt == VT_EMPTY)        name.Empty();      else if (propVariant.vt != VT_BSTR)        return E_INVALIDARG;      else        name = propVariant.bstrVal;    }    {      NCOM::CPropVariant propVariant;      RINOK(updateCallback->GetProperty(itemIndex, kpidIsFolder, &propVariant));      if (propVariant.vt == VT_EMPTY)        isDirectory = false;      else if (propVariant.vt != VT_BOOL)        return E_INVALIDARG;      else        isDirectory = (propVariant.boolVal != VARIANT_FALSE);    }    if (isDirectory || NFile::NFind::NAttributes::IsDirectory(attributes))      return E_INVALIDARG;    if(!FileTimeToUnixTime(utcTime, newItem.Time))      return E_INVALIDARG;    newItem.Name = UnicodeStringToMultiByte(name, CP_ACP);    int dirDelimiterPos = newItem.Name.ReverseFind(CHAR_PATH_SEPARATOR);    if (dirDelimiterPos >= 0)      newItem.Name = newItem.Name.Mid(dirDelimiterPos + 1);        newItem.SetNameIsPresentFlag(!newItem.Name.IsEmpty());  }  if (IntToBool(newData))  {    {      NCOM::CPropVariant propVariant;      RINOK(updateCallback->GetProperty(itemIndex, kpidSize, &propVariant));      if (propVariant.vt != VT_UI8)        return E_INVALIDARG;      size = propVariant.uhVal.QuadPart;    }    newItem.UnPackSize32 = (UInt32)size;    UInt32 level = m_Level;    if (level == 0xFFFFFFFF)      level = 5;    if (m_Method.NumPasses == 0xFFFFFFFF)      m_Method.NumPasses = (level >= 9 ? kNumPassesX9 :                            (level >= 7 ? kNumPassesX7 :                                          kNumPassesX1));    if (m_Method.NumFastBytes == 0xFFFFFFFF)      m_Method.NumFastBytes = (level >= 9 ? kNumFastBytesX9 :                               (level >= 7 ? kNumFastBytesX7 :                                             kNumFastBytesX1));    return UpdateArchive(m_Stream, size, outStream, newItem, m_Method, itemIndex, updateCallback);  }      if (indexInArchive != 0)    return E_INVALIDARG;  if (IntToBool(newProperties))  {    COutArchive outArchive;    outArchive.Create(outStream);    outArchive.WriteHeader(newItem);    RINOK(m_Stream->Seek(m_StreamStartPosition + m_DataOffset, STREAM_SEEK_SET, NULL));  }  else  {    RINOK(m_Stream->Seek(m_StreamStartPosition, STREAM_SEEK_SET, NULL));  }  return CopyStreams(m_Stream, outStream, updateCallback);}STDMETHODIMP CHandler::SetProperties(const wchar_t **names, const PROPVARIANT *values, Int32 numProperties){  InitMethodProperties();  for (int i = 0; i < numProperties; i++)  {    UString name = names[i];    name.MakeUpper();    const PROPVARIANT &prop = values[i];    if (name[0] == L'X')    {      UInt32 level = 9;      RINOK(ParsePropValue(name.Mid(1), prop, level));      m_Level = level;    }    else if (name.Left(4) == L"PASS")    {      UInt32 num = kNumPassesX9;      RINOK(ParsePropValue(name.Mid(4), prop, num));      m_Method.NumPasses = num;    }    else if (name.Left(2) == L"FB")    {      UInt32 num = kNumFastBytesX9;      RINOK(ParsePropValue(name.Mid(2), prop, num));      m_Method.NumFastBytes = num;    }    else if (name.Left(2) == L"MC")    {      UInt32 num = 0xFFFFFFFF;      RINOK(ParsePropValue(name.Mid(2), prop, num));      m_Method.NumMatchFinderCycles = num;      m_Method.NumMatchFinderCyclesDefined = true;    }    else      return E_INVALIDARG;  }  return S_OK;}  }}

⌨️ 快捷键说明

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