diff --git a/Installer/Installer.vcxproj b/Installer/Installer.vcxproj index 948f6abb..a69a3212 100644 --- a/Installer/Installer.vcxproj +++ b/Installer/Installer.vcxproj @@ -43,6 +43,9 @@ + + + @@ -61,6 +64,8 @@ + + diff --git a/Installer/Installer.vcxproj.filters b/Installer/Installer.vcxproj.filters index 51fc8f4b..26409b41 100644 --- a/Installer/Installer.vcxproj.filters +++ b/Installer/Installer.vcxproj.filters @@ -30,6 +30,18 @@ Source Files + + lzma + + + lzma + + + lzma + + + lzma + lzma @@ -63,9 +75,6 @@ lzma - - lzma - Source Files @@ -86,6 +95,12 @@ lzma + + lzma + + + lzma + lzma diff --git a/Installer/lzma/7zDec.c b/Installer/lzma/7zDec.c index e70391e4..73389d03 100644 --- a/Installer/lzma/7zDec.c +++ b/Installer/lzma/7zDec.c @@ -7,10 +7,8 @@ #include "7z.h" -#ifdef _7ZIP_BCJ2_SUPPPORT #include "Bcj2.h" #include "Bra.h" -#endif #include "CpuArch.h" #include "LzmaDec.h" #ifdef _7ZIP_LZMA2_SUPPPORT @@ -422,7 +420,6 @@ static SRes SzFolder_Decode2(const CSzFolder *folder, const UInt64 *packSizes, #endif } } - #ifdef _7ZIP_BCJ2_SUPPPORT else if (coder->MethodID == k_BCJ2) { UInt64 offset = GetSum(packSizes, 1); @@ -448,14 +445,12 @@ static SRes SzFolder_Decode2(const CSzFolder *folder, const UInt64 *packSizes, outBuffer, outSize); RINOK(res) } - #endif else { if (ci != 1) return SZ_ERROR_UNSUPPORTED; switch(coder->MethodID) { - #ifdef _7ZIP_BCJ2_SUPPPORT case k_BCJ: { UInt32 state; @@ -464,7 +459,6 @@ static SRes SzFolder_Decode2(const CSzFolder *folder, const UInt64 *packSizes, break; } CASE_BRA_CONV(ARM) - #endif default: return SZ_ERROR_UNSUPPORTED; } diff --git a/Installer/lzma/7zMemInStream.c b/Installer/lzma/7zMemInStream.c index 74758c31..ba32e601 100644 --- a/Installer/lzma/7zMemInStream.c +++ b/Installer/lzma/7zMemInStream.c @@ -1,84 +1,84 @@ -/* 7zMemInStream.c -- Memory input stream -** 2012 - Birunthan Mohanathas -** -** This file is public domain. -*/ - -#include "7zMemInStream.h" - -static SRes MemInStream_Look(void *pp, const void **buf, size_t *size) -{ - CMemInStream *p = (CMemInStream *)pp; - size_t remaining = p->end - p->pos; - if (remaining == 0 && *size > 0) - { - // Restart stream. - p->pos = 0; - remaining = *size; - } - - if (remaining < *size) - { - *size = remaining; - } - - *buf = p->pos; - return SZ_OK; -} - -static SRes MemInStream_Skip(void *pp, size_t offset) -{ - CMemInStream *p = (CMemInStream *)pp; - p->pos += offset; - return SZ_OK; -} - -static SRes MemInStream_Read(void *pp, void *buf, size_t *size) -{ - CMemInStream *p = (CMemInStream *)pp; - size_t remaining = p->end - p->pos; - if (remaining == 0) - { - // End of stream. - *size = 0; - } - else - { - if (remaining > *size) - { - remaining = *size; - } - - memcpy(buf, p->pos, remaining); - p->pos += remaining; - *size = remaining; - } - - return SZ_OK; -} - -static SRes MemInStream_Seek(void *pp, Int64 *pos, ESzSeek origin) -{ - CMemInStream *p = (CMemInStream *)pp; - switch (origin) - { - case SZ_SEEK_SET: p->pos = p->begin + *pos; break; - case SZ_SEEK_CUR: p->pos += *pos; break; - case SZ_SEEK_END: p->pos = p->end - *pos; break; - default: return 1; - } - - *pos = p->pos - p->begin; - return SZ_OK; -} - -void MemInStream_Init(CMemInStream *p, const void *begin, size_t length) -{ - p->begin = p->pos = (Byte *)begin; - p->end = p->begin + length; - - p->s.Look = MemInStream_Look; - p->s.Skip = MemInStream_Skip; - p->s.Read = MemInStream_Read; - p->s.Seek = MemInStream_Seek; -} +/* 7zMemInStream.c -- Memory input stream +** 2012 - Birunthan Mohanathas +** +** This file is public domain. +*/ + +#include "7zMemInStream.h" + +static SRes MemInStream_Look(void *pp, const void **buf, size_t *size) +{ + CMemInStream *p = (CMemInStream *)pp; + size_t remaining = p->end - p->pos; + if (remaining == 0 && *size > 0) + { + // Restart stream. + p->pos = 0; + remaining = *size; + } + + if (remaining < *size) + { + *size = remaining; + } + + *buf = p->pos; + return SZ_OK; +} + +static SRes MemInStream_Skip(void *pp, size_t offset) +{ + CMemInStream *p = (CMemInStream *)pp; + p->pos += offset; + return SZ_OK; +} + +static SRes MemInStream_Read(void *pp, void *buf, size_t *size) +{ + CMemInStream *p = (CMemInStream *)pp; + size_t remaining = p->end - p->pos; + if (remaining == 0) + { + // End of stream. + *size = 0; + } + else + { + if (remaining > *size) + { + remaining = *size; + } + + memcpy(buf, p->pos, remaining); + p->pos += remaining; + *size = remaining; + } + + return SZ_OK; +} + +static SRes MemInStream_Seek(void *pp, Int64 *pos, ESzSeek origin) +{ + CMemInStream *p = (CMemInStream *)pp; + switch (origin) + { + case SZ_SEEK_SET: p->pos = p->begin + *pos; break; + case SZ_SEEK_CUR: p->pos += *pos; break; + case SZ_SEEK_END: p->pos = p->end - *pos; break; + default: return 1; + } + + *pos = p->pos - p->begin; + return SZ_OK; +} + +void MemInStream_Init(CMemInStream *p, const void *begin, size_t length) +{ + p->begin = p->pos = (Byte *)begin; + p->end = p->begin + length; + + p->s.Look = MemInStream_Look; + p->s.Skip = MemInStream_Skip; + p->s.Read = MemInStream_Read; + p->s.Seek = MemInStream_Seek; +} diff --git a/Installer/lzma/7zMemInStream.h b/Installer/lzma/7zMemInStream.h index f11ad0e6..182b4cd4 100644 --- a/Installer/lzma/7zMemInStream.h +++ b/Installer/lzma/7zMemInStream.h @@ -1,26 +1,26 @@ -/* 7zMemInStream.h -- Memory input stream -** 2012 - Birunthan Mohanathas -** -** This file is public domain. -*/ - -#ifndef __7Z_MEMINSTREAM_H -#define __7Z_MEMINSTREAM_H - -#include "Types.h" - -EXTERN_C_BEGIN - -typedef struct -{ - ILookInStream s; - const Byte *begin; - const Byte *pos; - const Byte *end; -} CMemInStream; - -void MemInStream_Init(CMemInStream *p, const void *begin, size_t length); - -EXTERN_C_END - -#endif +/* 7zMemInStream.h -- Memory input stream +** 2012 - Birunthan Mohanathas +** +** This file is public domain. +*/ + +#ifndef __7Z_MEMINSTREAM_H +#define __7Z_MEMINSTREAM_H + +#include "Types.h" + +EXTERN_C_BEGIN + +typedef struct +{ + ILookInStream s; + const Byte *begin; + const Byte *pos; + const Byte *end; +} CMemInStream; + +void MemInStream_Init(CMemInStream *p, const void *begin, size_t length); + +EXTERN_C_END + +#endif diff --git a/Installer/lzma/Bcj2.c b/Installer/lzma/Bcj2.c new file mode 100644 index 00000000..474bdd45 --- /dev/null +++ b/Installer/lzma/Bcj2.c @@ -0,0 +1,132 @@ +/* Bcj2.c -- Converter for x86 code (BCJ2) +2008-10-04 : Igor Pavlov : Public domain */ + +#include "Bcj2.h" + +#ifdef _LZMA_PROB32 +#define CProb UInt32 +#else +#define CProb UInt16 +#endif + +#define IsJcc(b0, b1) ((b0) == 0x0F && ((b1) & 0xF0) == 0x80) +#define IsJ(b0, b1) ((b1 & 0xFE) == 0xE8 || IsJcc(b0, b1)) + +#define kNumTopBits 24 +#define kTopValue ((UInt32)1 << kNumTopBits) + +#define kNumBitModelTotalBits 11 +#define kBitModelTotal (1 << kNumBitModelTotalBits) +#define kNumMoveBits 5 + +#define RC_READ_BYTE (*buffer++) +#define RC_TEST { if (buffer == bufferLim) return SZ_ERROR_DATA; } +#define RC_INIT2 code = 0; range = 0xFFFFFFFF; \ + { int i; for (i = 0; i < 5; i++) { RC_TEST; code = (code << 8) | RC_READ_BYTE; }} + +#define NORMALIZE if (range < kTopValue) { RC_TEST; range <<= 8; code = (code << 8) | RC_READ_BYTE; } + +#define IF_BIT_0(p) ttt = *(p); bound = (range >> kNumBitModelTotalBits) * ttt; if (code < bound) +#define UPDATE_0(p) range = bound; *(p) = (CProb)(ttt + ((kBitModelTotal - ttt) >> kNumMoveBits)); NORMALIZE; +#define UPDATE_1(p) range -= bound; code -= bound; *(p) = (CProb)(ttt - (ttt >> kNumMoveBits)); NORMALIZE; + +int Bcj2_Decode( + const Byte *buf0, SizeT size0, + const Byte *buf1, SizeT size1, + const Byte *buf2, SizeT size2, + const Byte *buf3, SizeT size3, + Byte *outBuf, SizeT outSize) +{ + CProb p[256 + 2]; + SizeT inPos = 0, outPos = 0; + + const Byte *buffer, *bufferLim; + UInt32 range, code; + Byte prevByte = 0; + + unsigned int i; + for (i = 0; i < sizeof(p) / sizeof(p[0]); i++) + p[i] = kBitModelTotal >> 1; + + buffer = buf3; + bufferLim = buffer + size3; + RC_INIT2 + + if (outSize == 0) + return SZ_OK; + + for (;;) + { + Byte b; + CProb *prob; + UInt32 bound; + UInt32 ttt; + + SizeT limit = size0 - inPos; + if (outSize - outPos < limit) + limit = outSize - outPos; + while (limit != 0) + { + Byte b = buf0[inPos]; + outBuf[outPos++] = b; + if (IsJ(prevByte, b)) + break; + inPos++; + prevByte = b; + limit--; + } + + if (limit == 0 || outPos == outSize) + break; + + b = buf0[inPos++]; + + if (b == 0xE8) + prob = p + prevByte; + else if (b == 0xE9) + prob = p + 256; + else + prob = p + 257; + + IF_BIT_0(prob) + { + UPDATE_0(prob) + prevByte = b; + } + else + { + UInt32 dest; + const Byte *v; + UPDATE_1(prob) + if (b == 0xE8) + { + v = buf1; + if (size1 < 4) + return SZ_ERROR_DATA; + buf1 += 4; + size1 -= 4; + } + else + { + v = buf2; + if (size2 < 4) + return SZ_ERROR_DATA; + buf2 += 4; + size2 -= 4; + } + dest = (((UInt32)v[0] << 24) | ((UInt32)v[1] << 16) | + ((UInt32)v[2] << 8) | ((UInt32)v[3])) - ((UInt32)outPos + 4); + outBuf[outPos++] = (Byte)dest; + if (outPos == outSize) + break; + outBuf[outPos++] = (Byte)(dest >> 8); + if (outPos == outSize) + break; + outBuf[outPos++] = (Byte)(dest >> 16); + if (outPos == outSize) + break; + outBuf[outPos++] = prevByte = (Byte)(dest >> 24); + } + } + return (outPos == outSize) ? SZ_OK : SZ_ERROR_DATA; +} diff --git a/Installer/lzma/Bcj2.h b/Installer/lzma/Bcj2.h new file mode 100644 index 00000000..d9d857bc --- /dev/null +++ b/Installer/lzma/Bcj2.h @@ -0,0 +1,38 @@ +/* Bcj2.h -- Converter for x86 code (BCJ2) +2009-02-07 : Igor Pavlov : Public domain */ + +#ifndef __BCJ2_H +#define __BCJ2_H + +#include "Types.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* +Conditions: + outSize <= FullOutputSize, + where FullOutputSize is full size of output stream of x86_2 filter. + +If buf0 overlaps outBuf, there are two required conditions: + 1) (buf0 >= outBuf) + 2) (buf0 + size0 >= outBuf + FullOutputSize). + +Returns: + SZ_OK + SZ_ERROR_DATA - Data error +*/ + +int Bcj2_Decode( + const Byte *buf0, SizeT size0, + const Byte *buf1, SizeT size1, + const Byte *buf2, SizeT size2, + const Byte *buf3, SizeT size3, + Byte *outBuf, SizeT outSize); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/Installer/lzma/Bra.c b/Installer/lzma/Bra.c new file mode 100644 index 00000000..2a0f147b --- /dev/null +++ b/Installer/lzma/Bra.c @@ -0,0 +1,133 @@ +/* Bra.c -- Converters for RISC code +2010-04-16 : Igor Pavlov : Public domain */ + +#include "Bra.h" + +SizeT ARM_Convert(Byte *data, SizeT size, UInt32 ip, int encoding) +{ + SizeT i; + if (size < 4) + return 0; + size -= 4; + ip += 8; + for (i = 0; i <= size; i += 4) + { + if (data[i + 3] == 0xEB) + { + UInt32 dest; + UInt32 src = ((UInt32)data[i + 2] << 16) | ((UInt32)data[i + 1] << 8) | (data[i + 0]); + src <<= 2; + if (encoding) + dest = ip + (UInt32)i + src; + else + dest = src - (ip + (UInt32)i); + dest >>= 2; + data[i + 2] = (Byte)(dest >> 16); + data[i + 1] = (Byte)(dest >> 8); + data[i + 0] = (Byte)dest; + } + } + return i; +} + +SizeT ARMT_Convert(Byte *data, SizeT size, UInt32 ip, int encoding) +{ + SizeT i; + if (size < 4) + return 0; + size -= 4; + ip += 4; + for (i = 0; i <= size; i += 2) + { + if ((data[i + 1] & 0xF8) == 0xF0 && + (data[i + 3] & 0xF8) == 0xF8) + { + UInt32 dest; + UInt32 src = + (((UInt32)data[i + 1] & 0x7) << 19) | + ((UInt32)data[i + 0] << 11) | + (((UInt32)data[i + 3] & 0x7) << 8) | + (data[i + 2]); + + src <<= 1; + if (encoding) + dest = ip + (UInt32)i + src; + else + dest = src - (ip + (UInt32)i); + dest >>= 1; + + data[i + 1] = (Byte)(0xF0 | ((dest >> 19) & 0x7)); + data[i + 0] = (Byte)(dest >> 11); + data[i + 3] = (Byte)(0xF8 | ((dest >> 8) & 0x7)); + data[i + 2] = (Byte)dest; + i += 2; + } + } + return i; +} + +SizeT PPC_Convert(Byte *data, SizeT size, UInt32 ip, int encoding) +{ + SizeT i; + if (size < 4) + return 0; + size -= 4; + for (i = 0; i <= size; i += 4) + { + if ((data[i] >> 2) == 0x12 && (data[i + 3] & 3) == 1) + { + UInt32 src = ((UInt32)(data[i + 0] & 3) << 24) | + ((UInt32)data[i + 1] << 16) | + ((UInt32)data[i + 2] << 8) | + ((UInt32)data[i + 3] & (~3)); + + UInt32 dest; + if (encoding) + dest = ip + (UInt32)i + src; + else + dest = src - (ip + (UInt32)i); + data[i + 0] = (Byte)(0x48 | ((dest >> 24) & 0x3)); + data[i + 1] = (Byte)(dest >> 16); + data[i + 2] = (Byte)(dest >> 8); + data[i + 3] &= 0x3; + data[i + 3] |= dest; + } + } + return i; +} + +SizeT SPARC_Convert(Byte *data, SizeT size, UInt32 ip, int encoding) +{ + UInt32 i; + if (size < 4) + return 0; + size -= 4; + for (i = 0; i <= size; i += 4) + { + if ((data[i] == 0x40 && (data[i + 1] & 0xC0) == 0x00) || + (data[i] == 0x7F && (data[i + 1] & 0xC0) == 0xC0)) + { + UInt32 src = + ((UInt32)data[i + 0] << 24) | + ((UInt32)data[i + 1] << 16) | + ((UInt32)data[i + 2] << 8) | + ((UInt32)data[i + 3]); + UInt32 dest; + + src <<= 2; + if (encoding) + dest = ip + i + src; + else + dest = src - (ip + i); + dest >>= 2; + + dest = (((0 - ((dest >> 22) & 1)) << 22) & 0x3FFFFFFF) | (dest & 0x3FFFFF) | 0x40000000; + + data[i + 0] = (Byte)(dest >> 24); + data[i + 1] = (Byte)(dest >> 16); + data[i + 2] = (Byte)(dest >> 8); + data[i + 3] = (Byte)dest; + } + } + return i; +} diff --git a/Installer/lzma/Bra.h b/Installer/lzma/Bra.h new file mode 100644 index 00000000..9c91e332 --- /dev/null +++ b/Installer/lzma/Bra.h @@ -0,0 +1,68 @@ +/* Bra.h -- Branch converters for executables +2009-02-07 : Igor Pavlov : Public domain */ + +#ifndef __BRA_H +#define __BRA_H + +#include "Types.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* +These functions convert relative addresses to absolute addresses +in CALL instructions to increase the compression ratio. + + In: + data - data buffer + size - size of data + ip - current virtual Instruction Pinter (IP) value + state - state variable for x86 converter + encoding - 0 (for decoding), 1 (for encoding) + + Out: + state - state variable for x86 converter + + Returns: + The number of processed bytes. If you call these functions with multiple calls, + you must start next call with first byte after block of processed bytes. + + Type Endian Alignment LookAhead + + x86 little 1 4 + ARMT little 2 2 + ARM little 4 0 + PPC big 4 0 + SPARC big 4 0 + IA64 little 16 0 + + size must be >= Alignment + LookAhead, if it's not last block. + If (size < Alignment + LookAhead), converter returns 0. + + Example: + + UInt32 ip = 0; + for () + { + ; size must be >= Alignment + LookAhead, if it's not last block + SizeT processed = Convert(data, size, ip, 1); + data += processed; + size -= processed; + ip += processed; + } +*/ + +#define x86_Convert_Init(state) { state = 0; } +SizeT x86_Convert(Byte *data, SizeT size, UInt32 ip, UInt32 *state, int encoding); +SizeT ARM_Convert(Byte *data, SizeT size, UInt32 ip, int encoding); +SizeT ARMT_Convert(Byte *data, SizeT size, UInt32 ip, int encoding); +SizeT PPC_Convert(Byte *data, SizeT size, UInt32 ip, int encoding); +SizeT SPARC_Convert(Byte *data, SizeT size, UInt32 ip, int encoding); +SizeT IA64_Convert(Byte *data, SizeT size, UInt32 ip, int encoding); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/Installer/lzma/Bra86.c b/Installer/lzma/Bra86.c new file mode 100644 index 00000000..93566cb2 --- /dev/null +++ b/Installer/lzma/Bra86.c @@ -0,0 +1,85 @@ +/* Bra86.c -- Converter for x86 code (BCJ) +2008-10-04 : Igor Pavlov : Public domain */ + +#include "Bra.h" + +#define Test86MSByte(b) ((b) == 0 || (b) == 0xFF) + +const Byte kMaskToAllowedStatus[8] = {1, 1, 1, 0, 1, 0, 0, 0}; +const Byte kMaskToBitNumber[8] = {0, 1, 2, 2, 3, 3, 3, 3}; + +SizeT x86_Convert(Byte *data, SizeT size, UInt32 ip, UInt32 *state, int encoding) +{ + SizeT bufferPos = 0, prevPosT; + UInt32 prevMask = *state & 0x7; + if (size < 5) + return 0; + ip += 5; + prevPosT = (SizeT)0 - 1; + + for (;;) + { + Byte *p = data + bufferPos; + Byte *limit = data + size - 4; + for (; p < limit; p++) + if ((*p & 0xFE) == 0xE8) + break; + bufferPos = (SizeT)(p - data); + if (p >= limit) + break; + prevPosT = bufferPos - prevPosT; + if (prevPosT > 3) + prevMask = 0; + else + { + prevMask = (prevMask << ((int)prevPosT - 1)) & 0x7; + if (prevMask != 0) + { + Byte b = p[4 - kMaskToBitNumber[prevMask]]; + if (!kMaskToAllowedStatus[prevMask] || Test86MSByte(b)) + { + prevPosT = bufferPos; + prevMask = ((prevMask << 1) & 0x7) | 1; + bufferPos++; + continue; + } + } + } + prevPosT = bufferPos; + + if (Test86MSByte(p[4])) + { + UInt32 src = ((UInt32)p[4] << 24) | ((UInt32)p[3] << 16) | ((UInt32)p[2] << 8) | ((UInt32)p[1]); + UInt32 dest; + for (;;) + { + Byte b; + int index; + if (encoding) + dest = (ip + (UInt32)bufferPos) + src; + else + dest = src - (ip + (UInt32)bufferPos); + if (prevMask == 0) + break; + index = kMaskToBitNumber[prevMask] * 8; + b = (Byte)(dest >> (24 - index)); + if (!Test86MSByte(b)) + break; + src = dest ^ ((1 << (32 - index)) - 1); + } + p[4] = (Byte)(~(((dest >> 24) & 1) - 1)); + p[3] = (Byte)(dest >> 16); + p[2] = (Byte)(dest >> 8); + p[1] = (Byte)dest; + bufferPos += 5; + } + else + { + prevMask = ((prevMask << 1) & 0x7) | 1; + bufferPos++; + } + } + prevPosT = bufferPos - prevPosT; + *state = ((prevPosT > 3) ? 0 : ((prevMask << ((int)prevPosT - 1)) & 0x7)); + return bufferPos; +}