diff options
author | Igor Pavlov <ipavlov@users.sourceforge.net> | 2007-08-03 04:00:00 +0400 |
---|---|---|
committer | Kornel LesiĆski <kornel@geekhood.net> | 2016-05-28 02:15:53 +0300 |
commit | 33ccab7e728a996800e166d849fe1e92a17e1afe (patch) | |
tree | e9d1148bae1da8127a3eefbc217aafd736fb74af | |
parent | d14d4dcdefbef6695a618c3cdac05ba2ede5572e (diff) |
4.52 beta
26 files changed, 912 insertions, 135 deletions
diff --git a/CPP/7zip/Archive/Cab/CabBlockInStream.h b/CPP/7zip/Archive/Cab/CabBlockInStream.h index 46e15222..b8b5d8b9 100755 --- a/CPP/7zip/Archive/Cab/CabBlockInStream.h +++ b/CPP/7zip/Archive/Cab/CabBlockInStream.h @@ -17,7 +17,6 @@ class CCabBlockInStream: Byte *_buffer; UInt32 _pos; UInt32 _size; - int _align; public: UInt32 TotalPackSize; @@ -25,24 +24,13 @@ public: bool DataError; bool MsZip; - CCabBlockInStream(): _buffer(0), ReservedSize(0), MsZip(false), DataError(false), _align(0), TotalPackSize(0) {} + CCabBlockInStream(): _buffer(0), ReservedSize(0), MsZip(false), DataError(false), TotalPackSize(0) {} ~CCabBlockInStream(); bool Create(); void SetStream(ISequentialInStream *stream) { _stream = stream; } - void InitForNewFolder() - { - _align = 0; - TotalPackSize = 0; - } - - void InitForNewBlock() - { - _size = 0; - _align = (_align + (int)TotalPackSize) & 1; - } - - int GetAlign() const { return _align; } + void InitForNewFolder() { TotalPackSize = 0; } + void InitForNewBlock() { _size = 0; } MY_UNKNOWN_IMP diff --git a/CPP/7zip/Archive/Cab/CabHandler.cpp b/CPP/7zip/Archive/Cab/CabHandler.cpp index 1c0e2feb..2ce9d9ce 100755 --- a/CPP/7zip/Archive/Cab/CabHandler.cpp +++ b/CPP/7zip/Archive/Cab/CabHandler.cpp @@ -769,7 +769,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems, res = deflateDecoder->Code(cabBlockInStream, outStream, NULL, &unpackRemain, NULL); break; case NHeader::NCompressionMethodMajor::kLZX: - lzxDecoderSpec->SetKeepHistory(keepHistory, cabBlockInStreamSpec->GetAlign()); + lzxDecoderSpec->SetKeepHistory(keepHistory); res = lzxDecoder->Code(cabBlockInStream, outStream, NULL, &unpackRemain, NULL); break; case NHeader::NCompressionMethodMajor::kQuantum: diff --git a/CPP/7zip/Archive/Chm/ChmHandler.cpp b/CPP/7zip/Archive/Chm/ChmHandler.cpp index 5de871da..a3c3b6a0 100755 --- a/CPP/7zip/Archive/Chm/ChmHandler.cpp +++ b/CPP/7zip/Archive/Chm/ChmHandler.cpp @@ -262,7 +262,7 @@ public: const CFilesDatabase *database, IArchiveExtractCallback *extractCallback, bool testMode); - HRESULT FlushCorrupted(); + HRESULT FlushCorrupted(UInt64 maxSize); }; void CChmFolderOutStream::Init( @@ -356,7 +356,7 @@ HRESULT CChmFolderOutStream::Write2(const void *data, UInt32 size, UInt32 *proce else { if (m_CurrentIndex >= m_NumFiles) - return E_FAIL; + return E_FAIL; int fullIndex = m_StartIndex + m_CurrentIndex; m_RemainFileSize = m_Database->GetFileSize(fullIndex); UInt64 fileOffset = m_Database->GetFileOffset(fullIndex); @@ -390,17 +390,21 @@ STDMETHODIMP CChmFolderOutStream::Write(const void *data, UInt32 size, UInt32 *p return Write2(data, size, processedSize, true); } -HRESULT CChmFolderOutStream::FlushCorrupted() +HRESULT CChmFolderOutStream::FlushCorrupted(UInt64 maxSize) { const UInt32 kBufferSize = (1 << 10); Byte buffer[kBufferSize]; for (int i = 0; i < kBufferSize; i++) buffer[i] = 0; - while(m_PosInFolder < m_FolderSize) + if (maxSize > m_FolderSize) + maxSize = m_FolderSize; + while (m_PosInFolder < maxSize) { - UInt32 size = (UInt32)MyMin(m_FolderSize - m_PosInFolder, (UInt64)kBufferSize); + UInt32 size = (UInt32)MyMin(maxSize - m_PosInFolder, (UInt64)kBufferSize); UInt32 processedSizeLocal = 0; RINOK(Write2(buffer, size, &processedSizeLocal, false)); + if (processedSizeLocal == 0) + return S_OK; } return S_OK; } @@ -688,24 +692,28 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems, UInt64 bCur = startBlock + b; if (bCur >= rt.ResetOffsets.Size()) return E_FAIL; - UInt64 startOffset = rt.ResetOffsets[(int)startBlock]; UInt64 offset = rt.ResetOffsets[(int)bCur]; UInt64 compressedSize; rt.GetCompressedSizeOfBlock(bCur, compressedSize); UInt64 rem = finishPos - chmFolderOutStream->m_PosInSection; if (rem > rt.BlockSize) rem = rt.BlockSize; - // const UInt64 *offsets = (const UInt64 *)&rt.ResetOffsets.Front(); RINOK(m_Stream->Seek(compressedPos + offset, STREAM_SEEK_SET, NULL)); streamSpec->SetStream(m_Stream); streamSpec->Init(compressedSize); - lzxDecoderSpec->SetKeepHistory(b > 0, (int)((offset - startOffset) & 1)); - RINOK(lzxDecoder->Code(inStream, outStream, NULL, &rem, NULL)); + lzxDecoderSpec->SetKeepHistory(b > 0); + HRESULT res = lzxDecoder->Code(inStream, outStream, NULL, &rem, NULL); + if (res != S_OK) + { + if (res != S_FALSE) + return res; + throw 1; + } } } catch(...) { - RINOK(chmFolderOutStream->FlushCorrupted()); + RINOK(chmFolderOutStream->FlushCorrupted(unPackSize)); } currentTotalSize += folderSize; if (folderIndex == lastFolderIndex) diff --git a/CPP/7zip/Archive/Com/ComHandler.cpp b/CPP/7zip/Archive/Com/ComHandler.cpp new file mode 100755 index 00000000..6d548256 --- /dev/null +++ b/CPP/7zip/Archive/Com/ComHandler.cpp @@ -0,0 +1,264 @@ +// ComHandler.cpp + +#include "StdAfx.h" + +#include "Common/ComTry.h" +#include "Windows/PropVariant.h" +#include "../../Common/StreamUtils.h" +#include "ComHandler.h" + +namespace NArchive { +namespace NCom { + +STATPROPSTG kProperties[] = +{ + { NULL, kpidPath, VT_BSTR}, + { NULL, kpidIsFolder, VT_BOOL}, + { NULL, kpidSize, VT_UI8}, + // { NULL, kpidAttributes, VT_UI4}, + { NULL, kpidPackedSize, VT_UI8}, + { NULL, kpidCreationTime, VT_FILETIME}, + { NULL, kpidLastWriteTime, VT_FILETIME} +}; + +STDMETHODIMP CHandler::GetArchiveProperty(PROPID /* propID */, PROPVARIANT *value) +{ + value->vt = VT_EMPTY; + return S_OK; +} + +STDMETHODIMP CHandler::GetNumberOfProperties(UInt32 *numProperties) +{ + *numProperties = sizeof(kProperties) / sizeof(kProperties[0]); + return S_OK; +} + +STDMETHODIMP CHandler::GetPropertyInfo(UInt32 index, + BSTR *name, PROPID *propID, VARTYPE *varType) +{ + if(index >= sizeof(kProperties) / sizeof(kProperties[0])) + return E_INVALIDARG; + const STATPROPSTG &srcItem = kProperties[index]; + *propID = srcItem.propid; + *varType = srcItem.vt; + if (srcItem.lpwstrName == 0) + *name = 0; + else + *name = ::SysAllocString(srcItem.lpwstrName); + return S_OK; +} + +STDMETHODIMP CHandler::GetNumberOfArchiveProperties(UInt32 *numProperties) +{ + *numProperties = 0; + return S_OK; +} + +STDMETHODIMP CHandler::GetArchivePropertyInfo(UInt32 /* index */, + BSTR * /* name */, PROPID * /* propID */, VARTYPE * /* varType */) +{ + return E_INVALIDARG; +} + +STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *value) +{ + COM_TRY_BEGIN + NWindows::NCOM::CPropVariant propVariant; + const CRef &ref = _db.Refs[index]; + const CItem &item = _db.Items[ref.Did]; + + switch(propID) + { + case kpidPath: + { + UString name = _db.GetItemPath(index); + propVariant = name; + break; + } + case kpidIsFolder: + propVariant = item.IsDir(); + break; + case kpidCreationTime: + propVariant = item.CreationTime; + break; + case kpidLastWriteTime: + propVariant = item.LastWriteTime; + break; + /* + case kpidAttributes: + propVariant = item.Falgs; + break; + */ + case kpidPackedSize: + if (!item.IsDir()) + { + int numBits = _db.IsLargeStream(item.Size) ? + _db.SectorSizeBits : + _db.MiniSectorSizeBits; + propVariant = (item.Size + ((UInt32)1 << numBits) - 1) >> numBits << numBits; + break; + } + case kpidSize: + if (!item.IsDir()) + propVariant = (UInt64)item.Size; + break; + } + propVariant.Detach(value); + return S_OK; + COM_TRY_END +} + +STDMETHODIMP CHandler::Open(IInStream *inStream, + const UInt64 * /* maxCheckStartPosition */, + IArchiveOpenCallback * /* openArchiveCallback */) +{ + COM_TRY_BEGIN + Close(); + try + { + if (OpenArchive(inStream, _db) != S_OK) + return S_FALSE; + _stream = inStream; + } + catch(...) { return S_FALSE; } + return S_OK; + COM_TRY_END +} + +STDMETHODIMP CHandler::Close() +{ + _db.Clear(); + _stream.Release(); + return S_OK; +} + +STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems, + Int32 _aTestMode, IArchiveExtractCallback *extractCallback) +{ + COM_TRY_BEGIN + bool testMode = (_aTestMode != 0); + bool allFilesMode = (numItems == UInt32(-1)); + if (allFilesMode) + numItems = _db.Refs.Size(); + if (numItems == 0) + return S_OK; + UInt32 i; + UInt64 totalSize = 0; + for(i = 0; i < numItems; i++) + { + const CItem &item = _db.Items[_db.Refs[allFilesMode ? i : indices[i]].Did]; + if (!item.IsDir()) + totalSize += item.Size; + } + RINOK(extractCallback->SetTotal(totalSize)); + + UInt64 currentTotalSize = 0, currentItemSize = 0; + + CByteBuffer sect; + sect.SetCapacity((UInt32)1 << _db.SectorSizeBits); + + for (i = 0; i < numItems; i++, currentTotalSize += currentItemSize) + { + RINOK(extractCallback->SetCompleted(¤tTotalSize)); + Int32 index = allFilesMode ? i : indices[i]; + const CItem &item = _db.Items[_db.Refs[index].Did]; + currentItemSize = 0; + if (!item.IsDir()) + currentItemSize = item.Size; + + CMyComPtr<ISequentialOutStream> realOutStream; + Int32 askMode = testMode ? + NArchive::NExtract::NAskMode::kTest : + NArchive::NExtract::NAskMode::kExtract; + RINOK(extractCallback->GetStream(index, &realOutStream, askMode)); + + if (item.IsDir()) + { + RINOK(extractCallback->PrepareOperation(askMode)); + RINOK(extractCallback->SetOperationResult(NArchive::NExtract::NOperationResult::kOK)); + continue; + } + if (!testMode && (!realOutStream)) + continue; + RINOK(extractCallback->PrepareOperation(askMode)); + Int32 res = NArchive::NExtract::NOperationResult::kDataError; + { + UInt32 sid = item.Sid; + UInt64 prev = 0; + for (UInt64 pos = 0;;) + { + if (sid == NFatID::kEndOfChain) + { + if (pos != item.Size) + break; + res = NArchive::NExtract::NOperationResult::kOK; + break; + } + if (pos >= item.Size) + break; + + UInt64 offset; + UInt32 size; + + if (_db.IsLargeStream(item.Size)) + { + if (pos - prev > (1 << 20)) + { + UInt64 processed = currentTotalSize + pos; + RINOK(extractCallback->SetCompleted(&processed)); + prev = pos; + } + size = 1 << _db.SectorSizeBits; + offset = ((UInt64)sid + 1) << _db.SectorSizeBits; + if (sid >= _db.FatSize) + break; + sid = _db.Fat[sid]; + } + else + { + int subBits = (_db.SectorSizeBits - _db.MiniSectorSizeBits); + UInt32 fid = sid >> subBits; + if (fid >= _db.NumSectorsInMiniStream) + break; + size = 1 << _db.MiniSectorSizeBits; + offset = (((UInt64)_db.MiniSids[fid] + 1) << _db.SectorSizeBits) + + ((sid & ((1 << subBits) - 1)) << _db.MiniSectorSizeBits); + if (sid >= _db.MatSize) + break; + sid = _db.Mat[sid]; + } + + // last sector can be smaller than sector size (it can contain requied data only). + UInt64 rem = item.Size - pos; + if (size > rem) + size = (UInt32)rem; + + RINOK(_stream->Seek(offset, STREAM_SEEK_SET, NULL)); + UInt32 realProcessedSize; + RINOK(ReadStream(_stream, sect, size, &realProcessedSize)); + if (realProcessedSize != size) + break; + + if (realOutStream) + { + RINOK(WriteStream(realOutStream, sect, size, &realProcessedSize)); + if (realProcessedSize != size) + break; + } + pos += size; + } + } + realOutStream.Release(); + RINOK(extractCallback->SetOperationResult(res)); + } + return S_OK; + COM_TRY_END +} + +STDMETHODIMP CHandler::GetNumberOfItems(UInt32 *numItems) +{ + *numItems = _db.Refs.Size(); + return S_OK; +} + +}} diff --git a/CPP/7zip/Archive/Com/ComHandler.h b/CPP/7zip/Archive/Com/ComHandler.h new file mode 100755 index 00000000..f8b2b135 --- /dev/null +++ b/CPP/7zip/Archive/Com/ComHandler.h @@ -0,0 +1,28 @@ +// ComHandler.h + +#ifndef __ARCHIVE_COM_HANDLER_H +#define __ARCHIVE_COM_HANDLER_H + +#include "Common/MyCom.h" +#include "../IArchive.h" +#include "ComIn.h" + +namespace NArchive { +namespace NCom { + +class CHandler: + public IInArchive, + public CMyUnknownImp +{ +public: + MY_UNKNOWN_IMP1(IInArchive) + INTERFACE_IInArchive(;) + +private: + CMyComPtr<IInStream> _stream; + CDatabase _db; +}; + +}} + +#endif diff --git a/CPP/7zip/Archive/Com/ComIn.cpp b/CPP/7zip/Archive/Com/ComIn.cpp new file mode 100755 index 00000000..0db3f1c6 --- /dev/null +++ b/CPP/7zip/Archive/Com/ComIn.cpp @@ -0,0 +1,371 @@ +// Archive/ComIn.cpp + +#include "StdAfx.h" + +extern "C" +{ +#include "../../../../C/Alloc.h" +} + +#include "Common/MyCom.h" +#include "../../Common/StreamUtils.h" +#include "Common/IntToString.h" + +#include "ComIn.h" + +namespace NArchive{ +namespace NCom{ + +static const UInt32 kSignatureSize = 8; +static const Byte kSignature[kSignatureSize] = { 0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1 }; + +static HRESULT ReadBytes(ISequentialInStream *inStream, void *data, UInt32 size) +{ + UInt32 realProcessedSize; + RINOK(ReadStream(inStream, data, size, &realProcessedSize)); + return (realProcessedSize == size) ? S_OK : S_FALSE; +} + +#ifdef LITTLE_ENDIAN_UNALIGN +#define GetUi16(p) (*(const UInt16 *)(p)) +#define GetUi32(p) (*(const UInt32 *)(p)) +#else +#define GetUi16(p) ((p)[0] | ((UInt16)(p)[1] << 8)) +#define GetUi32(p) ((p)[0] | ((UInt32)(p)[1] << 8) | ((UInt32)(p)[2] << 16) | ((UInt32)(p)[3] << 24)) +#endif + + +void CUInt32Buf::Free() +{ + MyFree(_buf); + _buf = 0; +} + +bool CUInt32Buf::Allocate(UInt32 numItems) +{ + Free(); + if (numItems == 0) + return true; + size_t newSize = (size_t)numItems * sizeof(UInt32); + if (newSize / sizeof(UInt32) != numItems) + return false; + _buf = (UInt32 *)MyAlloc(newSize); + return (_buf != 0); +} + +static HRESULT ReadSector(IInStream *inStream, Byte *buf, int sectorSizeBits, UInt32 sid) +{ + RINOK(inStream->Seek((((UInt64)sid + 1) << sectorSizeBits), STREAM_SEEK_SET, NULL)); + return ReadBytes(inStream, buf, (UInt32)1 << sectorSizeBits); +} + +static HRESULT ReadIDs(IInStream *inStream, Byte *buf, int sectorSizeBits, UInt32 sid, UInt32 *dest) +{ + RINOK(ReadSector(inStream, buf, sectorSizeBits, sid)); + UInt32 sectorSize = (UInt32)1 << sectorSizeBits; + for (UInt32 t = 0; t < sectorSize; t += 4) + *dest++ = GetUi32(buf + t); + return S_OK; +} + +static void GetFileTimeFromMem(const Byte *p, FILETIME *ft) +{ + ft->dwLowDateTime = GetUi32(p); + ft->dwHighDateTime = GetUi32(p + 4); +} + +static void ReadItem(Byte *p, CItem &item, bool mode64bit) +{ + memcpy(item.Name, p, 64); + // item.NameSize = GetUi16(p + 64); + item.Type = p[66]; + item.LeftDid = GetUi32(p + 68); + item.RightDid = GetUi32(p + 72); + item.SonDid = GetUi32(p + 76); + // item.Flags = GetUi32(p + 96); + GetFileTimeFromMem(p + 100, &item.CreationTime); + GetFileTimeFromMem(p + 108, &item.LastWriteTime); + item.Sid = GetUi32(p + 116); + item.Size = GetUi32(p + 120); + if (mode64bit) + item.Size |= ((UInt64)GetUi32(p + 124) << 32); +} + +static const UInt32 kNoDid = 0xFFFFFFFF; + +HRESULT CDatabase::AddNode(int parent, UInt32 did) +{ + if (did == kNoDid) + return S_OK; + if (did >= (UInt32)Items.Size()) + return S_FALSE; + const CItem &item = Items[did]; + if (item.IsEmpty()) + return S_FALSE; + CRef ref; + ref.Parent = parent; + ref.Did = did; + int index = Refs.Add(ref); + if (Refs.Size() > Items.Size()) + return S_FALSE; + RINOK(AddNode(parent, item.LeftDid)); + RINOK(AddNode(parent, item.RightDid)); + if (item.IsDir()) + { + RINOK(AddNode(index, item.SonDid)); + } + return S_OK; +} + +static const char kCharOpenBracket = '['; +static const char kCharCloseBracket = ']'; + +UString DWORDToString(UInt32 val) +{ + wchar_t buf[32]; + ConvertUInt64ToString(val, buf); + return buf; +} + +static UString CompoundNameToFileName(const UString &s) +{ + UString res; + for (int i = 0; i < s.Length(); i++) + { + wchar_t c = s[i]; + if (c < 0x20) + { + res += kCharOpenBracket; + res += DWORDToString(c); + res += kCharCloseBracket; + } + else + res += c; + } + return res; +} + +static char g_MsiChars[] = +"0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz._"; + +static const wchar_t *kMsi_ID = L""; // L"{msi}"; + +static const int kMsiNumBits = 6; +static const UInt32 kMsiNumChars = 1 << kMsiNumBits; +static const UInt32 kMsiCharMask = kMsiNumChars - 1; +static const UInt32 kMsiStartUnicodeChar = 0x3800; +static const UInt32 kMsiUnicodeRange = kMsiNumChars * (kMsiNumChars + 1); + +bool CompoundMsiNameToFileName(const UString &name, UString &resultName) +{ + resultName.Empty(); + for (int i = 0; i < name.Length(); i++) + { + wchar_t c = name[i]; + if (c < kMsiStartUnicodeChar || c > kMsiStartUnicodeChar + kMsiUnicodeRange) + return false; + if (i == 0) + resultName += kMsi_ID; + c -= kMsiStartUnicodeChar; + + UInt32 c0 = c & kMsiCharMask; + UInt32 c1 = c >> kMsiNumBits; + + if (c1 <= kMsiNumChars) + { + resultName += (wchar_t)g_MsiChars[c0]; + if (c1 == kMsiNumChars) + break; + resultName += (wchar_t)g_MsiChars[c1]; + } + else + resultName += L'!'; + } + return true; +} + +static UString ConvertName(const Byte *p) +{ + UString s; + for (int i = 0; i < kNameSizeMax; i += 2) + { + wchar_t c = (p[i] | (wchar_t)p[i + 1] << 8); + if (c == 0) + break; + s += c; + } + UString msiName; + if (CompoundMsiNameToFileName(s, msiName)) + return msiName; + return CompoundNameToFileName(s); +} + +UString CDatabase::GetItemPath(UInt32 index) const +{ + UString s; + while (index != kNoDid) + { + const CRef &ref = Refs[index]; + const CItem &item = Items[ref.Did]; + if (!s.IsEmpty()) + s = (UString)WCHAR_PATH_SEPARATOR + s; + s = ConvertName(item.Name) + s; + index = ref.Parent; + } + return s; +} + +HRESULT OpenArchive(IInStream *inStream, CDatabase &db) +{ + static const UInt32 kHeaderSize = 512; + Byte p[kHeaderSize]; + RINOK(ReadBytes(inStream, p, kHeaderSize)); + if (memcmp(p, kSignature, kSignatureSize) != 0) + return S_FALSE; + UInt16 majorVer = GetUi16(p + 0x1A); + if (majorVer > 4) + return S_FALSE; + if (GetUi16(p + 0x1C) != 0xFFFE) + return S_FALSE; + UInt16 sectorSizeBits = GetUi16(p + 0x1E); + bool mode64bit = (sectorSizeBits >= 12); + UInt16 miniSectorSizeBits = GetUi16(p + 0x20); + db.SectorSizeBits = sectorSizeBits; + db.MiniSectorSizeBits = miniSectorSizeBits; + + if (sectorSizeBits > 28 || miniSectorSizeBits > 28 || + sectorSizeBits < 7 || miniSectorSizeBits < 2 || miniSectorSizeBits > sectorSizeBits) + return S_FALSE; + UInt32 numSectorsForFAT = GetUi32(p + 0x2C); + db.LongStreamMinSize = GetUi32(p + 0x38); + + UInt32 sectSize = (UInt32)1 << (int)(sectorSizeBits); + + CByteBuffer sect; + sect.SetCapacity(sectSize); + + int ssb2 = (int)(sectorSizeBits - 2); + UInt32 numSidsInSec = (UInt32)1 << ssb2; + UInt32 numFatItems = numSectorsForFAT << ssb2; + if ((numFatItems >> ssb2) != numSectorsForFAT) + return S_FALSE; + db.FatSize = numFatItems; + + { + CUInt32Buf bat; + UInt32 numSectorsForBat = GetUi32(p + 0x48); + const UInt32 kNumHeaderBatItems = 109; + UInt32 numBatItems = kNumHeaderBatItems + (numSectorsForBat << ssb2); + if (numBatItems < kNumHeaderBatItems || ((numBatItems - kNumHeaderBatItems) >> ssb2) != numSectorsForBat) + return S_FALSE; + if (!bat.Allocate(numBatItems)) + return S_FALSE; + UInt32 i; + for (i = 0; i < kNumHeaderBatItems; i++) + bat[i] = GetUi32(p + 0x4c + i * 4); + UInt32 sid = GetUi32(p + 0x44); + for (UInt32 s = 0; s < numSectorsForBat; s++) + { + RINOK(ReadIDs(inStream, sect, sectorSizeBits, sid, bat + i)); + i += numSidsInSec - 1; + sid = bat[i]; + } + numBatItems = i; + + if (!db.Fat.Allocate(numFatItems)) + return S_FALSE; + UInt32 j = 0; + + for (i = 0; i < numFatItems; j++, i += numSidsInSec) + { + if (j >= numBatItems) + return S_FALSE; + RINOK(ReadIDs(inStream, sect, sectorSizeBits, bat[j], db.Fat + i)); + } + } + + UInt32 numMatItems; + { + UInt32 numSectorsForMat = GetUi32(p + 0x40); + numMatItems = (UInt32)numSectorsForMat << ssb2; + if ((numMatItems >> ssb2) != numSectorsForMat) + return S_FALSE; + if (!db.Mat.Allocate(numMatItems)) + return S_FALSE; + UInt32 i; + UInt32 sid = GetUi32(p + 0x3C); + for (i = 0; i < numMatItems; i += numSidsInSec) + { + RINOK(ReadIDs(inStream, sect, sectorSizeBits, sid, db.Mat + i)); + if (sid >= numFatItems) + return S_FALSE; + sid = db.Fat[sid]; + } + if (sid != NFatID::kEndOfChain) + return S_FALSE; + } + + { + UInt32 sid = GetUi32(p + 0x30); + for (;;) + { + if (sid >= numFatItems) + return S_FALSE; + RINOK(ReadSector(inStream, sect, sectorSizeBits, sid)); + for (UInt32 i = 0; i < sectSize; i += 128) + { + CItem item; + ReadItem(sect + i, item, mode64bit); + db.Items.Add(item); + } + sid = db.Fat[sid]; + if (sid == NFatID::kEndOfChain) + break; + } + } + + CItem root = db.Items[0]; + + { + UInt32 numSectorsInMiniStream; + { + UInt64 numSatSects64 = (root.Size + sectSize - 1) >> sectorSizeBits; + if (numSatSects64 > NFatID::kMaxValue) + return S_FALSE; + numSectorsInMiniStream = (UInt32)numSatSects64; + } + db.NumSectorsInMiniStream = numSectorsInMiniStream; + if (!db.MiniSids.Allocate(numSectorsInMiniStream)) + return S_FALSE; + { + UInt64 matSize64 = (root.Size + (1 << miniSectorSizeBits) - 1) >> miniSectorSizeBits; + if (matSize64 > NFatID::kMaxValue) + return S_FALSE; + db.MatSize = (UInt32)matSize64; + if (numMatItems < db.MatSize) + return S_FALSE; + } + + + UInt32 sid = root.Sid; + for (UInt32 i = 0; ; i++) + { + if (sid == NFatID::kEndOfChain) + { + if (i != numSectorsInMiniStream) + return S_FALSE; + break; + } + if (i >= numSectorsInMiniStream) + return S_FALSE; + db.MiniSids[i] = sid; + if (sid >= numFatItems) + return S_FALSE; + sid = db.Fat[sid]; + } + } + + return db.AddNode(-1, root.SonDid); +} + +}} diff --git a/CPP/7zip/Archive/Com/ComIn.h b/CPP/7zip/Archive/Com/ComIn.h new file mode 100755 index 00000000..683e61dc --- /dev/null +++ b/CPP/7zip/Archive/Com/ComIn.h @@ -0,0 +1,106 @@ +// Archive/ComIn.h + +#ifndef __ARCHIVE_COM_IN_H +#define __ARCHIVE_COM_IN_H + +#include "Common/MyString.h" +#include "Common/Buffer.h" + +namespace NArchive { +namespace NCom { + +struct CUInt32Buf +{ + UInt32 *_buf; +public: + CUInt32Buf(): _buf(0) {} + ~CUInt32Buf() { Free(); } + void Free(); + bool Allocate(UInt32 numItems); + operator UInt32 *() const { return _buf; }; +}; + +namespace NFatID +{ + const UInt32 kFree = 0xFFFFFFFF; + const UInt32 kEndOfChain = 0xFFFFFFFE; + const UInt32 kFatSector = 0xFFFFFFFD; + const UInt32 kMatSector = 0xFFFFFFFC; + const UInt32 kMaxValue = 0xFFFFFFFA; +} + +namespace NItemType +{ + const Byte kEmpty = 0; + const Byte kStorage = 1; + const Byte kStream = 2; + const Byte kLockBytes = 3; + const Byte kProperty = 4; + const Byte kRootStorage = 5; +} + +const UInt32 kNameSizeMax = 64; + +struct CItem +{ + Byte Name[kNameSizeMax]; + // UInt16 NameSize; + // UInt32 Flags; + FILETIME CreationTime; + FILETIME LastWriteTime; + UInt64 Size; + UInt32 LeftDid; + UInt32 RightDid; + UInt32 SonDid; + UInt32 Sid; + Byte Type; + + bool IsEmpty() const { return Type == NItemType::kEmpty; } + bool IsDir() const { return Type == NItemType::kStorage || Type == NItemType::kRootStorage; } +}; + +struct CRef +{ + int Parent; + UInt32 Did; +}; + +class CDatabase +{ +public: + HRESULT AddNode(int parent, UInt32 did); + + CUInt32Buf Fat; + UInt32 FatSize; + + CUInt32Buf MiniSids; + UInt32 NumSectorsInMiniStream; + + CUInt32Buf Mat; + UInt32 MatSize; + + CObjectVector<CItem> Items; + CRecordVector<CRef> Refs; + + UInt32 LongStreamMinSize; + int SectorSizeBits; + int MiniSectorSizeBits; + + void Clear() + { + Fat.Free(); + MiniSids.Free(); + Mat.Free(); + Items.Clear(); + Refs.Clear(); + } + + bool IsLargeStream(UInt64 size) { return size >= LongStreamMinSize; } + UString GetItemPath(UInt32 index) const; +}; + +HRESULT OpenArchive(IInStream *inStream, CDatabase &database); + +}} + +#endif diff --git a/CPP/7zip/Archive/Com/ComRegister.cpp b/CPP/7zip/Archive/Com/ComRegister.cpp new file mode 100755 index 00000000..688c9803 --- /dev/null +++ b/CPP/7zip/Archive/Com/ComRegister.cpp @@ -0,0 +1,13 @@ +// ComRegister.cpp + +#include "StdAfx.h" + +#include "../../Common/RegisterArc.h" + +#include "ComHandler.h" +static IInArchive *CreateArc() { return new NArchive::NCom::CHandler; } + +static CArcInfo g_ArcInfo = + { L"Com", L"msi doc xls ppt", 0, 0xE5, { 0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1 }, 8, false, CreateArc, 0 }; + +REGISTER_ARC(Com) diff --git a/CPP/7zip/Archive/Wim/WimIn.cpp b/CPP/7zip/Archive/Wim/WimIn.cpp index 80ac1954..951fc79b 100755 --- a/CPP/7zip/Archive/Wim/WimIn.cpp +++ b/CPP/7zip/Archive/Wim/WimIn.cpp @@ -123,7 +123,7 @@ HRESULT CUnpacker::Unpack(IInStream *inStream, const CResource &resource, if (outProcessed + outSize > resource.UnpackSize) outSize = (UInt32)(resource.UnpackSize - outProcessed); UInt64 outSize64 = outSize; - lzxDecoderSpec->SetKeepHistory(false, 0); + lzxDecoderSpec->SetKeepHistory(false); ICompressCoder *coder = (inSize == outSize) ? copyCoder : lzxDecoder; RINOK(coder->Code(limitedStreamSpec, outStream, NULL, &outSize64, NULL)); outProcessed += outSize; diff --git a/CPP/7zip/Bundles/Format7zF/Format7z.dsp b/CPP/7zip/Bundles/Format7zF/Format7z.dsp index 66dfd29b..eddccf5e 100755 --- a/CPP/7zip/Bundles/Format7zF/Format7z.dsp +++ b/CPP/7zip/Bundles/Format7zF/Format7z.dsp @@ -2373,6 +2373,30 @@ SOURCE=..\..\Archive\Wim\WimIn.h SOURCE=..\..\Archive\Wim\WimRegister.cpp # End Source File # End Group +# Begin Group "Com" + +# PROP Default_Filter "" +# Begin Source File + +SOURCE=..\..\Archive\Com\ComHandler.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Archive\Com\ComHandler.h +# End Source File +# Begin Source File + +SOURCE=..\..\Archive\Com\ComIn.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Archive\Com\ComIn.h +# End Source File +# Begin Source File + +SOURCE=..\..\Archive\Com\ComRegister.cpp +# End Source File +# End Group # Begin Source File SOURCE=..\..\Archive\IArchive.h diff --git a/CPP/7zip/Bundles/Format7zF/makefile b/CPP/7zip/Bundles/Format7zF/makefile index 00e3e43d..887386ee 100755 --- a/CPP/7zip/Bundles/Format7zF/makefile +++ b/CPP/7zip/Bundles/Format7zF/makefile @@ -108,6 +108,11 @@ CHM_OBJS = \ $O\ChmIn.obj \ $O\ChmRegister.obj \ +COM_OBJS = \ + $O\ComHandler.obj \ + $O\ComIn.obj \ + $O\ComRegister.obj \ + CPIO_OBJS = \ $O\CpioHandler.obj \ $O\CpioHeader.obj \ @@ -339,6 +344,7 @@ OBJS = \ $(BZ2_OBJS) \ $(CAB_OBJS) \ $(CHM_OBJS) \ + $(COM_OBJS) \ $(CPIO_OBJS) \ $(DEB_OBJS) \ $(GZ_OBJS) \ @@ -411,6 +417,8 @@ $(CAB_OBJS): ../../Archive/Cab/$(*B).cpp $(COMPL) $(CHM_OBJS): ../../Archive/Chm/$(*B).cpp $(COMPL) +$(COM_OBJS): ../../Archive/Com/$(*B).cpp + $(COMPL) $(CPIO_OBJS): ../../Archive/Cpio/$(*B).cpp $(COMPL) $(DEB_OBJS): ../../Archive/Deb/$(*B).cpp diff --git a/CPP/7zip/Common/CreateCoder.h b/CPP/7zip/Common/CreateCoder.h index 49f1552a..4d86ae70 100755 --- a/CPP/7zip/Common/CreateCoder.h +++ b/CPP/7zip/Common/CreateCoder.h @@ -30,7 +30,7 @@ HRESULT LoadExternalCodecs(ICompressCodecsInfo *codecsInfo, CObjectVector<CCodec #define DECL_ISetCompressCodecsInfo STDMETHOD(SetCompressCodecsInfo)(ICompressCodecsInfo *compressCodecsInfo); #define IMPL_ISetCompressCodecsInfo2(x) \ STDMETHODIMP x::SetCompressCodecsInfo(ICompressCodecsInfo *compressCodecsInfo) { \ - _codecsInfo = compressCodecsInfo; return LoadExternalCodecs(_codecsInfo, _externalCodecs); } + COM_TRY_BEGIN _codecsInfo = compressCodecsInfo; return LoadExternalCodecs(_codecsInfo, _externalCodecs); COM_TRY_END } #define IMPL_ISetCompressCodecsInfo IMPL_ISetCompressCodecsInfo2(CHandler) #define EXTERNAL_CODECS_VARS2 _codecsInfo, &_externalCodecs diff --git a/CPP/7zip/Compress/Lzx/LzxDecoder.cpp b/CPP/7zip/Compress/Lzx/LzxDecoder.cpp index 8beb879b..5ed05b53 100755 --- a/CPP/7zip/Compress/Lzx/LzxDecoder.cpp +++ b/CPP/7zip/Compress/Lzx/LzxDecoder.cpp @@ -1,4 +1,4 @@ -// LzxDecoder.cpp + // LzxDecoder.cpp #include "StdAfx.h" @@ -18,7 +18,7 @@ const int kLenIdNeedInit = -2; CDecoder::CDecoder(bool wimMode): _keepHistory(false), - m_AlignPos(0), + _skipByte(false), _wimMode(wimMode) { m_x86ConvertOutStreamSpec = new Cx86ConvertOutStream; @@ -94,6 +94,10 @@ bool CDecoder::ReadTables(void) { Byte newLevels[kMaxTableSize]; { + if (_skipByte) + m_InBitStream.DirectReadByte(); + m_InBitStream.Normalize(); + int blockType = (int)ReadBits(kNumBlockTypeBits); if (blockType > kBlockTypeUncompressed) return false; @@ -106,6 +110,9 @@ bool CDecoder::ReadTables(void) m_UnCompressedBlockSize = m_InBitStream.ReadBitsBig(kUncompressedBlockSizeNumBits); m_IsUncompressedBlock = (blockType == kBlockTypeUncompressed); + + _skipByte = (m_IsUncompressedBlock && ((m_UnCompressedBlockSize & 1) != 0)); + if (m_IsUncompressedBlock) { ReadBits(16 - m_InBitStream.GetBitPosition()); @@ -170,12 +177,12 @@ HRESULT CDecoder::CodeSpec(UInt32 curSize) if (_remainLen == kLenIdNeedInit) { _remainLen = 0; - if (_keepHistory && m_IsUncompressedBlock && m_UnCompressedBlockSize > 0) - m_InBitStream.InitDirect(); - else - m_InBitStream.InitNormal(); + m_InBitStream.Init(); + if (!_keepHistory || !m_IsUncompressedBlock) + m_InBitStream.Normalize(); if (!_keepHistory) { + _skipByte = false; m_UnCompressedBlockSize = 0; ClearPrevLevels(); UInt32 i86TranslationSize = 12000000; @@ -196,9 +203,6 @@ HRESULT CDecoder::CodeSpec(UInt32 curSize) } } - if (curSize == 0) - return S_OK; - while(_remainLen > 0 && curSize > 0) { m_OutWindowStream.PutByte(m_OutWindowStream.GetByte(m_RepDistances[0])); @@ -209,8 +213,8 @@ HRESULT CDecoder::CodeSpec(UInt32 curSize) while(curSize > 0) { if (m_UnCompressedBlockSize == 0) - if (!ReadTables()) - return S_FALSE; + if (!ReadTables()) + return S_FALSE; UInt32 next = (Int32)MyMin(m_UnCompressedBlockSize, curSize); curSize -= next; m_UnCompressedBlockSize -= next; @@ -221,11 +225,6 @@ HRESULT CDecoder::CodeSpec(UInt32 curSize) m_OutWindowStream.PutByte(m_InBitStream.DirectReadByte()); next--; } - if (m_UnCompressedBlockSize == 0) - { - m_InBitStream.Align(m_AlignPos); - // m_AlignPos = 0; - } } else while(next > 0) { diff --git a/CPP/7zip/Compress/Lzx/LzxDecoder.h b/CPP/7zip/Compress/Lzx/LzxDecoder.h index 7c549f45..777067e0 100755 --- a/CPP/7zip/Compress/Lzx/LzxDecoder.h +++ b/CPP/7zip/Compress/Lzx/LzxDecoder.h @@ -33,14 +33,7 @@ public: void SetStream(ISequentialInStream *s) { m_Stream.SetStream(s); } void ReleaseStream() { m_Stream.ReleaseStream(); } - void InitNormal() - { - m_Stream.Init(); - m_BitPos = kNumBigValueBits; - Normalize(); - } - - void InitDirect() + void Init() { m_Stream.Init(); m_BitPos = kNumBigValueBits; @@ -100,12 +93,6 @@ public: Byte DirectReadByte() { return m_Stream.ReadByte(); } - void Align(int alignPos) - { - if (((m_Stream.GetProcessedSize() + alignPos) & 1) != 0) - m_Stream.ReadByte(); - Normalize(); - } }; } @@ -137,7 +124,7 @@ class CDecoder : bool _keepHistory; int _remainLen; - int m_AlignPos; + bool _skipByte; bool _wimMode; @@ -171,11 +158,7 @@ public: STDMETHOD(SetOutStreamSize)(const UInt64 *outSize); HRESULT SetParams(int numDictBits); - void SetKeepHistory(bool keepHistory, int alignPos) - { - _keepHistory = keepHistory; - m_AlignPos = alignPos; - } + void SetKeepHistory(bool keepHistory) { _keepHistory = keepHistory; } }; }} diff --git a/CPP/7zip/FileManager/PanelItemOpen.cpp b/CPP/7zip/FileManager/PanelItemOpen.cpp index 25de271a..8ec6596f 100755 --- a/CPP/7zip/FileManager/PanelItemOpen.cpp +++ b/CPP/7zip/FileManager/PanelItemOpen.cpp @@ -143,15 +143,11 @@ HRESULT CPanel::OpenParentArchiveFolder() static const wchar_t *kStartExtensions[] = { - L"exe", - L"bat", - L"com", + L"exe", L"bat", L"com", L"chm", - L"msi", - L"doc", - L"odt", - L"pdf", - L"xls" + L"msi", L"doc", L"xls", L"ppt", + L"odt", L"ods", + L"pdf" }; static bool DoItemAlwaysStart(const UString &name) diff --git a/CPP/7zip/Guid.txt b/CPP/7zip/Guid.txt index 2a4d8abb..3bc6ebe6 100755 --- a/CPP/7zip/Guid.txt +++ b/CPP/7zip/Guid.txt @@ -121,6 +121,7 @@ Handler GUIDs: 09 Nsis 0A Lzma +E5 Compound E6 Wim E7 Iso E8 Bkf diff --git a/CPP/7zip/MyVersion.h b/CPP/7zip/MyVersion.h index 44feed92..8ea6e3ac 100755 --- a/CPP/7zip/MyVersion.h +++ b/CPP/7zip/MyVersion.h @@ -1,8 +1,8 @@ #define MY_VER_MAJOR 4 -#define MY_VER_MINOR 51 +#define MY_VER_MINOR 52 #define MY_VER_BUILD 0 -#define MY_VERSION "4.51 beta" -#define MY_7ZIP_VERSION "7-Zip 4.51 beta" -#define MY_DATE "2007-07-25" +#define MY_VERSION "4.52 beta" +#define MY_7ZIP_VERSION "7-Zip 4.52 beta" +#define MY_DATE "2007-08-03" #define MY_COPYRIGHT "Copyright (c) 1999-2007 Igor Pavlov" #define MY_VERSION_COPYRIGHT_DATE MY_VERSION " " MY_COPYRIGHT " " MY_DATE diff --git a/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp b/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp index bd0dfef6..a38d4173 100755 --- a/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp +++ b/CPP/7zip/UI/Common/ArchiveExtractCallback.cpp @@ -101,7 +101,7 @@ HRESULT CArchiveExtractCallback::GetTime(int index, PROPID propID, FILETIME &fil if (prop.vt == VT_FILETIME) { filetime = prop.filetime; - filetimeIsDefined = true; + filetimeIsDefined = (filetime.dwHighDateTime != 0 || filetime.dwLowDateTime != 0); } else if (prop.vt != VT_EMPTY) return E_FAIL; diff --git a/CPP/7zip/UI/Common/ExtractingFilePath.cpp b/CPP/7zip/UI/Common/ExtractingFilePath.cpp index 86234ac3..fa796ca6 100755 --- a/CPP/7zip/UI/Common/ExtractingFilePath.cpp +++ b/CPP/7zip/UI/Common/ExtractingFilePath.cpp @@ -70,12 +70,9 @@ static bool IsSupportedName(const UString &name) static UString GetCorrectFileName(const UString &path) { - UString result = path; - UString test = path; - // test.Trim(); - if (test == L"..") - result.Replace(L"..", L""); - return ReplaceIncorrectChars(result); + if (path == L".." || path == L".") + return UString(); + return ReplaceIncorrectChars(path); } void MakeCorrectPath(UStringVector &pathParts) diff --git a/CPP/7zip/UI/GUI/CompressDialog.cpp b/CPP/7zip/UI/GUI/CompressDialog.cpp index 3591b14f..99ac831d 100755 --- a/CPP/7zip/UI/GUI/CompressDialog.cpp +++ b/CPP/7zip/UI/GUI/CompressDialog.cpp @@ -309,6 +309,7 @@ bool CCompressDialog::OnInit() OnButtonSFX(); SetEncryptionMethod(); + SetMemoryUsage(); return CModalDialog::OnInit(); } @@ -350,6 +351,7 @@ bool CCompressDialog::OnButtonClicked(int buttonID, HWND buttonHWND) case IDC_COMPRESS_SFX: { OnButtonSFX(); + SetMemoryUsage(); return true; } case IDC_COMPRESS_CHECK_SHOW_PASSWORD: @@ -604,7 +606,16 @@ bool CCompressDialog::OnCommand(int code, int itemID, LPARAM lParam) { case IDC_COMPRESS_COMBO_FORMAT: { - OnChangeFormat(); + bool isSFX = IsSFX(); + SaveOptionsInMem(); + SetLevel(); + SetSolidBlockSize(); + SetNumThreads(); + SetParams(); + CheckControlsEnable(); + SetArchiveName2(isSFX); + SetEncryptionMethod(); + SetMemoryUsage(); return true; } case IDC_COMPRESS_COMBO_LEVEL: @@ -617,6 +628,7 @@ bool CCompressDialog::OnCommand(int code, int itemID, LPARAM lParam) SetSolidBlockSize(); SetNumThreads(); CheckSFXNameChange(); + SetMemoryUsage(); return true; } case IDC_COMPRESS_COMBO_METHOD: @@ -626,6 +638,7 @@ bool CCompressDialog::OnCommand(int code, int itemID, LPARAM lParam) SetSolidBlockSize(); SetNumThreads(); CheckSFXNameChange(); + SetMemoryUsage(); return true; } case IDC_COMPRESS_COMBO_DICTIONARY: @@ -673,19 +686,6 @@ void CCompressDialog::SetArchiveName2(bool prevWasSFX) SetArchiveName(fileName); } -void CCompressDialog::OnChangeFormat() -{ - bool isSFX = IsSFX(); - SaveOptionsInMem(); - SetLevel(); - SetSolidBlockSize(); - SetNumThreads(); - SetParams(); - CheckControlsEnable(); - SetArchiveName2(isSFX); - SetEncryptionMethod(); -} - // if type.KeepName then use OriginalFileName // else if !KeepName remove extension // add new extension @@ -939,10 +939,7 @@ void CCompressDialog::SetDictionary() int methodID = GetMethodID(); UInt32 level = GetLevel2(); if (methodID < 0) - { - SetMemoryUsage(); return; - } const UInt64 maxRamSize = GetMaxRamSizeForProgram(); switch (methodID) { @@ -1042,7 +1039,6 @@ void CCompressDialog::SetDictionary() break; } } - SetMemoryUsage(); } UInt32 CCompressDialog::GetComboValue(NWindows::NControl::CComboBox &c, int defMax) @@ -1084,10 +1080,7 @@ void CCompressDialog::SetOrder() int methodID = GetMethodID(); UInt32 level = GetLevel2(); if (methodID < 0) - { - SetMemoryUsage(); return; - } switch (methodID) { case kLZMA: @@ -1161,7 +1154,6 @@ void CCompressDialog::SetOrder() break; } } - SetMemoryUsage(); } bool CCompressDialog::GetOrderMode() diff --git a/CPP/7zip/UI/GUI/CompressDialog.h b/CPP/7zip/UI/GUI/CompressDialog.h index cf479f0a..a23605d4 100755 --- a/CPP/7zip/UI/GUI/CompressDialog.h +++ b/CPP/7zip/UI/GUI/CompressDialog.h @@ -98,7 +98,6 @@ class CCompressDialog: public NWindows::NControl::CModalDialog int FindRegistryFormat(const UString &name); int FindRegistryFormatAlways(const UString &name); - void OnChangeFormat(); void CheckSFXNameChange(); void SetArchiveName2(bool prevWasSFX); diff --git a/CPP/Common/MyVector.cpp b/CPP/Common/MyVector.cpp index 86e56da0..def2a581 100755 --- a/CPP/Common/MyVector.cpp +++ b/CPP/Common/MyVector.cpp @@ -6,8 +6,7 @@ #include "MyVector.h" -CBaseRecordVector::~CBaseRecordVector() - { Free(); } +CBaseRecordVector::~CBaseRecordVector() { Free(); } void CBaseRecordVector::Free() { @@ -17,16 +16,13 @@ void CBaseRecordVector::Free() _items = 0; } -void CBaseRecordVector::Clear() - { DeleteFrom(0); } -void CBaseRecordVector::DeleteBack() - { Delete(_size - 1); } -void CBaseRecordVector::DeleteFrom(int index) - { Delete(index, _size - index); } +void CBaseRecordVector::Clear() { DeleteFrom(0); } +void CBaseRecordVector::DeleteBack() { Delete(_size - 1); } +void CBaseRecordVector::DeleteFrom(int index) { Delete(index, _size - index); } void CBaseRecordVector::ReserveOnePosition() { - if(_size != _capacity) + if (_size != _capacity) return; int delta; if (_capacity > 64) @@ -40,17 +36,16 @@ void CBaseRecordVector::ReserveOnePosition() void CBaseRecordVector::Reserve(int newCapacity) { - if(newCapacity <= _capacity) + if (newCapacity <= _capacity) return; - /* - #ifndef _DEBUG - static const unsigned int kMaxVectorSize = 0xF0000000; - if(newCapacity < _size || - ((unsigned int )newCapacity * (unsigned int )_itemSize) > kMaxVectorSize) + if ((unsigned)newCapacity >= ((unsigned)1 << (sizeof(unsigned) * 8 - 1))) + throw 1052353; + size_t newSize = (size_t)(unsigned)newCapacity * _itemSize; + if (newSize / _itemSize != (size_t)(unsigned)newCapacity) throw 1052354; - #endif - */ - unsigned char *p = new unsigned char[newCapacity * _itemSize]; + unsigned char *p = new unsigned char[newSize]; + if (p == 0) + throw 1052355; int numRecordsToMove = _capacity; memmove(p, _items, _itemSize * numRecordsToMove); delete [](unsigned char *)_items; diff --git a/CPP/Windows/FileDir.cpp b/CPP/Windows/FileDir.cpp index c94c737d..6d561701 100755 --- a/CPP/Windows/FileDir.cpp +++ b/CPP/Windows/FileDir.cpp @@ -214,9 +214,12 @@ bool MyCreateDirectory(LPCTSTR pathName) if (::CreateDirectory(pathName, NULL)) return true; #ifdef WIN_LONG_PATH2 - UString longPath; - if (GetLongPath(pathName, longPath)) - return BOOLToBool(::CreateDirectoryW(longPath, NULL)); + if (::GetLastError() != ERROR_ALREADY_EXISTS) + { + UString longPath; + if (GetLongPath(pathName, longPath)) + return BOOLToBool(::CreateDirectoryW(longPath, NULL)); + } #endif return false; } @@ -227,11 +230,14 @@ bool MyCreateDirectory(LPCWSTR pathName) if (!g_IsNT) return MyCreateDirectory(GetSysPath(pathName)); if (::CreateDirectoryW(pathName, NULL)) - return true; + return true; #ifdef WIN_LONG_PATH - UString longPath; - if (GetLongPath(pathName, longPath)) - return BOOLToBool(::CreateDirectoryW(longPath, NULL)); + if (::GetLastError() != ERROR_ALREADY_EXISTS) + { + UString longPath; + if (GetLongPath(pathName, longPath)) + return BOOLToBool(::CreateDirectoryW(longPath, NULL)); + } #endif return false; } diff --git a/DOC/7zip.nsi b/DOC/7zip.nsi index 7d2d1cc3..6d7713ba 100755 --- a/DOC/7zip.nsi +++ b/DOC/7zip.nsi @@ -2,7 +2,7 @@ ;Defines !define VERSION_MAJOR 4 -!define VERSION_MINOR 51 +!define VERSION_MINOR 52 !define VERSION_POSTFIX_FULL " beta" !ifdef WIN64 !ifdef IA64 diff --git a/DOC/7zip.wxs b/DOC/7zip.wxs index a1a74e12..09828543 100755 --- a/DOC/7zip.wxs +++ b/DOC/7zip.wxs @@ -1,7 +1,7 @@ <?xml version="1.0"?> <?define VerMajor = "4" ?> -<?define VerMinor = "51" ?> +<?define VerMinor = "52" ?> <?define VerBuild = "00" ?> <?define MmVer = "$(var.VerMajor).$(var.VerMinor)" ?> <?define MmHex = "0$(var.VerMajor)$(var.VerMinor)" ?> @@ -214,7 +214,6 @@ <Component Id="Docs" Guid="$(var.CompDocs)" DiskId="1" Win64="$(var.Is64)"> <File Id="copying.txt" Name="copying.txt" /> <File Id="descript.ion" Name="descript.ion" /> - <File Id="file_id.diz" Name="file_id.diz" /> <File Id="History.txt" Name="History.txt" /> <File Id="License.txt" Name="License.txt" /> <File Id="readme.txt" Name="readme.txt" /> diff --git a/DOC/readme.txt b/DOC/readme.txt index da1acdfa..9e45acf4 100755 --- a/DOC/readme.txt +++ b/DOC/readme.txt @@ -1,4 +1,4 @@ -7-Zip 4.51 Sources +7-Zip 4.52 Sources ------------------ 7-Zip is a file archiver for Windows 95/98/ME/NT/2000/2003/XP/Vista. |