Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/kornelski/7z.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIgor Pavlov <ipavlov@users.sourceforge.net>2017-04-30 03:00:00 +0300
committerKornel <kornel@geekhood.net>2017-05-05 20:56:20 +0300
commit2efa10565ac395d2ce9a679ead46e70fb2f963eb (patch)
tree84c8df4deb69ec44ea15af9378f24347db55c357 /CPP/7zip/Archive/Nsis
parent603abd5528c97346e9448c0ff47949f818fe558c (diff)
17.0017.00
Diffstat (limited to 'CPP/7zip/Archive/Nsis')
-rw-r--r--CPP/7zip/Archive/Nsis/NsisDecode.cpp49
-rw-r--r--CPP/7zip/Archive/Nsis/NsisDecode.h16
-rw-r--r--CPP/7zip/Archive/Nsis/NsisHandler.cpp18
-rw-r--r--CPP/7zip/Archive/Nsis/NsisIn.cpp51
-rw-r--r--CPP/7zip/Archive/Nsis/NsisIn.h19
5 files changed, 97 insertions, 56 deletions
diff --git a/CPP/7zip/Archive/Nsis/NsisDecode.cpp b/CPP/7zip/Archive/Nsis/NsisDecode.cpp
index daf3df6e..e2822184 100644
--- a/CPP/7zip/Archive/Nsis/NsisDecode.cpp
+++ b/CPP/7zip/Archive/Nsis/NsisDecode.cpp
@@ -11,13 +11,24 @@
#include "../../Common/MethodId.h"
#include "../../Compress/BcjCoder.h"
-#include "../../Compress/BZip2Decoder.h"
#define Get32(p) GetUi32(p)
namespace NArchive {
namespace NNsis {
+UInt64 CDecoder::GetInputProcessedSize() const
+{
+ if (_lzmaDecoder)
+ return _lzmaDecoder->GetInputProcessedSize();
+ if (_deflateDecoder)
+ return _deflateDecoder->GetInputProcessedSize();
+ if (_bzDecoder)
+ return _bzDecoder->GetInputProcessedSize();
+ return 0;
+}
+
+
HRESULT CDecoder::Init(ISequentialInStream *inStream, bool &useFilter)
{
useFilter = false;
@@ -36,7 +47,10 @@ HRESULT CDecoder::Init(ISequentialInStream *inStream, bool &useFilter)
_deflateDecoder = new NCompress::NDeflate::NDecoder::CCOMCoder();
_codecInStream = _deflateDecoder;
break;
- case NMethodType::kBZip2: _codecInStream = new NCompress::NBZip2::CNsisDecoder(); break;
+ case NMethodType::kBZip2:
+ _bzDecoder = new NCompress::NBZip2::CNsisDecoder();
+ _codecInStream = _bzDecoder;
+ break;
case NMethodType::kLZMA:
_lzmaDecoder = new NCompress::NLzma::CDecoder();
_codecInStream = _lzmaDecoder;
@@ -103,15 +117,15 @@ HRESULT CDecoder::Init(ISequentialInStream *inStream, bool &useFilter)
return S_OK;
}
+
static const UInt32 kMask_IsCompressed = (UInt32)1 << 31;
+
HRESULT CDecoder::SetToPos(UInt64 pos, ICompressProgressInfo *progress)
{
if (StreamPos > pos)
return E_FAIL;
- UInt64 inSizeStart = 0;
- if (_lzmaDecoder)
- inSizeStart = _lzmaDecoder->GetInputProcessedSize();
+ const UInt64 inSizeStart = GetInputProcessedSize();
UInt64 offset = 0;
while (StreamPos < pos)
{
@@ -122,14 +136,13 @@ HRESULT CDecoder::SetToPos(UInt64 pos, ICompressProgressInfo *progress)
StreamPos += size;
offset += size;
- UInt64 inSize = 0;
- if (_lzmaDecoder)
- inSize = _lzmaDecoder->GetInputProcessedSize() - inSizeStart;
+ const UInt64 inSize = GetInputProcessedSize() - inSizeStart;
RINOK(progress->SetRatioInfo(&inSize, &offset));
}
return S_OK;
}
+
HRESULT CDecoder::Decode(CByteBuffer *outBuf, bool unpackSizeDefined, UInt32 unpackSize,
ISequentialOutStream *realOutStream, ICompressProgressInfo *progress,
UInt32 &packSizeRes, UInt32 &unpackSizeRes)
@@ -144,9 +157,9 @@ HRESULT CDecoder::Decode(CByteBuffer *outBuf, bool unpackSizeDefined, UInt32 unp
Byte temp[4];
size_t processedSize = 4;
RINOK(Read(temp, &processedSize));
+ StreamPos += processedSize;
if (processedSize != 4)
return S_FALSE;
- StreamPos += processedSize;
UInt32 size = Get32(temp);
if (unpackSizeDefined && size != unpackSize)
return S_FALSE;
@@ -156,8 +169,13 @@ HRESULT CDecoder::Decode(CByteBuffer *outBuf, bool unpackSizeDefined, UInt32 unp
else
{
Byte temp[4];
- RINOK(ReadStream_FALSE(InputStream, temp, 4));
- StreamPos += 4;
+ {
+ size_t processedSize = 4;
+ RINOK(ReadStream(InputStream, temp, &processedSize));
+ StreamPos += processedSize;
+ if (processedSize != 4)
+ return S_FALSE;
+ }
UInt32 size = Get32(temp);
if ((size & kMask_IsCompressed) == 0)
@@ -209,9 +227,7 @@ HRESULT CDecoder::Decode(CByteBuffer *outBuf, bool unpackSizeDefined, UInt32 unp
outBuf->Alloc(unpackSize);
}
- UInt64 inSizeStart = 0;
- if (_lzmaDecoder)
- inSizeStart = _lzmaDecoder->GetInputProcessedSize();
+ const UInt64 inSizeStart = GetInputProcessedSize();
// we don't allow files larger than 4 GB;
if (!unpackSizeDefined)
@@ -254,9 +270,8 @@ HRESULT CDecoder::Decode(CByteBuffer *outBuf, bool unpackSizeDefined, UInt32 unp
StreamPos += size;
offset += (UInt32)size;
- UInt64 inSize = 0; // it can be improved: we need inSize for Deflate and BZip2 too.
- if (_lzmaDecoder)
- inSize = _lzmaDecoder->GetInputProcessedSize() - inSizeStart;
+ const UInt64 inSize = GetInputProcessedSize() - inSizeStart;
+
if (Solid)
packSizeRes = (UInt32)inSize;
unpackSizeRes += (UInt32)size;
diff --git a/CPP/7zip/Archive/Nsis/NsisDecode.h b/CPP/7zip/Archive/Nsis/NsisDecode.h
index ec713d05..2153d785 100644
--- a/CPP/7zip/Archive/Nsis/NsisDecode.h
+++ b/CPP/7zip/Archive/Nsis/NsisDecode.h
@@ -8,6 +8,7 @@
#include "../../Common/FilterCoder.h"
#include "../../Common/StreamUtils.h"
+#include "../../Compress/BZip2Decoder.h"
#include "../../Compress/DeflateDecoder.h"
#include "../../Compress/LzmaDecoder.h"
@@ -38,6 +39,7 @@ class CDecoder
CMyComPtr<ISequentialInStream> _codecInStream;
CMyComPtr<ISequentialInStream> _decoderInStream;
+ NCompress::NBZip2::CNsisDecoder *_bzDecoder;
NCompress::NDeflate::NDecoder::CCOMCoder *_deflateDecoder;
NCompress::NLzma::CDecoder *_lzmaDecoder;
@@ -50,13 +52,17 @@ public:
bool Solid;
bool IsNsisDeflate;
- CByteBuffer Buffer; // temp buf.
+ CByteBuffer Buffer; // temp buf
CDecoder():
FilterFlag(false),
Solid(true),
IsNsisDeflate(true)
- {}
+ {
+ _bzDecoder = NULL;
+ _deflateDecoder = NULL;
+ _lzmaDecoder = NULL;
+ }
void Release()
{
@@ -64,10 +70,16 @@ public:
_codecInStream.Release();
_decoderInStream.Release();
InputStream.Release();
+
+ _bzDecoder = NULL;
+ _deflateDecoder = NULL;
_lzmaDecoder = NULL;
}
+
+ UInt64 GetInputProcessedSize() const;
HRESULT Init(ISequentialInStream *inStream, bool &useFilter);
+
HRESULT Read(void *data, size_t *processedSize)
{
return ReadStream(_decoderInStream, data, processedSize);;
diff --git a/CPP/7zip/Archive/Nsis/NsisHandler.cpp b/CPP/7zip/Archive/Nsis/NsisHandler.cpp
index 971c8464..095105fe 100644
--- a/CPP/7zip/Archive/Nsis/NsisHandler.cpp
+++ b/CPP/7zip/Archive/Nsis/NsisHandler.cpp
@@ -23,8 +23,8 @@ using namespace NWindows;
namespace NArchive {
namespace NNsis {
-static const char *kBcjMethod = "BCJ";
-static const char *kUnknownMethod = "Unknown";
+#define kBcjMethod "BCJ"
+#define kUnknownMethod "Unknown"
static const char * const kMethods[] =
{
@@ -64,7 +64,7 @@ static AString UInt32ToString(UInt32 val)
{
char s[16];
ConvertUInt32ToString(val, s);
- return s;
+ return (AString)s;
}
static AString GetStringForSizeValue(UInt32 val)
@@ -123,7 +123,7 @@ STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
// case kpidCodePage: if (_archive.IsUnicode) prop = "UTF-16"; break;
case kpidSubType:
{
- AString s = _archive.GetFormatDescription();
+ AString s (_archive.GetFormatDescription());
if (!_archive.IsInstaller)
{
s.Add_Space_if_NotEmpty();
@@ -308,7 +308,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidOffset: prop = item.Pos; break;
case kpidPath:
{
- UString s = NItemName::WinNameToOSName(_archive.GetReducedName(index));
+ UString s = NItemName::WinPathToOsPath(_archive.GetReducedName(index));
if (!s.IsEmpty())
prop = (const wchar_t *)s;
break;
@@ -481,7 +481,7 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
Int32 askMode = testMode ?
NExtract::NAskMode::kTest :
NExtract::NAskMode::kExtract;
- UInt32 index = allFilesMode ? i : indices[i];
+ const UInt32 index = allFilesMode ? i : indices[i];
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
@@ -647,6 +647,12 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
{
UInt32 curPacked2 = 0;
UInt32 curUnpacked2 = 0;
+
+ if (!_archive.IsSolid)
+ {
+ RINOK(_archive.SeekTo(_archive.GetPosOfNonSolidItem(index) + 4 + curPacked ));
+ }
+
HRESULT res = _archive.Decoder.Decode(
writeToTemp ? &tempBuf2 : NULL,
false, 0,
diff --git a/CPP/7zip/Archive/Nsis/NsisIn.cpp b/CPP/7zip/Archive/Nsis/NsisIn.cpp
index a3bfcaec..f739b0ff 100644
--- a/CPP/7zip/Archive/Nsis/NsisIn.cpp
+++ b/CPP/7zip/Archive/Nsis/NsisIn.cpp
@@ -398,11 +398,9 @@ static const char * const kShellStrings[] =
};
-static void UIntToString(AString &s, UInt32 v)
+static inline void UIntToString(AString &s, UInt32 v)
{
- char sz[16];
- ConvertUInt32ToString(v, sz);
- s += sz;
+ s.Add_UInt32(v);
}
#ifdef NSIS_SCRIPT
@@ -461,7 +459,7 @@ void CInArchive::AddLicense(UInt32 param, Int32 langID)
}
}
}
- AString fileName = "[LICENSE]";
+ AString fileName ("[LICENSE]");
if (langID >= 0)
{
fileName += "\\license-";
@@ -940,7 +938,7 @@ void CInArchive::GetNsisString_Unicode_Raw(const Byte *p)
break;
if (c < 0x80)
{
- Raw_UString += (wchar_t)c;
+ Raw_UString += (char)c;
continue;
}
@@ -963,7 +961,7 @@ void CInArchive::GetNsisString_Unicode_Raw(const Byte *p)
else // if (c == PARK_CODE_LANG)
Add_LangStr(Raw_AString, n);
}
- Raw_UString.AddAscii(Raw_AString);
+ Raw_UString += Raw_AString.Ptr(); // check it !
continue;
}
c = n;
@@ -1009,7 +1007,7 @@ void CInArchive::GetNsisString_Unicode_Raw(const Byte *p)
else // if (c == NS_3_CODE_LANG)
Add_LangStr(Raw_AString, n);
}
- Raw_UString.AddAscii(Raw_AString);
+ Raw_UString += Raw_AString.Ptr();
}
}
@@ -1145,7 +1143,7 @@ void CInArchive::ReadString2_Raw(UInt32 pos)
GetNsisString_Raw(_data + _stringsPos + pos);
return;
}
- Raw_UString.SetFromAscii(Raw_AString);
+ Raw_UString = Raw_AString.Ptr();
}
bool CInArchive::IsGoodString(UInt32 param) const
@@ -2309,7 +2307,7 @@ static void AddString(AString &dest, const char *src)
AString CInArchive::GetFormatDescription() const
{
- AString s = "NSIS-";
+ AString s ("NSIS-");
char c;
if (IsPark())
{
@@ -3185,8 +3183,8 @@ HRESULT CInArchive::ReadEntries(const CBlockHeader &bh)
UString spec_outdir_U;
AString spec_outdir_A;
- UPrefixes.Add(L"$INSTDIR");
- APrefixes.Add("$INSTDIR");
+ UPrefixes.Add(UString("$INSTDIR"));
+ APrefixes.Add(AString("$INSTDIR"));
p = _data + bh.Offset;
@@ -4021,7 +4019,7 @@ HRESULT CInArchive::ReadEntries(const CBlockHeader &bh)
case EW_INTOP:
{
AddParam_Var(params[0]);
- const char *kOps = "+-*/|&^!|&%<>"; // NSIS 2.01+
+ const char * const kOps = "+-*/|&^!|&%<>"; // NSIS 2.01+
// "+-*/|&^!|&%"; // NSIS 2.0b4+
// "+-*/|&^~!|&%"; // NSIS old
UInt32 opIndex = params[3];
@@ -4857,11 +4855,11 @@ static int CompareItems(void *const *p1, void *const *p2, void *param)
{
if (i1.Prefix < 0) return -1;
if (i2.Prefix < 0) return 1;
- RINOZ(wcscmp(
- inArchive->UPrefixes[i1.Prefix],
+ RINOZ(
+ inArchive->UPrefixes[i1.Prefix].Compare(
inArchive->UPrefixes[i2.Prefix]));
}
- RINOZ(wcscmp(i1.NameU, i2.NameU));
+ RINOZ(i1.NameU.Compare(i2.NameU));
}
else
{
@@ -4934,7 +4932,7 @@ HRESULT CInArchive::SortItems()
for (i = 0; i < Items.Size(); i++)
{
CItem &item = Items[i];
- RINOK(_stream->Seek(GetPosOfNonSolidItem(i), STREAM_SEEK_SET, NULL));
+ RINOK(SeekToNonSolidItem(i));
const UInt32 kSigSize = 4 + 1 + 1 + 4; // size,[flag],prop,dict
BYTE sig[kSigSize];
size_t processedSize = kSigSize;
@@ -4997,6 +4995,9 @@ HRESULT CInArchive::Parse()
// ???? offset == FirstHeader.HeaderSize
const Byte *p = _data;
+ if (_size < 4 + 8 * 8)
+ return S_FALSE;
+
CBlockHeader bhEntries, bhStrings, bhLangTables;
bhEntries.Parse(p + 4 + 8 * 2);
bhStrings.Parse(p + 4 + 8 * 3);
@@ -5014,12 +5015,14 @@ HRESULT CInArchive::Parse()
#endif
_stringsPos = bhStrings.Offset;
- if (_stringsPos > _size)
+ if (_stringsPos > _size
+ || bhLangTables.Offset > _size
+ || bhEntries.Offset > _size)
return S_FALSE;
{
if (bhLangTables.Offset < bhStrings.Offset)
return S_FALSE;
- UInt32 stringTableSize = bhLangTables.Offset - bhStrings.Offset;
+ const UInt32 stringTableSize = bhLangTables.Offset - bhStrings.Offset;
if (stringTableSize < 2)
return S_FALSE;
const Byte *strData = _data + _stringsPos;
@@ -5035,13 +5038,10 @@ HRESULT CInArchive::Parse()
if (strData[stringTableSize - 2] != 0)
return S_FALSE;
}
-
}
if (bhEntries.Num > (1 << 25))
return S_FALSE;
- if (bhEntries.Offset > _size)
- return S_FALSE;
if (bhEntries.Num * kCmdSize > _size - bhEntries.Offset)
return S_FALSE;
@@ -5595,16 +5595,19 @@ HRESULT CInArchive::Open2(const Byte *sig, size_t size)
if (IsSolid)
{
- RINOK(_stream->Seek(DataStreamOffset, STREAM_SEEK_SET, NULL));
+ RINOK(SeekTo_DataStreamOffset());
}
else
{
_headerIsCompressed = ((compressedHeaderSize & kMask_IsCompressed) != 0);
compressedHeaderSize &= ~kMask_IsCompressed;
_nonSolidStartOffset = compressedHeaderSize;
- RINOK(_stream->Seek(DataStreamOffset + 4, STREAM_SEEK_SET, NULL));
+ RINOK(SeekTo(DataStreamOffset + 4));
}
+ if (FirstHeader.HeaderSize == 0)
+ return S_FALSE;
+
_data.Alloc(FirstHeader.HeaderSize);
_size = (size_t)FirstHeader.HeaderSize;
diff --git a/CPP/7zip/Archive/Nsis/NsisIn.h b/CPP/7zip/Archive/Nsis/NsisIn.h
index d8e6808b..028e4a5d 100644
--- a/CPP/7zip/Archive/Nsis/NsisIn.h
+++ b/CPP/7zip/Archive/Nsis/NsisIn.h
@@ -350,14 +350,19 @@ public:
return Decoder.Init(_stream, useFilter);
}
+ HRESULT SeekTo(UInt64 pos)
+ {
+ return _stream->Seek(pos, STREAM_SEEK_SET, NULL);
+ }
+
HRESULT SeekTo_DataStreamOffset()
{
- return _stream->Seek(DataStreamOffset, STREAM_SEEK_SET, NULL);
+ return SeekTo(DataStreamOffset);
}
HRESULT SeekToNonSolidItem(unsigned index)
{
- return _stream->Seek(GetPosOfNonSolidItem(index), STREAM_SEEK_SET, NULL);
+ return SeekTo(GetPosOfNonSolidItem(index));
}
void Clear();
@@ -403,23 +408,23 @@ public:
s = MultiByteToUnicodeString(APrefixes[item.Prefix]);
if (s.Len() > 0)
if (s.Back() != L'\\')
- s += L'\\';
+ s += '\\';
}
if (IsUnicode)
{
s += item.NameU;
if (item.NameU.IsEmpty())
- s += L"file";
+ s += "file";
}
else
{
s += MultiByteToUnicodeString(item.NameA);
if (item.NameA.IsEmpty())
- s += L"file";
+ s += "file";
}
- const char *kRemoveStr = "$INSTDIR\\";
+ const char * const kRemoveStr = "$INSTDIR\\";
if (s.IsPrefixedBy_Ascii_NoCase(kRemoveStr))
{
s.Delete(0, MyStringLen(kRemoveStr));
@@ -427,7 +432,7 @@ public:
s.DeleteFrontal(1);
}
if (item.IsUninstaller && ExeStub.Size() == 0)
- s += L".nsis";
+ s += ".nsis";
return s;
}