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

📄 cpioin.cpp

📁 由7-zip提供的压缩、解压缩程序
💻 CPP
字号:
// Archive/cpioIn.cpp#include "StdAfx.h"#include "CpioIn.h"#include "Common/StringToInt.h"#include "Windows/Defs.h"#include "../../Common/StreamUtils.h"#include "CpioHeader.h"namespace NArchive {namespace NCpio { HRESULT CInArchive::ReadBytes(void *data, UInt32 size, UInt32 &processedSize){  RINOK(ReadStream(m_Stream, data, size, &processedSize));  m_Position += processedSize;  return S_OK;}Byte CInArchive::ReadByte(){  if (_blockPos >= _blockSize)    throw "Incorrect cpio archive";  return _block[_blockPos++];}UInt16 CInArchive::ReadUInt16(){  UInt16 value = 0;  for (int i = 0; i < 2; i++)  {    Byte b = ReadByte();    value |= (UInt16(b) << (8 * i));  }  return value;}UInt32 CInArchive::ReadUInt32(){  UInt32 value = 0;  for (int i = 0; i < 4; i++)  {    Byte b = ReadByte();    value |= (UInt32(b) << (8 * i));  }  return value;}HRESULT CInArchive::Open(IInStream *inStream){  RINOK(inStream->Seek(0, STREAM_SEEK_CUR, &m_Position));  m_Stream = inStream;  return S_OK;}bool CInArchive::ReadNumber(UInt32 &resultValue){  resultValue = 0;  for (int i = 0; i < 8; i++)  {    char c = char(ReadByte());    int d;    if (c >= '0' && c <= '9')      d = c - '0';    else if (c >= 'A' && c <= 'F')      d = 10 + c - 'A';    else if (c >= 'a' && c <= 'f')      d = 10 + c - 'a';    else      return false;    resultValue *= 0x10;    resultValue += d;  }  return true;}static bool OctalToNumber(const char *s, UInt64 &res){  const char *end;  res = ConvertOctStringToUInt64(s, &end);  return (*end == ' ' || *end == 0);}static bool OctalToNumber32(const char *s, UInt32 &res){  UInt64 res64;  if (!OctalToNumber(s, res64))    return false;  res = (UInt32)res64;  return (res64 <= 0xFFFFFFFF);}bool CInArchive::ReadOctNumber(int size, UInt32 &resultValue){  char sz[32 + 4];  int i;  for (i = 0; i < size && i < 32; i++)    sz[i] = (char)ReadByte();  sz[i] = 0;  return OctalToNumber32(sz, resultValue);}#define GetFromHex(y) { if (!ReadNumber(y)) return S_FALSE; }#define GetFromOct6(y) { if (!ReadOctNumber(6, y)) return S_FALSE; }#define GetFromOct11(y) { if (!ReadOctNumber(11, y)) return S_FALSE; }static unsigned short ConvertValue(unsigned short value, bool convert){  if (!convert)    return value;  return (((unsigned short)(value & 0xFF)) << 8) | (value >> 8);}static UInt32 GetAlignedSize(UInt32 size, UInt32 align){  while ((size & (align - 1)) != 0)    size++;  return size;}HRESULT CInArchive::GetNextItem(bool &filled, CItemEx &item){  filled = false;  UInt32 processedSize;  item.HeaderPosition = m_Position;  _blockSize = kMaxBlockSize;  RINOK(ReadBytes(_block, 2, processedSize));  if (processedSize != 2)    return S_FALSE;  _blockPos = 0;  UInt32 nameSize;  bool oldBE =     _block[0] == NFileHeader::NMagic::kMagicForRecord2[1] &&    _block[1] == NFileHeader::NMagic::kMagicForRecord2[0];  bool binMode = (_block[0] == NFileHeader::NMagic::kMagicForRecord2[0] &&    _block[1] == NFileHeader::NMagic::kMagicForRecord2[1]) ||     oldBE;  if (binMode)  {    RINOK(ReadBytes(_block + 2, NFileHeader::kRecord2Size - 2, processedSize));    if (processedSize != NFileHeader::kRecord2Size - 2)      return S_FALSE;    item.Align = 2;    _blockPos = 2;    item.DevMajor = 0;    item.DevMinor = ConvertValue(ReadUInt16(), oldBE);    item.inode = ConvertValue(ReadUInt16(), oldBE);    item.Mode = ConvertValue(ReadUInt16(), oldBE);    item.UID = ConvertValue(ReadUInt16(), oldBE);    item.GID = ConvertValue(ReadUInt16(), oldBE);    item.NumLinks = ConvertValue(ReadUInt16(), oldBE);    item.RDevMajor =0;    item.RDevMinor = ConvertValue(ReadUInt16(), oldBE);    UInt16 timeHigh = ConvertValue(ReadUInt16(), oldBE);    UInt16 timeLow = ConvertValue(ReadUInt16(), oldBE);    item.ModificationTime = (UInt32(timeHigh) << 16) + timeLow;    nameSize = ConvertValue(ReadUInt16(), oldBE);    UInt16 sizeHigh = ConvertValue(ReadUInt16(), oldBE);    UInt16 sizeLow = ConvertValue(ReadUInt16(), oldBE);    item.Size = (UInt32(sizeHigh) << 16) + sizeLow;    item.ChkSum = 0;    item.HeaderSize = GetAlignedSize(        nameSize + NFileHeader::kRecord2Size, item.Align);    nameSize = item.HeaderSize - NFileHeader::kRecord2Size;    }  else  {    RINOK(ReadBytes(_block + 2, 4, processedSize));    if (processedSize != 4)      return S_FALSE;    bool magicOK =         memcmp(_block, NFileHeader::NMagic::kMagic1, 6) == 0 ||         memcmp(_block, NFileHeader::NMagic::kMagic2, 6) == 0;    _blockPos = 6;    if (magicOK)    {      RINOK(ReadBytes(_block + 6, NFileHeader::kRecordSize - 6, processedSize));      if (processedSize != NFileHeader::kRecordSize - 6)        return S_FALSE;      item.Align = 4;      GetFromHex(item.inode);      GetFromHex(item.Mode);      GetFromHex(item.UID);      GetFromHex(item.GID);      GetFromHex(item.NumLinks);      UInt32 modificationTime;      GetFromHex(modificationTime);      item.ModificationTime = modificationTime;      GetFromHex(item.Size);      GetFromHex(item.DevMajor);      GetFromHex(item.DevMinor);      GetFromHex(item.RDevMajor);      GetFromHex(item.RDevMinor);      GetFromHex(nameSize);      GetFromHex(item.ChkSum);      item.HeaderSize = GetAlignedSize(          nameSize + NFileHeader::kRecordSize, item.Align);      nameSize = item.HeaderSize - NFileHeader::kRecordSize;      }    else    {      if (!memcmp(_block, NFileHeader::NMagic::kMagic3, 6) == 0)        return S_FALSE;      RINOK(ReadBytes(_block + 6, NFileHeader::kOctRecordSize - 6, processedSize));      if (processedSize != NFileHeader::kOctRecordSize - 6)        return S_FALSE;      item.Align = 1;      item.DevMajor = 0;      GetFromOct6(item.DevMinor);      GetFromOct6(item.inode);      GetFromOct6(item.Mode);      GetFromOct6(item.UID);      GetFromOct6(item.GID);      GetFromOct6(item.NumLinks);      item.RDevMajor = 0;      GetFromOct6(item.RDevMinor);      UInt32 modificationTime;      GetFromOct11(modificationTime);      item.ModificationTime = modificationTime;      GetFromOct6(nameSize);      GetFromOct11(item.Size);  // ?????      item.HeaderSize = GetAlignedSize(          nameSize + NFileHeader::kOctRecordSize, item.Align);      nameSize = item.HeaderSize - NFileHeader::kOctRecordSize;      }  }  if (nameSize == 0 || nameSize >= (1 << 27))    return E_FAIL;  RINOK(ReadBytes(item.Name.GetBuffer(nameSize),       nameSize, processedSize));  if (processedSize != nameSize)    return E_FAIL;  item.Name.ReleaseBuffer();  if (strcmp(item.Name, NFileHeader::NMagic::kEndName) == 0)    return S_OK;  filled = true;  return S_OK;}HRESULT CInArchive::Skeep(UInt64 numBytes){  UInt64 newPostion;  RINOK(m_Stream->Seek(numBytes, STREAM_SEEK_CUR, &newPostion));  m_Position += numBytes;  if (m_Position != newPostion)    return E_FAIL;  return S_OK;}HRESULT CInArchive::SkeepDataRecords(UInt64 dataSize, UInt32 align){  while ((dataSize & (align - 1)) != 0)    dataSize++;  return Skeep(dataSize);}}}

⌨️ 快捷键说明

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