mirror of
https://github.com/Xevion/easy7zip.git
synced 2025-12-08 12:07:03 -06:00
16.00
This commit is contained in:
committed by
Kornel Lesiński
parent
c20d013055
commit
66ac98bb02
@@ -2333,6 +2333,7 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
|
||||
{
|
||||
UInt64 total = 0;
|
||||
bool isThereUndefinedSize = false;
|
||||
bool thereAreLinks = false;
|
||||
|
||||
{
|
||||
@@ -2342,9 +2343,14 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
unsigned index = allFilesMode ? t : indices[t];
|
||||
const CRefItem &ref = _refs[index];
|
||||
const CItem &item = _items[ref.Item];
|
||||
const CItem &lastItem = _items[ref.Last];
|
||||
|
||||
extractStatuses[index] |= kStatus_Extract;
|
||||
total += item.Size;
|
||||
|
||||
if (!lastItem.Is_UnknownSize())
|
||||
total += lastItem.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
|
||||
if (ref.Link >= 0)
|
||||
{
|
||||
@@ -2352,11 +2358,18 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
{
|
||||
if ((unsigned)ref.Link < index)
|
||||
{
|
||||
const CItem &linkItem = _items[_refs[(unsigned)ref.Link].Item];
|
||||
const CRefItem &linkRef = _refs[(unsigned)ref.Link];
|
||||
const CItem &linkItem = _items[linkRef.Item];
|
||||
if (linkItem.IsSolid() && linkItem.Size <= k_CopyLinkFile_MaxSize)
|
||||
{
|
||||
if (extractStatuses[(unsigned)ref.Link] == 0)
|
||||
total += linkItem.Size;
|
||||
{
|
||||
const CItem &lastLinkItem = _items[linkRef.Last];
|
||||
if (!lastLinkItem.Is_UnknownSize())
|
||||
total += lastLinkItem.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
}
|
||||
extractStatuses[(unsigned)ref.Link] |= kStatus_Link;
|
||||
thereAreLinks = true;
|
||||
}
|
||||
@@ -2375,11 +2388,18 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
while (j > solidLimit)
|
||||
{
|
||||
j--;
|
||||
const CItem &item2 = _items[_refs[j].Item];
|
||||
const CRefItem &ref2 = _refs[j];
|
||||
const CItem &item2 = _items[ref2.Item];
|
||||
if (!item2.IsService())
|
||||
{
|
||||
if (extractStatuses[j] == 0)
|
||||
total += item2.Size;
|
||||
{
|
||||
const CItem &lastItem2 = _items[ref2.Last];
|
||||
if (!lastItem2.Is_UnknownSize())
|
||||
total += lastItem2.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
}
|
||||
extractStatuses[j] |= kStatus_Skip;
|
||||
if (!item2.IsSolid())
|
||||
break;
|
||||
@@ -2415,13 +2435,20 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
while (j > solidLimit)
|
||||
{
|
||||
j--;
|
||||
const CItem &item2 = _items[_refs[j].Item];
|
||||
const CRefItem &ref2 = _refs[j];
|
||||
const CItem &item2 = _items[ref2.Item];
|
||||
if (!item2.IsService())
|
||||
{
|
||||
if (extractStatuses[j] != 0)
|
||||
break;
|
||||
extractStatuses[j] = kStatus_Skip;
|
||||
total += item2.Size;
|
||||
{
|
||||
const CItem &lastItem2 = _items[ref2.Last];
|
||||
if (!lastItem2.Is_UnknownSize())
|
||||
total += lastItem2.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
}
|
||||
if (!item2.IsSolid())
|
||||
break;
|
||||
}
|
||||
@@ -2449,7 +2476,10 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
}
|
||||
}
|
||||
|
||||
RINOK(extractCallback->SetTotal(total));
|
||||
if (total != 0 || !isThereUndefinedSize)
|
||||
{
|
||||
RINOK(extractCallback->SetTotal(total));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -2502,8 +2532,12 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
|
||||
const CRefItem *ref = &_refs[index];
|
||||
const CItem *item = &_items[ref->Item];
|
||||
const CItem &lastItem = _items[ref->Last];
|
||||
|
||||
curUnpackSize = 0;
|
||||
if (!lastItem.Is_UnknownSize())
|
||||
curUnpackSize = lastItem.Size;
|
||||
|
||||
curUnpackSize = item->Size;
|
||||
curPackSize = GetPackSize(index);
|
||||
|
||||
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
|
||||
@@ -2532,11 +2566,15 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
{
|
||||
const CRefItem &ref2 = _refs[index2];
|
||||
const CItem &item2 = _items[ref2.Item];
|
||||
const CItem &lastItem2 = _items[ref2.Last];
|
||||
if (!item2.IsSolid())
|
||||
{
|
||||
item = &item2;
|
||||
ref = &ref2;
|
||||
curUnpackSize = item->Size;
|
||||
if (!lastItem2.Is_UnknownSize())
|
||||
curUnpackSize = lastItem2.Size;
|
||||
else
|
||||
curUnpackSize = 0;
|
||||
curPackSize = GetPackSize(index2);
|
||||
}
|
||||
else if ((unsigned)index2 < index)
|
||||
|
||||
@@ -953,6 +953,8 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
|
||||
NCOM::CPropVariant prop;
|
||||
const CRefItem &refItem = _refItems[index];
|
||||
const CItem &item = _items[refItem.ItemIndex];
|
||||
const CItem &lastItem = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
|
||||
/*
|
||||
const CItem *mainItem = &item;
|
||||
if (item.BaseFileIndex >= 0)
|
||||
@@ -972,7 +974,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
|
||||
break;
|
||||
}
|
||||
case kpidIsDir: prop = item.IsDir(); break;
|
||||
case kpidSize: prop = item.Size; break;
|
||||
case kpidSize: if (lastItem.Is_Size_Defined()) prop = lastItem.Size; break;
|
||||
case kpidPackSize: prop = GetPackSize(index); break;
|
||||
case kpidMTime: RarTimeToProp(item.MTime, prop); break;
|
||||
case kpidCTime: if (item.CTimeDefined) RarTimeToProp(item.CTime, prop); break;
|
||||
@@ -985,7 +987,6 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
|
||||
case kpidSplitAfter: prop = _items[refItem.ItemIndex + refItem.NumItems - 1].IsSplitAfter(); break;
|
||||
case kpidCRC:
|
||||
{
|
||||
const CItem &lastItem = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
prop = ((lastItem.IsSplitAfter()) ? item.FileCRC : lastItem.FileCRC);
|
||||
break;
|
||||
}
|
||||
@@ -1378,34 +1379,52 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
CRecordVector<unsigned> importantIndexes;
|
||||
CRecordVector<bool> extractStatuses;
|
||||
|
||||
bool isThereUndefinedSize = false;
|
||||
|
||||
for (UInt32 t = 0; t < numItems; t++)
|
||||
{
|
||||
unsigned index = allFilesMode ? t : indices[t];
|
||||
const CRefItem &refItem = _refItems[index];
|
||||
const CItem &item = _items[refItem.ItemIndex];
|
||||
censoredTotalUnPacked += item.Size;
|
||||
// censoredTotalPacked += item.PackSize;
|
||||
|
||||
{
|
||||
const CRefItem &refItem = _refItems[index];
|
||||
const CItem &item = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
|
||||
if (item.Is_Size_Defined())
|
||||
censoredTotalUnPacked += item.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
|
||||
// censoredTotalPacked += item.PackSize;
|
||||
}
|
||||
|
||||
unsigned j;
|
||||
for (j = lastIndex; j <= index; j++)
|
||||
// if (!_items[_refItems[j].ItemIndex].IsSolid())
|
||||
if (!IsSolid(j))
|
||||
lastIndex = j;
|
||||
|
||||
for (j = lastIndex; j <= index; j++)
|
||||
{
|
||||
const CRefItem &refItem = _refItems[j];
|
||||
const CItem &item = _items[refItem.ItemIndex];
|
||||
const CItem &item = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
|
||||
// const CItem &item = _items[j];
|
||||
|
||||
importantTotalUnPacked += item.Size;
|
||||
if (item.Is_Size_Defined())
|
||||
importantTotalUnPacked += item.Size;
|
||||
else
|
||||
isThereUndefinedSize = true;
|
||||
// importantTotalPacked += item.PackSize;
|
||||
importantIndexes.Add(j);
|
||||
extractStatuses.Add(j == index);
|
||||
}
|
||||
|
||||
lastIndex = index + 1;
|
||||
}
|
||||
|
||||
RINOK(extractCallback->SetTotal(importantTotalUnPacked));
|
||||
if (importantTotalUnPacked != 0 || !isThereUndefinedSize)
|
||||
{
|
||||
RINOK(extractCallback->SetTotal(importantTotalUnPacked));
|
||||
}
|
||||
|
||||
UInt64 currentImportantTotalUnPacked = 0;
|
||||
UInt64 currentImportantTotalPacked = 0;
|
||||
UInt64 currentUnPackSize, currentPackSize;
|
||||
@@ -1431,13 +1450,19 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
lps->Init(extractCallback, false);
|
||||
|
||||
bool solidStart = true;
|
||||
for (unsigned i = 0; i < importantIndexes.Size(); i++,
|
||||
|
||||
for (unsigned i = 0;;
|
||||
i++,
|
||||
currentImportantTotalUnPacked += currentUnPackSize,
|
||||
currentImportantTotalPacked += currentPackSize)
|
||||
{
|
||||
lps->InSize = currentImportantTotalPacked;
|
||||
lps->OutSize = currentImportantTotalUnPacked;
|
||||
RINOK(lps->SetCur());
|
||||
|
||||
if (i >= importantIndexes.Size())
|
||||
break;
|
||||
|
||||
CMyComPtr<ISequentialOutStream> realOutStream;
|
||||
|
||||
Int32 askMode;
|
||||
@@ -1452,8 +1477,15 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
|
||||
const CRefItem &refItem = _refItems[index];
|
||||
const CItem &item = _items[refItem.ItemIndex];
|
||||
|
||||
currentUnPackSize = item.Size;
|
||||
const CItem &lastItem = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
|
||||
UInt64 outSize = (UInt64)(Int64)-1;
|
||||
currentUnPackSize = 0;
|
||||
if (lastItem.Is_Size_Defined())
|
||||
{
|
||||
outSize = lastItem.Size;
|
||||
currentUnPackSize = outSize;
|
||||
}
|
||||
|
||||
currentPackSize = GetPackSize(index);
|
||||
|
||||
@@ -1678,12 +1710,14 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
continue;
|
||||
}
|
||||
|
||||
HRESULT result = commonCoder->Code(inStream, outStream, &packSize, &item.Size, progress);
|
||||
HRESULT result = commonCoder->Code(inStream, outStream, &packSize, &outSize, progress);
|
||||
|
||||
if (item.IsEncrypted())
|
||||
filterStreamSpec->ReleaseInStream();
|
||||
|
||||
const CItem &lastItem = _items[refItem.ItemIndex + refItem.NumItems - 1];
|
||||
if (outSize == (UInt64)(Int64)-1)
|
||||
currentUnPackSize = outStreamSpec->GetSize();
|
||||
|
||||
int opRes = (volsInStreamSpec->CrcIsOK && outStreamSpec->GetCRC() == lastItem.FileCRC) ?
|
||||
NExtract::NOperationResult::kOK:
|
||||
NExtract::NOperationResult::kCRCError;
|
||||
|
||||
@@ -42,6 +42,8 @@ struct CItem
|
||||
|
||||
Byte Salt[8];
|
||||
|
||||
bool Is_Size_Defined() const { return Size != (UInt64)(Int64)-1; }
|
||||
|
||||
bool IsEncrypted() const { return (Flags & NHeader::NFile::kEncrypted) != 0; }
|
||||
bool IsSolid() const { return (Flags & NHeader::NFile::kSolid) != 0; }
|
||||
bool IsCommented() const { return (Flags & NHeader::NFile::kComment) != 0; }
|
||||
|
||||
Reference in New Issue
Block a user