4.37 beta

This commit is contained in:
Igor Pavlov
2006-03-19 00:00:00 +00:00
committed by Kornel Lesiński
parent 8304895f29
commit cb9eea7264
44 changed files with 691 additions and 170 deletions

View File

@@ -70,7 +70,7 @@ STDAPI GetHandlerProperty(PROPID propID, PROPVARIANT *value)
propVariant = L"iso";
break;
case NArchive::kUpdate:
propVariant = true;
propVariant = false;
break;
case NArchive::kKeepName:
propVariant = false;

View File

@@ -128,7 +128,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidSize:
case kpidPackedSize:
{
propVariant = (UInt64)be.GetSize();
propVariant = (UInt64)_archive.GetBootItemSize(index);
break;
}
}
@@ -146,7 +146,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
if (_archive.IsJoliet())
s = item.GetPathU();
else
s = MultiByteToUnicodeString(item.GetPath(), CP_OEMCP);
s = MultiByteToUnicodeString(item.GetPath(_archive.IsSusp, _archive.SuspSkipSize), CP_OEMCP);
int pos = s.ReverseFind(L';');
if (pos >= 0 && pos == s.Length() - 2)
@@ -210,8 +210,7 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
}
else
{
const CBootInitialEntry &be = _archive.BootEntries[index - _archive.Refs.Size()];
totalSize += be.GetSize();
totalSize += _archive.GetBootItemSize(index - _archive.Refs.Size());
}
}
extractCallback->SetTotal(totalSize);
@@ -248,8 +247,9 @@ STDMETHODIMP CHandler::Extract(const UInt32* indices, UInt32 numItems,
}
else
{
const CBootInitialEntry &be = _archive.BootEntries[index - _archive.Refs.Size()];
currentItemSize = be.GetSize();
int bootIndex = index - _archive.Refs.Size();
const CBootInitialEntry &be = _archive.BootEntries[bootIndex];
currentItemSize = _archive.GetBootItemSize(bootIndex);
blockIndex = be.LoadRBA;
}

View File

@@ -253,6 +253,7 @@ void CInArchive::ReadDir(CDir &d, int level)
SeekToBlock(d.ExtentLocation);
UInt64 startPos = _position;
bool firstItem = true;
while(true)
{
UInt64 offset = _position - startPos;
@@ -263,8 +264,13 @@ void CInArchive::ReadDir(CDir &d, int level)
continue;
CDir subItem;
ReadDirRecord2(subItem, len);
if (firstItem && level == 0)
IsSusp = subItem.CheckSusp(SuspSkipSize);
if (!subItem.IsSystemItem())
d._subItems.Add(subItem);
firstItem = false;
}
for (int i = 0; i < d._subItems.Size(); i++)
ReadDir(d._subItems[i], level + 1);
@@ -404,6 +410,10 @@ HRESULT CInArchive::Open2()
HRESULT CInArchive::Open(IInStream *inStream)
{
_stream = inStream;
UInt64 pos;
RINOK(_stream->Seek(0, STREAM_SEEK_CUR, &pos));
RINOK(_stream->Seek(0, STREAM_SEEK_END, &_archiveSize));
RINOK(_stream->Seek(pos, STREAM_SEEK_SET, &_position));
HRESULT res = S_FALSE;
try { res = Open2(); }
catch(...) { Clear(); res = S_FALSE; }
@@ -418,6 +428,8 @@ void CInArchive::Clear()
VolDescs.Clear();
_bootIsDefined = false;
BootEntries.Clear();
SuspSkipSize = 0;
IsSusp = false;
}
}}

View File

@@ -25,12 +25,12 @@ struct CDir: public CDirRecord
_subItems.Clear();
}
int GetLength() const
int GetLength(bool checkSusp, int skipSize) const
{
int len = FileId.GetCapacity();
int len = GetLengthCur(checkSusp, skipSize);
if (Parent != 0)
if (Parent->Parent != 0)
len += 1 + Parent->GetLength();
len += 1 + Parent->GetLength(checkSusp, skipSize);
return len;
}
@@ -43,19 +43,19 @@ struct CDir: public CDirRecord
return len;
}
AString GetPath() const
AString GetPath(bool checkSusp, int skipSize) const
{
AString s;
int len = GetLength();
int len = GetLength(checkSusp, skipSize);
char *p = s.GetBuffer(len + 1);
p += len;
*p = 0;
const CDir *cur = this;
while(true)
{
int curLen = cur->FileId.GetCapacity();
int curLen = cur->GetLengthCur(checkSusp, skipSize);
p -= curLen;
memmove(p, (const char *)(const Byte *)cur->FileId, curLen);
memmove(p, (const char *)(const Byte *)cur->GetNameCur(checkSusp, skipSize), curLen);
cur = cur->Parent;
if (cur == 0)
break;
@@ -262,13 +262,38 @@ public:
HRESULT Open(IInStream *inStream);
void Clear();
CObjectVector<CRef> Refs;
UInt64 _archiveSize;
CRecordVector<CRef> Refs;
CObjectVector<CVolumeDescriptor> VolDescs;
int MainVolDescIndex;
UInt32 BlockSize;
CObjectVector<CBootInitialEntry> BootEntries;
bool IsJoliet() const { return VolDescs[MainVolDescIndex].IsJoliet(); }
UInt64 GetBootItemSize(int index) const
{
const CBootInitialEntry &be = BootEntries[index];
UInt64 size = be.GetSize();
if (be.BootMediaType == NBootMediaType::k1d2Floppy)
size = (1200 << 10);
else if (be.BootMediaType == NBootMediaType::k1d44Floppy)
size = (1440 << 10);
else if (be.BootMediaType == NBootMediaType::k2d88Floppy)
size = (2880 << 10);
UInt64 startPos = be.LoadRBA * BlockSize;
if (startPos < _archiveSize)
{
if (_archiveSize - startPos < size)
size = _archiveSize - startPos;
}
return size;
}
bool IsSusp;
int SuspSkipSize;
};
}}

View File

@@ -64,6 +64,80 @@ struct CDirRecord
Byte b = *(const Byte *)FileId;
return (b == 0 || b == 1);
}
const Byte* FindSuspName(int skipSize, int &lenRes) const
{
lenRes = 0;
const Byte *p = (const Byte *)SystemUse + skipSize;
int length = SystemUse.GetCapacity() - skipSize;
while (length >= 5)
{
int len = p[2];
if (p[0] == 'N' && p[1] == 'M' && p[3] == 1)
{
lenRes = len - 5;
return p + 5;
}
p += len;
length -= len;
}
return 0;
}
int GetLengthCur(bool checkSusp, int skipSize) const
{
if (checkSusp)
{
int len;
const Byte *res = FindSuspName(skipSize, len);
if (res != 0)
return len;
}
return FileId.GetCapacity();
}
const Byte* GetNameCur(bool checkSusp, int skipSize) const
{
if (checkSusp)
{
int len;
const Byte *res = FindSuspName(skipSize, len);
if (res != 0)
return res;
}
return (const Byte *)FileId;
}
bool CheckSusp(const Byte *p, int &startPos) const
{
if (p[0] == 'S' &&
p[1] == 'P' &&
p[2] == 0x7 &&
p[3] == 0x1 &&
p[4] == 0xBE &&
p[5] == 0xEF)
{
startPos = p[6];
return true;
}
return false;
}
bool CheckSusp(int &startPos) const
{
const Byte *p = (const Byte *)SystemUse;
int length = SystemUse.GetCapacity();
const int kMinLen = 7;
if (length < kMinLen)
return false;
if (CheckSusp(p, startPos))
return true;
const int kOffset2 = 14;
if (length < kOffset2 + kMinLen)
return false;
return CheckSusp(p + kOffset2, startPos);
}
};
}}