Compare commits

..

3 Commits
15.10 ... 15.13

Author SHA1 Message Date
Igor Pavlov
9608215ad8 15.13 2016-05-28 00:16:58 +01:00
Igor Pavlov
5de23c1deb 15.12 2016-05-28 00:16:58 +01:00
Igor Pavlov
e24f7fba53 15.11 2016-05-28 00:16:57 +01:00
136 changed files with 2896 additions and 1487 deletions

82
C/7z.h
View File

@@ -1,5 +1,5 @@
/* 7z.h -- 7z interface
2014-02-08 : Igor Pavlov : Public domain */
2015-11-18 : Igor Pavlov : Public domain */
#ifndef __7Z_H
#define __7Z_H
@@ -48,21 +48,10 @@ typedef struct
UInt32 PackStreams[SZ_NUM_PACK_STREAMS_IN_FOLDER_MAX];
CSzBond Bonds[SZ_NUM_BONDS_IN_FOLDER_MAX];
CSzCoderInfo Coders[SZ_NUM_CODERS_IN_FOLDER_MAX];
UInt64 CodersUnpackSizes[SZ_NUM_CODERS_IN_FOLDER_MAX];
} CSzFolder;
/*
typedef struct
{
size_t CodersDataOffset;
size_t UnpackSizeDataOffset;
// UInt32 StartCoderUnpackSizesIndex;
UInt32 StartPackStreamIndex;
// UInt32 IndexOfMainOutStream;
} CSzFolder2;
*/
SRes SzGetNextFolderItem(CSzFolder *f, CSzData *sd, CSzData *sdSizes);
SRes SzGetNextFolderItem(CSzFolder *f, CSzData *sd);
typedef struct
{
@@ -92,47 +81,25 @@ typedef struct
UInt32 NumPackStreams;
UInt32 NumFolders;
UInt64 *PackPositions; // NumPackStreams + 1
CSzBitUi32s FolderCRCs;
UInt64 *PackPositions; // NumPackStreams + 1
CSzBitUi32s FolderCRCs; // NumFolders
size_t *FoCodersOffsets;
size_t *FoSizesOffsets;
// UInt32 StartCoderUnpackSizesIndex;
UInt32 *FoStartPackStreamIndex;
size_t *FoCodersOffsets; // NumFolders + 1
UInt32 *FoStartPackStreamIndex; // NumFolders + 1
UInt32 *FoToCoderUnpackSizes; // NumFolders + 1
Byte *FoToMainUnpackSizeIndex; // NumFolders
UInt64 *CoderUnpackSizes; // for all coders in all folders
// CSzFolder2 *Folders; // +1 item for sum values
Byte *CodersData;
Byte *UnpackSizesData;
size_t UnpackSizesDataSize;
// UInt64 *CoderUnpackSizes;
} CSzAr;
UInt64 SzAr_GetFolderUnpackSize(const CSzAr *p, UInt32 folderIndex);
SRes SzAr_DecodeFolder(const CSzAr *p, UInt32 folderIndex,
ILookInStream *stream, UInt64 startPos,
Byte *outBuffer, size_t outSize,
ISzAlloc *allocMain);
/*
SzExtract extracts file from archive
*outBuffer must be 0 before first call for each new archive.
Extracting cache:
If you need to decompress more than one file, you can send
these values from previous call:
*blockIndex,
*outBuffer,
*outBufferSize
You can consider "*outBuffer" as cache of solid block. If your archive is solid,
it will increase decompression speed.
If you use external function, you can declare these 3 cache variables
(blockIndex, outBuffer, outBufferSize) as static in that external function.
Free *outBuffer and set *outBuffer to 0, if you want to flush cache.
*/
typedef struct
{
CSzAr db;
@@ -142,7 +109,7 @@ typedef struct
UInt32 NumFiles;
UInt64 *UnpackPositions;
UInt64 *UnpackPositions; // NumFiles + 1
// Byte *IsEmptyFiles;
Byte *IsDirs;
CSzBitUi32s CRCs;
@@ -152,9 +119,8 @@ typedef struct
CSzBitUi64s MTime;
CSzBitUi64s CTime;
// UInt32 *FolderStartPackStreamIndex;
UInt32 *FolderStartFileIndex; // + 1
UInt32 *FileIndexToFolderIndexMap;
UInt32 *FolderToFile; // NumFolders + 1
UInt32 *FileToFolder; // NumFiles
size_t *FileNameOffsets; /* in 2-byte steps */
Byte *FileNames; /* UTF-16-LE */
@@ -182,6 +148,28 @@ size_t SzArEx_GetFullNameLen(const CSzArEx *p, size_t fileIndex);
UInt16 *SzArEx_GetFullNameUtf16_Back(const CSzArEx *p, size_t fileIndex, UInt16 *dest);
*/
/*
SzArEx_Extract extracts file from archive
*outBuffer must be 0 before first call for each new archive.
Extracting cache:
If you need to decompress more than one file, you can send
these values from previous call:
*blockIndex,
*outBuffer,
*outBufferSize
You can consider "*outBuffer" as cache of solid block. If your archive is solid,
it will increase decompression speed.
If you use external function, you can declare these 3 cache variables
(blockIndex, outBuffer, outBufferSize) as static in that external function.
Free *outBuffer and set *outBuffer to 0, if you want to flush cache.
*/
SRes SzArEx_Extract(
const CSzArEx *db,
ILookInStream *inStream,

View File

@@ -1,5 +1,5 @@
/* 7zAlloc.c -- Allocation functions
2015-02-21 : Igor Pavlov : Public domain */
2015-11-09 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -26,7 +26,7 @@ void *SzAlloc(void *p, size_t size)
if (size == 0)
return 0;
#ifdef _SZ_ALLOC_DEBUG
fprintf(stderr, "\nAlloc %10d bytes; count = %10d", size, g_allocCount);
fprintf(stderr, "\nAlloc %10u bytes; count = %10d", (unsigned)size, g_allocCount);
g_allocCount++;
#endif
return malloc(size);
@@ -51,7 +51,7 @@ void *SzAllocTemp(void *p, size_t size)
if (size == 0)
return 0;
#ifdef _SZ_ALLOC_DEBUG
fprintf(stderr, "\nAlloc_temp %10d bytes; count = %10d", size, g_allocCountTemp);
fprintf(stderr, "\nAlloc_temp %10u bytes; count = %10d", (unsigned)size, g_allocCountTemp);
g_allocCountTemp++;
#ifdef _WIN32
return HeapAlloc(GetProcessHeap(), 0, size);

View File

File diff suppressed because it is too large Load Diff

View File

@@ -1,5 +1,5 @@
/* 7zDec.c -- Decoding from 7z folder
2015-08-01 : Igor Pavlov : Public domain */
2015-11-18 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -8,6 +8,7 @@
/* #define _7ZIP_PPMD_SUPPPORT */
#include "7z.h"
#include "7zCrc.h"
#include "Bcj2.h"
#include "Bra.h"
@@ -160,14 +161,23 @@ static SRes SzDecodeLzma(const Byte *props, unsigned propsSize, UInt64 inSize, I
inSize -= inProcessed;
if (res != SZ_OK)
break;
if (state.dicPos == state.dicBufSize || (inProcessed == 0 && dicPos == state.dicPos))
if (status == LZMA_STATUS_FINISHED_WITH_MARK)
{
if (state.dicBufSize != outSize || lookahead != 0 ||
(status != LZMA_STATUS_FINISHED_WITH_MARK &&
status != LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK))
if (outSize != state.dicPos || inSize != 0)
res = SZ_ERROR_DATA;
break;
}
if (outSize == state.dicPos && inSize == 0 && status == LZMA_STATUS_MAYBE_FINISHED_WITHOUT_MARK)
break;
if (inProcessed == 0 && dicPos == state.dicPos)
{
res = SZ_ERROR_DATA;
break;
}
res = inStream->Skip((void *)inStream, inProcessed);
if (res != SZ_OK)
break;
@@ -213,13 +223,20 @@ static SRes SzDecodeLzma2(const Byte *props, unsigned propsSize, UInt64 inSize,
inSize -= inProcessed;
if (res != SZ_OK)
break;
if (state.decoder.dicPos == state.decoder.dicBufSize || (inProcessed == 0 && dicPos == state.decoder.dicPos))
if (status == LZMA_STATUS_FINISHED_WITH_MARK)
{
if (state.decoder.dicBufSize != outSize || lookahead != 0 ||
(status != LZMA_STATUS_FINISHED_WITH_MARK))
if (outSize != state.decoder.dicPos || inSize != 0)
res = SZ_ERROR_DATA;
break;
}
if (inProcessed == 0 && dicPos == state.decoder.dicPos)
{
res = SZ_ERROR_DATA;
break;
}
res = inStream->Skip((void *)inStream, inProcessed);
if (res != SZ_OK)
break;
@@ -537,33 +554,38 @@ SRes SzAr_DecodeFolder(const CSzAr *p, UInt32 folderIndex,
SRes res;
CSzFolder folder;
CSzData sd;
CSzData sdSizes;
const Byte *data = p->CodersData + p->FoCodersOffsets[folderIndex];
sd.Data = data;
sd.Size = p->FoCodersOffsets[folderIndex + 1] - p->FoCodersOffsets[folderIndex];
sdSizes.Data = p->UnpackSizesData + p->FoSizesOffsets[folderIndex];
sdSizes.Size =
p->FoSizesOffsets[folderIndex + 1] -
p->FoSizesOffsets[folderIndex];
res = SzGetNextFolderItem(&folder, &sd, &sdSizes);
res = SzGetNextFolderItem(&folder, &sd);
if (res != SZ_OK)
return res;
if (sd.Size != 0 || outSize != folder.CodersUnpackSizes[folder.UnpackStream])
if (sd.Size != 0
|| folder.UnpackStream != p->FoToMainUnpackSizeIndex[folderIndex]
|| outSize != SzAr_GetFolderUnpackSize(p, folderIndex))
return SZ_ERROR_FAIL;
{
unsigned i;
Byte *tempBuf[3] = { 0, 0, 0};
res = SzFolder_Decode2(&folder, data, folder.CodersUnpackSizes,
res = SzFolder_Decode2(&folder, data,
&p->CoderUnpackSizes[p->FoToCoderUnpackSizes[folderIndex]],
p->PackPositions + p->FoStartPackStreamIndex[folderIndex],
inStream, startPos,
outBuffer, (SizeT)outSize, allocMain, tempBuf);
for (i = 0; i < 3; i++)
IAlloc_Free(allocMain, tempBuf[i]);
if (res == SZ_OK)
if (SzBitWithVals_Check(&p->FolderCRCs, folderIndex))
if (CrcCalc(outBuffer, outSize) != p->FolderCRCs.Vals[folderIndex])
res = SZ_ERROR_CRC;
return res;
}
}

View File

@@ -1,9 +1,9 @@
#define MY_VER_MAJOR 15
#define MY_VER_MINOR 10
#define MY_VER_MINOR 13
#define MY_VER_BUILD 0
#define MY_VERSION_NUMBERS "15.10"
#define MY_VERSION "15.10 beta"
#define MY_DATE "2015-11-01"
#define MY_VERSION_NUMBERS "15.13"
#define MY_VERSION "15.13"
#define MY_DATE "2015-12-31"
#undef MY_COPYRIGHT
#undef MY_VERSION_COPYRIGHT_DATE
#define MY_AUTHOR_NAME "Igor Pavlov"

View File

@@ -513,4 +513,3 @@ UInt32 BlockSort(UInt32 *Indices, const Byte *data, UInt32 blockSize)
#endif
return Groups[0];
}

View File

@@ -1,5 +1,5 @@
/* CpuArch.h -- CPU specific code
2015-10-31: Igor Pavlov : Public domain */
2015-12-01: Igor Pavlov : Public domain */
#ifndef __CPU_ARCH_H
#define __CPU_ARCH_H
@@ -78,7 +78,9 @@ MY_CPU_LE_UNALIGN means that CPU is LITTLE ENDIAN and CPU supports unaligned mem
|| defined(__MIPSEB) \
|| defined(_MIPSEB) \
|| defined(__m68k__) \
|| defined(__s390__) \
|| defined(__s390x__) \
|| defined(__zarch__) \
|| (defined(__BYTE_ORDER__) && (__BYTE_ORDER__ == __ORDER_BIG_ENDIAN__))
#define MY_CPU_BE
#endif

View File

@@ -1,5 +1,5 @@
/* Lzma2Dec.c -- LZMA2 Decoder
2014-10-29 : Igor Pavlov : Public domain */
2015-11-09 : Igor Pavlov : Public domain */
/* #define SHOW_DEBUG_INFO */
@@ -103,8 +103,8 @@ static ELzma2State Lzma2Dec_UpdateState(CLzma2Dec *p, Byte b)
{
case LZMA2_STATE_CONTROL:
p->control = b;
PRF(printf("\n %4X ", p->decoder.dicPos));
PRF(printf(" %2X", b));
PRF(printf("\n %4X ", (unsigned)p->decoder.dicPos));
PRF(printf(" %2X", (unsigned)b));
if (p->control == 0)
return LZMA2_STATE_FINISHED;
if (LZMA2_IS_UNCOMPRESSED_STATE(p))
@@ -124,7 +124,7 @@ static ELzma2State Lzma2Dec_UpdateState(CLzma2Dec *p, Byte b)
case LZMA2_STATE_UNPACK1:
p->unpackSize |= (UInt32)b;
p->unpackSize++;
PRF(printf(" %8d", p->unpackSize));
PRF(printf(" %8u", (unsigned)p->unpackSize));
return (LZMA2_IS_UNCOMPRESSED_STATE(p)) ? LZMA2_STATE_DATA : LZMA2_STATE_PACK0;
case LZMA2_STATE_PACK0:
@@ -134,7 +134,7 @@ static ELzma2State Lzma2Dec_UpdateState(CLzma2Dec *p, Byte b)
case LZMA2_STATE_PACK1:
p->packSize |= (UInt32)b;
p->packSize++;
PRF(printf(" %8d", p->packSize));
PRF(printf(" %8u", (unsigned)p->packSize));
return LZMA2_IS_THERE_PROP(LZMA2_GET_LZMA_MODE(p)) ? LZMA2_STATE_PROP:
(p->needInitProp ? LZMA2_STATE_ERROR : LZMA2_STATE_DATA);

View File

@@ -1,5 +1,7 @@
/* Lzma86Dec.c -- LZMA + x86 (BCJ) Filter Decoder
2009-08-14 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "Precomp.h"
#include "Lzma86.h"
@@ -7,8 +9,8 @@
#include "Bra.h"
#include "LzmaDec.h"
static void *SzAlloc(void *p, size_t size) { p = p; return MyAlloc(size); }
static void SzFree(void *p, void *address) { p = p; MyFree(address); }
static void *SzAlloc(void *p, size_t size) { UNUSED_VAR(p); return MyAlloc(size); }
static void SzFree(void *p, void *address) { UNUSED_VAR(p); MyFree(address); }
SRes Lzma86_GetUnpackSize(const Byte *src, SizeT srcLen, UInt64 *unpackSize)
{

View File

@@ -1,5 +1,7 @@
/* Lzma86Enc.c -- LZMA + x86 (BCJ) Filter Encoder
2009-08-14 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "Precomp.h"
#include <string.h>
@@ -11,8 +13,8 @@
#define SZE_OUT_OVERFLOW SZE_DATA_ERROR
static void *SzAlloc(void *p, size_t size) { p = p; return MyAlloc(size); }
static void SzFree(void *p, void *address) { p = p; MyFree(address); }
static void *SzAlloc(void *p, size_t size) { UNUSED_VAR(p); return MyAlloc(size); }
static void SzFree(void *p, void *address) { UNUSED_VAR(p); MyFree(address); }
int Lzma86_Encode(Byte *dest, size_t *destLen, const Byte *src, size_t srcLen,
int level, UInt32 dictSize, int filterMode)

View File

@@ -1,5 +1,5 @@
/* LzmaEnc.c -- LZMA Encoder
2015-10-15 Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -854,7 +854,7 @@ static void MovePos(CLzmaEnc *p, UInt32 num)
{
#ifdef SHOW_STAT
g_STAT_OFFSET += num;
printf("\n MovePos %d", num);
printf("\n MovePos %u", num);
#endif
if (num != 0)
@@ -871,12 +871,12 @@ static UInt32 ReadMatchDistances(CLzmaEnc *p, UInt32 *numDistancePairsRes)
numPairs = p->matchFinder.GetMatches(p->matchFinderObj, p->matches);
#ifdef SHOW_STAT
printf("\n i = %d numPairs = %d ", g_STAT_OFFSET, numPairs / 2);
printf("\n i = %u numPairs = %u ", g_STAT_OFFSET, numPairs / 2);
g_STAT_OFFSET++;
{
UInt32 i;
for (i = 0; i < numPairs; i += 2)
printf("%2d %6d | ", p->matches[i], p->matches[i + 1]);
printf("%2u %6u | ", p->matches[i], p->matches[i + 1]);
}
#endif
@@ -1167,12 +1167,12 @@ static UInt32 GetOptimum(CLzmaEnc *p, UInt32 position, UInt32 *backRes)
cur = 0;
#ifdef SHOW_STAT2
if (position >= 0)
/* if (position >= 0) */
{
unsigned i;
printf("\n pos = %4X", position);
for (i = cur; i <= lenEnd; i++)
printf("\nprice[%4X] = %d", position - cur + i, p->opt[i].price);
printf("\nprice[%4X] = %u", position - cur + i, p->opt[i].price);
}
#endif
@@ -1397,13 +1397,13 @@ static UInt32 GetOptimum(CLzmaEnc *p, UInt32 position, UInt32 *backRes)
{
UInt32 lenTest2 = lenTest + 1;
UInt32 limit = lenTest2 + p->numFastBytes;
UInt32 nextRepMatchPrice;
if (limit > numAvailFull)
limit = numAvailFull;
for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++);
lenTest2 -= lenTest + 1;
if (lenTest2 >= 2)
{
UInt32 nextRepMatchPrice;
UInt32 state2 = kRepNextStates[state];
UInt32 posStateNext = (position + lenTest) & p->pbMask;
UInt32 curAndLenCharPrice =
@@ -1487,13 +1487,13 @@ static UInt32 GetOptimum(CLzmaEnc *p, UInt32 position, UInt32 *backRes)
const Byte *data2 = data - curBack - 1;
UInt32 lenTest2 = lenTest + 1;
UInt32 limit = lenTest2 + p->numFastBytes;
UInt32 nextRepMatchPrice;
if (limit > numAvailFull)
limit = numAvailFull;
for (; lenTest2 < limit && data[lenTest2] == data2[lenTest2]; lenTest2++);
lenTest2 -= lenTest + 1;
if (lenTest2 >= 2)
{
UInt32 nextRepMatchPrice;
UInt32 state2 = kMatchNextStates[state];
UInt32 posStateNext = (position + lenTest) & p->pbMask;
UInt32 curAndLenCharPrice = curAndLenPrice +
@@ -1829,7 +1829,7 @@ static SRes LzmaEnc_CodeOneBlock(CLzmaEnc *p, Bool useLimits, UInt32 maxPackSize
len = GetOptimum(p, nowPos32, &pos);
#ifdef SHOW_STAT2
printf("\n pos = %4X, len = %d pos = %d", nowPos32, len, pos);
printf("\n pos = %4X, len = %u pos = %u", nowPos32, len, pos);
#endif
posState = nowPos32 & p->pbMask;

View File

@@ -1,5 +1,5 @@
/* Crypto/Sha256.c -- SHA-256 Hash
2015-03-02 : Igor Pavlov : Public domain
2015-11-14 : Igor Pavlov : Public domain
This code is based on public domain code from Wei Dai's Crypto++ library. */
#include "Precomp.h"
@@ -113,10 +113,26 @@ static void Sha256_WriteByteBlock(CSha256 *p)
{
UInt32 W[16];
unsigned j;
UInt32 *state = p->state;
UInt32 *state;
#ifdef _SHA256_UNROLL2
UInt32 a,b,c,d,e,f,g,h;
#else
UInt32 T[8];
#endif
for (j = 0; j < 16; j += 4)
{
const Byte *ccc = p->buffer + j * 4;
W[j ] = GetBe32(ccc);
W[j + 1] = GetBe32(ccc + 4);
W[j + 2] = GetBe32(ccc + 8);
W[j + 3] = GetBe32(ccc + 12);
}
state = p->state;
#ifdef _SHA256_UNROLL2
a = state[0];
b = state[1];
c = state[2];
@@ -126,17 +142,10 @@ static void Sha256_WriteByteBlock(CSha256 *p)
g = state[6];
h = state[7];
#else
UInt32 T[8];
for (j = 0; j < 8; j++)
T[j] = state[j];
#endif
for (j = 0; j < 16; j += 2)
{
W[j ] = GetBe32(p->buffer + j * 4);
W[j + 1] = GetBe32(p->buffer + j * 4 + 4);
}
for (j = 0; j < 64; j += 16)
{
RX_16
@@ -226,11 +235,13 @@ void Sha256_Final(CSha256 *p, Byte *digest)
Sha256_WriteByteBlock(p);
for (i = 0; i < 8; i++)
for (i = 0; i < 8; i += 2)
{
UInt32 v = p->state[i];
SetBe32(digest, v);
digest += 4;
UInt32 v0 = p->state[i];
UInt32 v1 = p->state[i + 1];
SetBe32(digest , v0);
SetBe32(digest + 4, v1);
digest += 8;
}
Sha256_Init(p);

View File

@@ -73,4 +73,3 @@ Ppmd7Dec.o: ../../Ppmd7Dec.c
clean:
-$(RM) $(PROG) $(OBJS)

View File

@@ -1,5 +1,5 @@
/* 7zipInstall.c - 7-Zip Installer
2015-09-28 : Igor Pavlov : Public domain */
2015-12-09 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -261,7 +261,7 @@ static LONG MyRegistry_CreateKeyAndVal(HKEY parentKey, LPCWSTR keyName, LPCWSTR
if (res == ERROR_SUCCESS)
{
res = MyRegistry_SetString(destKey, valName, val);
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
return res;
}
@@ -284,7 +284,7 @@ static LONG MyRegistry_CreateKeyAndVal_32(HKEY parentKey, LPCWSTR keyName, LPCWS
if (res == ERROR_SUCCESS)
{
res = MyRegistry_SetString(destKey, valName, val);
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
return res;
}
@@ -322,7 +322,7 @@ static Bool FindSignature(CSzFile *stream, UInt64 *resPos)
processed -= k7zStartHeaderSize;
for (pos = 0; pos <= processed; pos++)
{
for (; buf[pos] != '7' && pos <= processed; pos++);
for (; pos <= processed && buf[pos] != '7'; pos++);
if (pos > processed)
break;
if (memcmp(buf + pos, k7zSignature, k7zSignatureSize) == 0)
@@ -571,6 +571,8 @@ static INT_PTR CALLBACK MyDlgProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM
#endif
break;
}
default: return FALSE;
}
break;
@@ -598,8 +600,8 @@ static LONG SetRegKey_Path2(HKEY parentKey)
if (res == ERROR_SUCCESS)
{
res = MyRegistry_SetString(destKey, k_Reg_Path32, path);
res = MyRegistry_SetString(destKey, k_Reg_Path, path);
res = RegCloseKey(destKey);
/* res = */ MyRegistry_SetString(destKey, k_Reg_Path, path);
/* res = */ RegCloseKey(destKey);
}
return res;
}
@@ -718,10 +720,10 @@ static void WriteCLSID()
WCHAR destPath[MAX_PATH + 10];
wcscpy(destPath, path);
wcscat(destPath, L"7-zip32.dll");
res = MyRegistry_SetString(destKey, NULL, destPath);
res = MyRegistry_SetString(destKey, L"ThreadingModel", L"Apartment");
/* res = */ MyRegistry_SetString(destKey, NULL, destPath);
/* res = */ MyRegistry_SetString(destKey, L"ThreadingModel", L"Apartment");
// DeleteRegValue(destKey, L"InprocServer32");
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
#endif
@@ -737,10 +739,10 @@ static void WriteCLSID()
WCHAR destPath[MAX_PATH + 10];
wcscpy(destPath, path);
wcscat(destPath, L"7-zip.dll");
res = MyRegistry_SetString(destKey, NULL, destPath);
res = MyRegistry_SetString(destKey, L"ThreadingModel", L"Apartment");
/* res = */ MyRegistry_SetString(destKey, NULL, destPath);
/* res = */ MyRegistry_SetString(destKey, L"ThreadingModel", L"Apartment");
// DeleteRegValue(destKey, L"InprocServer32");
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
}
@@ -1011,7 +1013,8 @@ int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
BOOL bRet;
MSG msg;
while ((bRet = GetMessage(&msg, g_HWND, 0, 0)) != 0)
// we need messages for all thread windows (including EDITTEXT window in dialog)
while ((bRet = GetMessage(&msg, NULL, 0, 0)) != 0)
{
if (bRet == -1)
return retCode;
@@ -1083,7 +1086,6 @@ static int Install()
WCHAR sfxPath[MAX_PATH + 2];
Bool needReboot = False;
size_t pathLen;
allocImp.Alloc = SzAlloc;
allocImp.Free = SzFree;
@@ -1116,6 +1118,7 @@ static int Install()
if (res == SZ_OK)
{
size_t pathLen;
if (!g_SilentMode)
{
GetDlgItemTextW(g_HWND, IDE_EXTRACT_PATH, path, MAX_PATH);

View File

@@ -1,5 +1,5 @@
/* 7zipUninstall.c - 7-Zip Uninstaller
2015-08-09 : Igor Pavlov : Public domain */
2015-12-26 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -384,7 +384,7 @@ static void WriteCLSID()
if (res == ERROR_SUCCESS)
{
RegDeleteValueW(destKey, k_7zip_CLSID);
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
}
}
@@ -419,7 +419,7 @@ static void WriteCLSID()
if (res == ERROR_SUCCESS)
{
RegDeleteValueW(destKey, k_7zip_CLSID);
res = RegCloseKey(destKey);
/* res = */ RegCloseKey(destKey);
}
}
}
@@ -542,7 +542,7 @@ static BOOL RemoveDir()
#define k_Lang L"Lang"
// NUM_LANG_TXT_FILES files are placed before en.ttt
#define NUM_LANG_TXT_FILES 86
#define NUM_LANG_TXT_FILES 87
#ifdef _64BIT_INSTALLER
#define NUM_EXTRA_FILES_64BIT 1
@@ -556,7 +556,7 @@ static const char *k_Names =
"af an ar ast az ba be bg bn br ca co cs cy da de el eo es et eu ext"
" fa fi fr fur fy ga gl gu he hi hr hu hy id io is it ja ka kaa kk ko ku ku-ckb ky"
" lij lt lv mk mn mng mng2 mr ms nb ne nl nn pa-in pl ps pt pt-br ro ru"
" sa si sk sl sq sr-spc sr-spl sv ta th tr tt ug uk uz va vi zh-cn zh-tw"
" sa si sk sl sq sr-spc sr-spl sv ta th tr tt ug uk uz va vi yo zh-cn zh-tw"
" en.ttt"
" descript.ion"
" History.txt"
@@ -771,6 +771,8 @@ static INT_PTR CALLBACK MyDlgProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM
OnClose();
break;
}
default: return FALSE;
}
break;
@@ -1033,7 +1035,7 @@ int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
BOOL bRet;
MSG msg;
while ((bRet = GetMessage(&msg, g_HWND, 0, 0)) != 0)
while ((bRet = GetMessage(&msg, NULL, 0, 0)) != 0)
{
if (bRet == -1)
return retCode;

View File

@@ -1,5 +1,5 @@
/* LzmaUtil.c -- Test application for LZMA compression
2015-06-13 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "../../Precomp.h"
@@ -133,7 +133,7 @@ static SRes Encode(ISeqOutStream *outStream, ISeqInStream *inStream, UInt64 file
SRes res;
CLzmaEncProps props;
rs = rs;
UNUSED_VAR(rs);
enc = LzmaEnc_Create(&g_Alloc);
if (enc == 0)

View File

@@ -1,12 +1,14 @@
/* LzmaLibExports.c -- LZMA library DLL Entry point
2008-10-04 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "../../Precomp.h"
#include <windows.h>
BOOL WINAPI DllMain(HINSTANCE hInstance, DWORD dwReason, LPVOID lpReserved)
{
hInstance = hInstance;
dwReason = dwReason;
lpReserved = lpReserved;
UNUSED_VAR(hInstance);
UNUSED_VAR(dwReason);
UNUSED_VAR(lpReserved);
return TRUE;
}

View File

@@ -1,5 +1,5 @@
/* SfxSetup.c - 7z SFX Setup
2015-03-25 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -88,7 +88,7 @@ static unsigned FindItem(const char * const *items, unsigned num, const wchar_t
#ifdef _CONSOLE
static BOOL WINAPI HandlerRoutine(DWORD ctrlType)
{
ctrlType = ctrlType;
UNUSED_VAR(ctrlType);
return TRUE;
}
#endif
@@ -144,7 +144,7 @@ static Bool FindSignature(CSzFile *stream, UInt64 *resPos)
processed -= k7zStartHeaderSize;
for (pos = 0; pos <= processed; pos++)
{
for (; buf[pos] != '7' && pos <= processed; pos++);
for (; pos <= processed && buf[pos] != '7'; pos++);
if (pos > processed)
break;
if (memcmp(buf + pos, k7zSignature, k7zSignatureSize) == 0)
@@ -257,10 +257,10 @@ int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
#ifdef _CONSOLE
SetConsoleCtrlHandler(HandlerRoutine, TRUE);
#else
hInstance = hInstance;
hPrevInstance = hPrevInstance;
lpCmdLine = lpCmdLine;
nCmdShow = nCmdShow;
UNUSED_VAR(hInstance);
UNUSED_VAR(hPrevInstance);
UNUSED_VAR(lpCmdLine);
UNUSED_VAR(nCmdShow);
#endif
CrcGenerateTable();

View File

@@ -1,5 +1,5 @@
/* XzDec.c -- Xz Decode
2015-05-01 : Igor Pavlov : Public domain */
2015-11-09 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -74,7 +74,7 @@ static void BraState_Free(void *pp, ISzAlloc *alloc)
static SRes BraState_SetProps(void *pp, const Byte *props, size_t propSize, ISzAlloc *alloc)
{
CBraState *p = ((CBraState *)pp);
alloc = alloc;
UNUSED_VAR(alloc);
p->ip = 0;
if (p->methodId == XZ_ID_Delta)
{
@@ -129,9 +129,9 @@ static SRes BraState_Code(void *pp, Byte *dest, SizeT *destLen, const Byte *src,
CBraState *p = ((CBraState *)pp);
SizeT destLenOrig = *destLen;
SizeT srcLenOrig = *srcLen;
UNUSED_VAR(finishMode);
*destLen = 0;
*srcLen = 0;
finishMode = finishMode;
*wasFinished = 0;
while (destLenOrig > 0)
{
@@ -236,8 +236,8 @@ static void SbState_Free(void *pp, ISzAlloc *alloc)
static SRes SbState_SetProps(void *pp, const Byte *props, size_t propSize, ISzAlloc *alloc)
{
UNUSED_VAR(pp);
props = props;
alloc = alloc;
UNUSED_VAR(props);
UNUSED_VAR(alloc);
return (propSize == 0) ? SZ_OK : SZ_ERROR_UNSUPPORTED;
}
@@ -251,7 +251,7 @@ static SRes SbState_Code(void *pp, Byte *dest, SizeT *destLen, const Byte *src,
{
CSbDec *p = (CSbDec *)pp;
SRes res;
srcWasFinished = srcWasFinished;
UNUSED_VAR(srcWasFinished);
p->dest = dest;
p->destLen = *destLen;
p->src = src;
@@ -308,7 +308,7 @@ static SRes Lzma2State_Code(void *pp, Byte *dest, SizeT *destLen, const Byte *sr
ELzmaStatus status;
/* ELzmaFinishMode fm = (finishMode == LZMA_FINISH_ANY) ? LZMA_FINISH_ANY : LZMA_FINISH_END; */
SRes res = Lzma2Dec_DecodeToBuf((CLzma2Dec *)pp, dest, destLen, src, srcLen, (ELzmaFinishMode)finishMode, &status);
srcWasFinished = srcWasFinished;
UNUSED_VAR(srcWasFinished);
*wasFinished = (status == LZMA_STATUS_FINISHED_WITH_MARK);
return res;
}
@@ -555,7 +555,7 @@ SRes XzBlock_Parse(CXzBlock *p, const Byte *header)
pos += (unsigned)size;
#ifdef XZ_DUMP
printf("\nf[%d] = %2X: ", i, filter->id);
printf("\nf[%u] = %2X: ", i, (unsigned)filter->id);
{
unsigned i;
for (i = 0; i < size; i++)

View File

@@ -1,5 +1,5 @@
/* XzIn.c - Xz input
2015-04-21 : Igor Pavlov : Public domain */
2015-11-08 : Igor Pavlov : Public domain */
#include "Precomp.h"
@@ -72,7 +72,7 @@ SRes XzBlock_ReadFooter(CXzBlock *p, CXzStreamFlags f, ISeqInStream *inStream)
static SRes Xz_ReadIndex2(CXzStream *p, const Byte *buf, size_t size, ISzAlloc *alloc)
{
size_t i, numBlocks, pos = 1;
size_t numBlocks, pos = 1;
UInt32 crc;
if (size < 5 || buf[0] != 0)
@@ -94,6 +94,7 @@ static SRes Xz_ReadIndex2(CXzStream *p, const Byte *buf, size_t size, ISzAlloc *
Xz_Free(p, alloc);
if (numBlocks != 0)
{
size_t i;
p->numBlocks = numBlocks;
p->numBlocksAllocated = numBlocks;
p->blocks = alloc->Alloc(alloc, sizeof(CXzBlockSizes) * numBlocks);

View File

@@ -87,6 +87,8 @@ struct CFolders
return PackPositions[index + 1] - PackPositions[index];
}
CFolders(): NumPackStreams(0), NumFolders(0) {}
void Clear()
{
NumPackStreams = 0;

View File

@@ -567,14 +567,17 @@ static const char *g_Exts =
" iso bin nrg mdf img pdi tar cpio xpi"
" vfd vhd vud vmc vsv"
" vmdk dsk nvram vmem vmsd vmsn vmss vmtm"
" inl inc idl acf asa h hpp hxx c cpp cxx rc java cs pas bas vb cls ctl frm dlg def"
" inl inc idl acf asa"
" h hpp hxx c cpp cxx m mm go swift"
" rc java cs rs pas bas vb cls ctl frm dlg def"
" f77 f f90 f95"
" asm sql manifest dep"
" asm s"
" sql manifest dep"
" mak clw csproj vcproj sln dsp dsw"
" class"
" bat cmd"
" bat cmd bash sh"
" xml xsd xsl xslt hxk hxc htm html xhtml xht mht mhtml htw asp aspx css cgi jsp shtml"
" awk sed hta js php php3 php4 php5 phptml pl pm py pyo rb sh tcl vbs"
" awk sed hta js json php php3 php4 php5 phptml pl pm py pyo rb tcl ts vbs"
" text txt tex ans asc srt reg ini doc docx mcw dot rtf hlp xls xlr xlt xlw ppt pdf"
" sxc sxd sxi sxg sxw stc sti stw stm odt ott odg otg odp otp ods ots odf"
" abw afp cwk lwp wpd wps wpt wrf wri"

View File

@@ -781,6 +781,7 @@ HRESULT CFolderOutStream::Write2(const void *data, UInt32 size, UInt32 *processe
realProcessed += size;
if (processedSize)
*processedSize = realProcessed;
m_PosInFolder += size;
return S_OK;
// return E_FAIL;
}
@@ -843,7 +844,7 @@ HRESULT CFolderOutStream::FlushCorrupted(unsigned folderIndex)
return S_OK;
}
const unsigned kBufSize = (1 << 10);
const unsigned kBufSize = (1 << 12);
Byte buf[kBufSize];
for (unsigned i = 0; i < kBufSize; i++)
buf[i] = 0;
@@ -937,8 +938,15 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
CRecordVector<bool> extractStatuses;
for (i = 0; i < numItems;)
for (i = 0;;)
{
lps->OutSize = totalUnPacked;
lps->InSize = totalPacked;
RINOK(lps->SetCur());
if (i >= numItems)
break;
unsigned index = allFilesMode ? i : indices[i];
const CMvItem &mvItem = m_Database.Items[index];
@@ -1003,10 +1011,6 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
curUnpack = item.GetEndOffset();
}
lps->OutSize = totalUnPacked;
lps->InSize = totalPacked;
RINOK(lps->SetCur());
CFolderOutStream *cabFolderOutStream = new CFolderOutStream;
CMyComPtr<ISequentialOutStream> outStream(cabFolderOutStream);

View File

@@ -67,6 +67,7 @@ void CInArchive::ReadOtherArc(COtherArc &oa)
ReadName(oa.DiskName);
}
struct CSignatureFinder
{
Byte *Buf;
@@ -100,6 +101,7 @@ struct CSignatureFinder
HRESULT Find();
};
HRESULT CSignatureFinder::Find()
{
for (;;)
@@ -156,6 +158,7 @@ HRESULT CSignatureFinder::Find()
}
}
bool CInArcInfo::Parse(const Byte *p)
{
if (Get32(p + 0x0C) != 0 ||
@@ -177,6 +180,7 @@ bool CInArcInfo::Parse(const Byte *p)
return true;
}
HRESULT CInArchive::Open2(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
{
IsArc = false;
@@ -286,7 +290,9 @@ HRESULT CInArchive::Open2(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
if (ai.IsThereNext()) ReadOtherArc(ai.NextArc);
UInt32 i;
db.Folders.ClearAndReserve(ai.NumFolders);
for (i = 0; i < ai.NumFolders; i++)
{
Read(p, 8);
@@ -311,6 +317,7 @@ HRESULT CInArchive::Open2(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
}
db.Items.ClearAndReserve(ai.NumFiles);
for (i = 0; i < ai.NumFiles; i++)
{
Read(p, 16);
@@ -324,6 +331,7 @@ HRESULT CInArchive::Open2(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
item.Attributes = Get16(p + 14);
ReadName(item.Name);
if (item.GetFolderIndex(db.Folders.Size()) >= (int)db.Folders.Size())
{
HeaderError = true;
@@ -336,6 +344,7 @@ HRESULT CInArchive::Open2(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
return S_OK;
}
HRESULT CInArchive::Open(CDatabaseEx &db, const UInt64 *searchHeaderSizeLimit)
{
try
@@ -370,6 +379,7 @@ static int CompareMvItems(const CMvItem *p1, const CMvItem *p2, void *param)
return MyCompare(p1->ItemIndex, p2->ItemIndex);
}
bool CMvDatabaseEx::AreItemsEqual(unsigned i1, unsigned i2)
{
const CMvItem *p1 = &Items[i1];
@@ -384,12 +394,15 @@ bool CMvDatabaseEx::AreItemsEqual(unsigned i1, unsigned i2)
&& item1.Name == item2.Name;
}
void CMvDatabaseEx::FillSortAndShrink()
{
Items.Clear();
StartFolderOfVol.Clear();
FolderStartFileIndex.Clear();
int offset = 0;
FOR_VECTOR (v, Volumes)
{
const CDatabaseEx &db = Volumes[v];
@@ -422,11 +435,12 @@ void CMvDatabaseEx::FillSortAndShrink()
FOR_VECTOR (i, Items)
{
int folderIndex = GetFolderIndex(&Items[i]);
if (folderIndex >= (int)FolderStartFileIndex.Size())
while (folderIndex >= (int)FolderStartFileIndex.Size())
FolderStartFileIndex.Add(i);
}
}
bool CMvDatabaseEx::Check()
{
for (unsigned v = 1; v < Volumes.Size(); v++)
@@ -444,9 +458,11 @@ bool CMvDatabaseEx::Check()
return false;
}
}
UInt32 beginPos = 0;
UInt64 endPos = 0;
int prevFolder = -2;
FOR_VECTOR (i, Items)
{
const CMvItem &mvItem = Items[i];
@@ -456,15 +472,19 @@ bool CMvDatabaseEx::Check()
const CItem &item = Volumes[mvItem.VolumeIndex].Items[mvItem.ItemIndex];
if (item.IsDir())
continue;
int folderIndex = GetFolderIndex(&mvItem);
if (folderIndex != prevFolder)
prevFolder = folderIndex;
else if (item.Offset < endPos &&
(item.Offset != beginPos || item.GetEndOffset() != endPos))
return false;
beginPos = item.Offset;
endPos = item.GetEndOffset();
}
return true;
}

View File

@@ -25,6 +25,7 @@ struct COtherArc
}
};
struct CArchInfo
{
Byte VersionMinor; // cabinet file format version, minor
@@ -65,6 +66,7 @@ struct CArchInfo
}
};
struct CInArcInfo: public CArchInfo
{
UInt32 Size; // size of this cabinet file in bytes
@@ -105,17 +107,20 @@ struct CDatabase
}
};
struct CDatabaseEx: public CDatabase
{
CMyComPtr<IInStream> Stream;
};
struct CMvItem
{
unsigned VolumeIndex;
unsigned ItemIndex;
};
class CMvDatabaseEx
{
bool AreItemsEqual(unsigned i1, unsigned i2);

View File

@@ -571,6 +571,7 @@ HRESULT CDatabase::Open(IInStream *inStream)
RINOK(AddNode(-1, root.SonDid));
unsigned numCabs = 0;
FOR_VECTOR (i, Refs)
{
const CItem &item = Items[Refs[i].Did];
@@ -578,16 +579,20 @@ HRESULT CDatabase::Open(IInStream *inStream)
continue;
bool isMsiName;
UString msiName = ConvertName(item.Name, isMsiName);
if (isMsiName)
if (isMsiName && !msiName.IsEmpty())
{
bool isThereExt = (msiName.Find(L'.') >= 0);
bool isMsiSpec = (msiName[0] == k_Msi_SpecChar);
if (msiName.Len() >= 4 && StringsAreEqualNoCase_Ascii(msiName.RightPtr(4), ".cab")
|| msiName.Len() >= 3 && msiName[0] != k_Msi_SpecChar && StringsAreEqualNoCase_Ascii(msiName.RightPtr(3), "exe"))
|| !isMsiSpec && msiName.Len() >= 3 && StringsAreEqualNoCase_Ascii(msiName.RightPtr(3), "exe")
|| !isMsiSpec && !isThereExt)
{
numCabs++;
MainSubfile = i;
}
}
}
if (numCabs > 1)
MainSubfile = -1;

View File

@@ -26,6 +26,7 @@ HINSTANCE g_hInstance;
#define NT_CHECK_FAIL_ACTION return FALSE;
#ifdef _WIN32
extern "C"
BOOL WINAPI DllMain(
#ifdef UNDER_CE
@@ -49,6 +50,7 @@ BOOL WINAPI DllMain(
*/
return TRUE;
}
#endif
DEFINE_GUID(CLSID_CArchiveHandler,
k_7zip_GUID_Data1,

View File

@@ -1118,7 +1118,7 @@ HRESULT CHandler::SeekAndRead(IInStream *inStream, UInt64 block, Byte *data, siz
{
if (block == 0 || block >= _h.NumBlocks)
return S_FALSE;
if (((size + (1 << _h.BlockBits) + 1) >> _h.BlockBits) > _h.NumBlocks - block)
if (((size + ((size_t)1 << _h.BlockBits) - 1) >> _h.BlockBits) > _h.NumBlocks - block)
return S_FALSE;
RINOK(inStream->Seek((UInt64)block << _h.BlockBits, STREAM_SEEK_SET, NULL));
_totalRead += size;
@@ -1167,6 +1167,9 @@ HRESULT CHandler::Open2(IInStream *inStream)
RINOK(_openCallback->SetTotal(NULL, &_phySize));
}
UInt64 fileSize = 0;
RINOK(inStream->Seek(0, STREAM_SEEK_END, &fileSize));
CRecordVector<CGroupDescriptor> groups;
{
@@ -1213,6 +1216,21 @@ HRESULT CHandler::Open2(IInStream *inStream)
if (_h.NumInodes < _h.NumFreeInodes)
return S_FALSE;
UInt32 numNodes = _h.InodesPerGroup;
if (numNodes > _h.NumInodes)
numNodes = _h.NumInodes;
size_t nodesDataSize = (size_t)numNodes * _h.InodeSize;
if (nodesDataSize / _h.InodeSize != numNodes)
return S_FALSE;
// that code to reduce false detecting cases
if (nodesDataSize > fileSize)
{
if (numNodes > (1 << 24))
return S_FALSE;
}
UInt32 numReserveInodes = _h.NumInodes - _h.NumFreeInodes + 1;
// numReserveInodes = _h.NumInodes + 1;
@@ -1222,13 +1240,6 @@ HRESULT CHandler::Open2(IInStream *inStream)
_refs.Reserve(numReserveInodes);
}
UInt32 numNodes = _h.InodesPerGroup;
if (numNodes > _h.NumInodes)
numNodes = _h.NumInodes;
size_t nodesDataSize = numNodes * _h.InodeSize;
if (nodesDataSize / _h.InodeSize != numNodes)
return S_FALSE;
CByteBuffer nodesData;
nodesData.Alloc(nodesDataSize);

View File

@@ -160,10 +160,13 @@ bool CHeader::Parse(const Byte *p)
if (NumFats < 1 || NumFats > 4)
return false;
// we also support images that contain 0 in offset field.
bool isOkOffset = (codeOffset == 0 || (p[0] == 0xEB && p[1] == 0));
UInt16 numRootDirEntries = Get16(p + 17);
if (numRootDirEntries == 0)
{
if (codeOffset < 90)
if (codeOffset < 90 && !isOkOffset)
return false;
NumFatBits = 32;
NumRootDirSectors = 0;
@@ -171,7 +174,7 @@ bool CHeader::Parse(const Byte *p)
else
{
// Some FAT12s don't contain VolFields
if (codeOffset < 62 - 24)
if (codeOffset < 62 - 24 && !isOkOffset)
return false;
NumFatBits = 0;
UInt32 mask = (1 << (SectorSizeLog - 5)) - 1;

View File

@@ -170,7 +170,7 @@ struct CBootInitialEntry
// Partition Table found in the boot image.
UInt16 SectorCount; // This is the number of virtual/emulated sectors the system
// will store at Load Segment during the initial boot procedure.
UInt32 LoadRBA; // This is the start address of the virtual disk. CD<EFBFBD>s use
UInt32 LoadRBA; // This is the start address of the virtual disk. CDs use
// Relative/Logical block addressing.
Byte VendorSpec[20];

View File

@@ -347,18 +347,24 @@ struct CSection
CSection(): IsRealSect(false), IsDebug(false), IsAdditionalSection(false) {}
// const UInt32 GetSize() const { return PSize; }
const UInt32 GetSize() const { return MyMin(PSize, VSize); }
void UpdateTotalSize(UInt32 &totalSize) const
{
UInt32 t = Pa + PSize;
if (totalSize < t)
totalSize = t;
}
void Parse(const Byte *p);
int Compare(const CSection &s) const
{
RINOZ(MyCompare(Pa, s.Pa));
return MyCompare(PSize, s.PSize);
UInt32 size1 = GetSize();
UInt32 size2 = s.GetSize();
return MyCompare(size1, size2);
}
};
@@ -1039,7 +1045,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
switch (propID)
{
case kpidPath: prop = MultiByteToUnicodeString(item.Name); break;
case kpidSize: prop = (UInt64)MyMin(item.PSize, item.VSize); break;
case kpidSize: prop = (UInt64)item.GetSize(); break;
case kpidPackSize: prop = (UInt64)item.PSize; break;
case kpidVirtualSize: prop = (UInt64)item.VSize; break;
case kpidOffset: prop = item.Pa; break;
@@ -1883,14 +1889,17 @@ static bool ParseVersion(const Byte *p, UInt32 size, CTextFile &f, CObjectVector
}
f.CloseBlock(2);
}
f.CloseBlock(0);
return true;
}
HRESULT CHandler::OpenResources(unsigned sectionIndex, IInStream *stream, IArchiveOpenCallback *callback)
{
const CSection &sect = _sections[sectionIndex];
size_t fileSize = sect.PSize; // Maybe we need sect.VSize here !!!
const size_t fileSize = sect.GetSize();
if (fileSize > kFileSizeMax)
return S_FALSE;
{
@@ -2031,8 +2040,8 @@ HRESULT CHandler::OpenResources(unsigned sectionIndex, IInStream *stream, IArchi
{
UInt32 mask = (1 << numBits) - 1;
size_t end = ((maxOffset + mask) & ~mask);
// 9.29: we use only PSize. PSize can be larger than VSize
if (/* end < sect.VSize && */ end <= sect.PSize)
if (/* end < sect.VSize && */ end <= sect.GetSize())
{
CSection sect2;
sect2.Flags = 0;
@@ -2050,7 +2059,8 @@ HRESULT CHandler::OpenResources(unsigned sectionIndex, IInStream *stream, IArchi
// 9.29: we use sect.PSize instead of sect.VSize to support some CAB-SFX
// the code for .rsrc_2 is commented.
sect2.PSize = sect.PSize - (UInt32)maxOffset;
sect2.PSize = sect.GetSize() - (UInt32)maxOffset;
if (sect2.PSize != 0)
{
sect2.VSize = sect2.PSize;
@@ -2463,7 +2473,7 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
else if (mixItem.ResourceIndex >= 0)
size = _items[mixItem.ResourceIndex].GetSize();
else
size = _sections[mixItem.SectionIndex].PSize;
size = _sections[mixItem.SectionIndex].GetSize();
totalSize += size;
}
extractCallback->SetTotal(totalSize);
@@ -2539,7 +2549,7 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
}
else
{
currentItemSize = sect.PSize;
currentItemSize = sect.GetSize();
if (!testMode && !outStream)
continue;

View File

@@ -1,5 +1,5 @@
/* PpmdHandler.c -- PPMd format handler
2010-03-10 : Igor Pavlov : Public domain
/* PpmdHandler.cpp -- PPMd format handler
2015-11-30 : Igor Pavlov : Public domain
This code is based on:
PPMd var.H (2001) / var.I (2002): Dmitry Shkarin : Public domain
Carryless rangecoder (1999): Dmitry Subbotin : Public domain */
@@ -349,6 +349,7 @@ struct CPpmdCpp
}
};
STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
Int32 testMode, IArchiveExtractCallback *extractCallback)
{
@@ -386,13 +387,17 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
CPpmdCpp ppmd(_item.Ver);
if (!ppmd.Alloc(_item.MemInMB))
return E_OUTOFMEMORY;
Int32 opRes = NExtract::NOperationResult::kUnsupportedMethod;
if (_item.IsSupported())
{
opRes = NExtract::NOperationResult::kDataError;
ppmd.Init(_item.Order, _item.Restor);
inBuf.Init();
UInt64 outSize = 0;
if (ppmd.InitRc(&inBuf) && !inBuf.Extra && inBuf.Res == S_OK)
for (;;)
{
@@ -431,6 +436,13 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
{
RINOK(WriteStream(realOutStream, outBuf.Buf, i));
}
if (inBuf.Extra)
{
opRes = NExtract::NOperationResult::kUnexpectedEnd;
break;
}
if (sym < 0)
{
if (sym == -1 && ppmd.IsFinishedOK())
@@ -438,12 +450,15 @@ STDMETHODIMP CHandler::Extract(const UInt32 *indices, UInt32 numItems,
break;
}
}
RINOK(inBuf.Res);
}
realOutStream.Release();
return extractCallback->SetOperationResult(opRes);
}
static const Byte k_Signature[] = { 0x8F, 0xAF, 0xAC, 0x84 };
REGISTER_ARC_I(

View File

@@ -1825,6 +1825,8 @@ HRESULT CHandler::Open2(IInStream *stream,
int prevSplitFile = -1;
int prevMainFile = -1;
bool nextVol_is_Required = false;
CInArchive arch;
for (;;)
@@ -1861,7 +1863,8 @@ HRESULT CHandler::Open2(IInStream *stream,
if (!inStream || result != S_OK)
{
_missingVolName = volName;
if (nextVol_is_Required)
_missingVolName = volName;
break;
}
}
@@ -2111,11 +2114,18 @@ HRESULT CHandler::Open2(IInStream *stream,
}
curBytes += endPos;
nextVol_is_Required = false;
if (!arcInfo.IsVolume())
break;
if (arcInfo.EndOfArchive_was_Read
&& !arcInfo.AreMoreVolumes())
break;
if (arcInfo.EndOfArchive_was_Read)
{
if (!arcInfo.AreMoreVolumes())
break;
nextVol_is_Required = true;
}
}
FillLinks();

View File

@@ -640,6 +640,7 @@ HRESULT CInArchive::GetNextItem(CItem &item, ICryptoGetTextPassword *getTextPass
{
ArcInfo.EndFlags = m_BlockHeader.Flags;
UInt32 offset = 7;
if (m_BlockHeader.Flags & NHeader::NArchive::kEndOfArc_Flags_DataCRC)
{
if (processed < offset + 4)
@@ -648,6 +649,7 @@ HRESULT CInArchive::GetNextItem(CItem &item, ICryptoGetTextPassword *getTextPass
ArcInfo.DataCRC = Get32(m_FileHeaderData + offset);
offset += 4;
}
if (m_BlockHeader.Flags & NHeader::NArchive::kEndOfArc_Flags_VolNumber)
{
if (processed < offset + 2)
@@ -657,6 +659,7 @@ HRESULT CInArchive::GetNextItem(CItem &item, ICryptoGetTextPassword *getTextPass
ArcInfo.EndOfArchive_was_Read = true;
}
m_Position += processed;
FinishCryptoBlock();
ArcInfo.EndPos = m_Position;
@@ -699,11 +702,13 @@ HRESULT CInArchive::GetNextItem(CItem &item, ICryptoGetTextPassword *getTextPass
continue;
*/
}
if (m_CryptoMode && m_BlockHeader.HeadSize > (1 << 10))
{
error = k_ErrorType_DecryptionError;
return S_OK;
}
if ((m_BlockHeader.Flags & NHeader::NBlock::kLongBlock) != 0)
{
if (m_FileHeaderData.Size() < 7 + 4)
@@ -1032,7 +1037,10 @@ HRESULT CHandler::Open2(IInStream *stream,
openCallback->QueryInterface(IID_ICryptoGetTextPassword, (void **)&getTextPassword);
}
bool nextVol_is_Required = false;
CInArchive archive;
for (;;)
{
CMyComPtr<IInStream> inStream;
@@ -1072,7 +1080,8 @@ HRESULT CHandler::Open2(IInStream *stream,
if (!inStream || result != S_OK)
{
_missingVolName = volName;
if (nextVol_is_Required)
_missingVolName = volName;
break;
}
}
@@ -1191,6 +1200,18 @@ HRESULT CHandler::Open2(IInStream *stream,
arc.PhySize = archive.ArcInfo.GetPhySize();
arc.Stream = inStream;
}
nextVol_is_Required = false;
if (!archive.ArcInfo.IsVolume())
break;
if (archive.ArcInfo.EndOfArchive_was_Read)
{
if (!archive.ArcInfo.AreMoreVolumes())
break;
nextVol_is_Required = true;
}
}
}

View File

@@ -45,6 +45,7 @@ struct CInArcInfo
bool IsEncryptOld() const { return (!IsThereEncryptVer() || EncryptVersion < 36); }
bool AreMoreVolumes() const { return (EndFlags & NHeader::NArchive::kEndOfArc_Flags_NextVol) != 0; }
bool Is_VolNumber_Defined() const { return (EndFlags & NHeader::NArchive::kEndOfArc_Flags_VolNumber) != 0; }
bool Is_DataCRC_Defined() const { return (EndFlags & NHeader::NArchive::kEndOfArc_Flags_DataCRC) != 0; }
};

View File

@@ -98,6 +98,7 @@ STDMETHODIMP CHandler::GetArchiveProperty(PROPID propID, PROPVARIANT *value)
if (!_archive.IsArc) v |= kpv_ErrorFlags_IsNotArc;
if (_archive.Unsupported) v |= kpv_ErrorFlags_UnsupportedFeature;
if (_archive.UnexpectedEnd) v |= kpv_ErrorFlags_UnexpectedEnd;
if (_archive.NoEndAnchor) v |= kpv_ErrorFlags_HeadersError;
prop = v;
break;
}

View File

@@ -610,6 +610,7 @@ API_FUNC_IsArc IsArc_Udf(const Byte *p, size_t size)
}
}
HRESULT CInArchive::Open2()
{
Clear();
@@ -644,8 +645,10 @@ HRESULT CInArchive::Open2()
CExtent extentVDS;
extentVDS.Parse(buf + i + 16);
*/
const size_t kBufSize = 1 << 11;
Byte buf[kBufSize];
for (SecLogSize = 11;; SecLogSize -= 3)
{
if (SecLogSize < 8)
@@ -665,6 +668,7 @@ HRESULT CInArchive::Open2()
break;
}
}
PhySize = (UInt32)(256 + 1) << SecLogSize;
IsArc = true;
@@ -946,28 +950,63 @@ HRESULT CInArchive::Open2()
}
{
UInt32 secMask = ((UInt32)1 << SecLogSize) - 1;
const UInt32 secMask = ((UInt32)1 << SecLogSize) - 1;
PhySize = (PhySize + secMask) & ~(UInt64)secMask;
}
NoEndAnchor = true;
if (PhySize < fileSize)
{
UInt64 rem = fileSize - PhySize;
const size_t secSize = (size_t)1 << SecLogSize;
RINOK(_stream->Seek(PhySize, STREAM_SEEK_SET, NULL));
size_t bufSize = (UInt32)1 << SecLogSize;
size_t readSize = bufSize;
RINOK(ReadStream(_stream, buf, &readSize));
if (readSize == bufSize)
// some UDF images contain ZEROs before "Anchor Volume Descriptor Pointer" at the end
for (unsigned sec = 0; sec < 1024; sec++)
{
CTag tag;
if (tag.Parse(buf, readSize) == S_OK)
if (tag.Id == DESC_TYPE_AnchorVolPtr)
if (rem == 0)
break;
size_t readSize = secSize;
if (readSize > rem)
readSize = (size_t)rem;
RINOK(ReadStream(_stream, buf, &readSize));
if (readSize == 0)
break;
if (readSize == secSize && NoEndAnchor)
{
CTag tag;
if (tag.Parse(buf, readSize) == S_OK &&
tag.Id == DESC_TYPE_AnchorVolPtr)
{
PhySize += bufSize;
NoEndAnchor = false;
rem -= readSize;
PhySize = fileSize - rem;
continue;
}
}
size_t i;
for (i = 0; i < readSize && buf[i] == 0; i++);
if (i != readSize)
break;
rem -= readSize;
}
if (rem == 0)
PhySize = fileSize;
}
return S_OK;
}
HRESULT CInArchive::Open(IInStream *inStream, CProgressVirt *progress)
{
_progress = progress;
@@ -1000,6 +1039,7 @@ void CInArchive::Clear()
IsArc = false;
Unsupported = false;
UnexpectedEnd = false;
NoEndAnchor = false;
PhySize = 0;
FileSize = 0;

View File

@@ -370,6 +370,7 @@ public:
bool IsArc;
bool Unsupported;
bool UnexpectedEnd;
bool NoEndAnchor;
void UpdatePhySize(UInt64 val)
{

View File

@@ -4,6 +4,7 @@
#include "../../../Common/ComTry.h"
#include "../../../Common/IntToString.h"
#include "../../../Common/StringConvert.h"
#include "../../../Windows/PropVariant.h"
#include "../../../Windows/TimeUtils.h"
@@ -241,12 +242,14 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
COM_TRY_BEGIN
NWindows::NCOM::CPropVariant prop;
const CItemEx &item = m_Items[index];
const CExtraBlock &extra = item.GetMainExtra();
switch (propID)
{
case kpidPath:
{
UString res;
item.GetUnicodeString(item.Name, res, _forceCodePage, _specifiedCodePage);
item.GetUnicodeString(res, item.Name, false, _forceCodePage, _specifiedCodePage);
NItemName::ConvertToOSName2(res);
prop = res;
break;
@@ -261,9 +264,9 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
FILETIME ft;
UInt32 unixTime;
UInt32 type;
if (item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, ft))
if (extra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, ft))
type = NFileTimeType::kWindows;
else if (item.CentralExtra.GetUnixTime(true, NFileHeader::NUnixTime::kMTime, unixTime))
else if (extra.GetUnixTime(true, NFileHeader::NUnixTime::kMTime, unixTime))
type = NFileTimeType::kUnix;
else
type = NFileTimeType::kDOS;
@@ -274,7 +277,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidCTime:
{
FILETIME ft;
if (item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kCTime, ft))
if (extra.GetNtfsTime(NFileHeader::NNtfsExtra::kCTime, ft))
prop = ft;
break;
}
@@ -282,7 +285,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
case kpidATime:
{
FILETIME ft;
if (item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kATime, ft))
if (extra.GetNtfsTime(NFileHeader::NNtfsExtra::kATime, ft))
prop = ft;
break;
}
@@ -291,10 +294,10 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
{
FILETIME utc;
bool defined = true;
if (!item.CentralExtra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, utc))
if (!extra.GetNtfsTime(NFileHeader::NNtfsExtra::kMTime, utc))
{
UInt32 unixTime = 0;
if (item.CentralExtra.GetUnixTime(true, NFileHeader::NUnixTime::kMTime, unixTime))
if (extra.GetUnixTime(true, NFileHeader::NUnixTime::kMTime, unixTime))
NTime::UnixTimeToFileTime(unixTime, utc);
else
{
@@ -328,7 +331,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
if (item.Comment.Size() != 0)
{
UString res;
item.GetUnicodeString(BytesToString(item.Comment), res, _forceCodePage, _specifiedCodePage);
item.GetUnicodeString(res, BytesToString(item.Comment), true, _forceCodePage, _specifiedCodePage);
prop = res;
}
break;
@@ -347,7 +350,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
{
m += kMethod_AES;
CWzAesExtra aesField;
if (item.CentralExtra.GetWzAes(aesField))
if (extra.GetWzAes(aesField))
{
char s[16];
s[0] = '-';
@@ -360,7 +363,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
{
CStrongCryptoExtra f;
f.AlgId = 0;
if (item.CentralExtra.GetStrongCrypto(f))
if (extra.GetStrongCrypto(f))
{
const char *s = FindNameForId(k_StrongCryptoPairs, ARRAY_SIZE(k_StrongCryptoPairs), f.AlgId);
if (s)
@@ -373,6 +376,8 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
ConvertUInt32ToString(f.AlgId, temp + 1);
m += temp;
}
if (f.CertificateIsUsed())
m += "-Cert";
}
else
m += kMethod_StrongCrypto;
@@ -425,6 +430,7 @@ STDMETHODIMP CHandler::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *val
prop = (UInt32)item.ExtractVersion.Version;
break;
}
prop.Detach(value);
return S_OK;
COM_TRY_END
@@ -615,7 +621,7 @@ HRESULT CZipDecoder::Decode(
if (!pkAesMode && id == NFileHeader::NCompressionMethod::kWzAES)
{
CWzAesExtra aesField;
if (item.CentralExtra.GetWzAes(aesField))
if (item.GetMainExtra().GetWzAes(aesField))
{
wzAesMode = true;
needCRC = aesField.NeedCrc();
@@ -651,7 +657,7 @@ HRESULT CZipDecoder::Decode(
if (wzAesMode)
{
CWzAesExtra aesField;
if (!item.CentralExtra.GetWzAes(aesField))
if (!item.GetMainExtra().GetWzAes(aesField))
return S_OK;
id = aesField.Method;
if (!_wzAesDecoder)

View File

@@ -84,6 +84,8 @@ namespace NFileHeader
kNTFS = 0x0A,
kStrongEncrypt = 0x17,
kUnixTime = 0x5455,
kIzUnicodeComment = 0x6375,
kIzUnicodeName = 0x7075,
kWzAES = 0x9901
};
}

View File

@@ -188,9 +188,9 @@ API_FUNC_IsArc IsArc_Zip(const Byte *p, size_t size)
// Crc = Get32(p + 10);
// PackSize = Get32(p + 14);
// Size = Get32(p + 18);
unsigned nameSize = Get16(p + 22);
const unsigned nameSize = Get16(p + 22);
unsigned extraSize = Get16(p + 24);
UInt32 extraOffset = kLocalHeaderSize + (UInt32)nameSize;
const UInt32 extraOffset = kLocalHeaderSize + (UInt32)nameSize;
if (extraOffset + extraSize > (1 << 16))
return k_IsArc_Res_NO;
@@ -203,7 +203,8 @@ API_FUNC_IsArc IsArc_Zip(const Byte *p, size_t size)
const Byte *p2 = p + kLocalHeaderSize;
for (size_t i = 0; i < rem; i++)
if (p2[i] == 0)
return k_IsArc_Res_NO;
if (i != nameSize - 1)
return k_IsArc_Res_NO;
}
if (size < extraOffset)
@@ -562,13 +563,21 @@ bool CInArchive::ReadLocalItem(CItemEx &item)
// return false;
}
}
if (!CheckDosTime(item.Time))
{
HeadersWarning = true;
// return false;
}
if (item.Name.Len() != nameSize)
return false;
{
// we support "bad" archives with null-terminated name.
if (item.Name.Len() + 1 != nameSize)
return false;
HeadersWarning = true;
}
return item.LocalFullHeaderSize <= ((UInt32)1 << 16);
}
@@ -782,9 +791,9 @@ HRESULT CInArchive::ReadCdItem(CItemEx &item)
item.Crc = Get32(p + 12);
item.PackSize = Get32(p + 16);
item.Size = Get32(p + 20);
unsigned nameSize = Get16(p + 24);
UInt16 extraSize = Get16(p + 26);
UInt16 commentSize = Get16(p + 28);
const unsigned nameSize = Get16(p + 24);
const unsigned extraSize = Get16(p + 26);
const unsigned commentSize = Get16(p + 28);
UInt32 diskNumberStart = Get16(p + 30);
item.InternalAttrib = Get16(p + 32);
item.ExternalAttrib = Get32(p + 34);
@@ -961,7 +970,7 @@ HRESULT CInArchive::TryReadCd(CObjectVector<CItemEx> &items, UInt64 cdOffset, UI
CItemEx cdItem;
RINOK(ReadCdItem(cdItem));
items.Add(cdItem);
if (progress && items.Size() % 1 == 0)
if (progress && (items.Size() & 0xFFF) == 0)
RINOK(progress->SetCompletedCD(items.Size()));
}
return (m_Position - cdOffset == cdSize) ? S_OK : S_FALSE;
@@ -1009,6 +1018,7 @@ bool IsStrangeItem(const CItem &item)
return item.Name.Len() > (1 << 14) || item.Method > (1 << 8);
}
HRESULT CInArchive::ReadLocals(
CObjectVector<CItemEx> &items, CProgressVirt *progress)
{
@@ -1037,7 +1047,8 @@ HRESULT CInArchive::ReadLocals(
return S_FALSE;
throw;
}
if (progress && items.Size() % 1 == 0)
if (progress && (items.Size() & 0xFF) == 0)
RINOK(progress->SetCompletedLocal(items.Size(), item.LocalHeaderPos));
}
@@ -1154,15 +1165,17 @@ HRESULT CInArchive::ReadHeaders2(CObjectVector<CItemEx> &items, CProgressVirt *p
HeadersError = true;
return S_OK;
}
_inBufMode = true;
_inBuffer.Init();
cdAbsOffset = m_Position - 4;
for (;;)
{
CItemEx cdItem;
RINOK(ReadCdItem(cdItem));
cdItems.Add(cdItem);
if (progress && cdItems.Size() % 1 == 0)
if (progress && (cdItems.Size() & 0xFFF) == 0)
RINOK(progress->SetCompletedCD(items.Size()));
m_Signature = ReadUInt32();
if (m_Signature != NSignature::kCentralFileHeader)
@@ -1183,6 +1196,7 @@ HRESULT CInArchive::ReadHeaders2(CObjectVector<CItemEx> &items, CProgressVirt *p
CEcd64 ecd64;
bool isZip64 = false;
UInt64 ecd64AbsOffset = m_Position - 4;
if (m_Signature == NSignature::kEcd64)
{
IsZip64 = isZip64 = true;
@@ -1213,6 +1227,7 @@ HRESULT CInArchive::ReadHeaders2(CObjectVector<CItemEx> &items, CProgressVirt *p
(!items.IsEmpty())))
return S_FALSE;
}
if (m_Signature == NSignature::kEcd64Locator)
{
if (!isZip64)
@@ -1224,6 +1239,7 @@ HRESULT CInArchive::ReadHeaders2(CObjectVector<CItemEx> &items, CProgressVirt *p
return S_FALSE;
m_Signature = ReadUInt32();
}
if (m_Signature != NSignature::kEcd)
return S_FALSE;
@@ -1323,6 +1339,7 @@ HRESULT CInArchive::ReadHeaders2(CObjectVector<CItemEx> &items, CProgressVirt *p
return S_OK;
}
HRESULT CInArchive::ReadHeaders(CObjectVector<CItemEx> &items, CProgressVirt *progress)
{
HRESULT res;

View File

@@ -3,8 +3,10 @@
#include "StdAfx.h"
#include "../../../../C/CpuArch.h"
#include "../../../../C/7zCrc.h"
#include "../../../Common/MyLinux.h"
#include "../../../Common/StringConvert.h"
#include "../Common/ItemNameUtils.h"
@@ -80,6 +82,30 @@ bool CExtraSubBlock::ExtractUnixTime(bool isCentral, unsigned index, UInt32 &res
return false;
}
bool CExtraBlock::GetNtfsTime(unsigned index, FILETIME &ft) const
{
FOR_VECTOR (i, SubBlocks)
{
const CExtraSubBlock &sb = SubBlocks[i];
if (sb.ID == NFileHeader::NExtraID::kNTFS)
return sb.ExtractNtfsTime(index, ft);
}
return false;
}
bool CExtraBlock::GetUnixTime(bool isCentral, unsigned index, UInt32 &res) const
{
FOR_VECTOR (i, SubBlocks)
{
const CExtraSubBlock &sb = SubBlocks[i];
if (sb.ID == NFileHeader::NExtraID::kUnixTime)
return sb.ExtractUnixTime(isCentral, index, res);
}
return false;
}
bool CLocalItem::IsDir() const
{
return NItemName::HasTailSlash(Name, GetCodePage());
@@ -89,12 +115,29 @@ bool CItem::IsDir() const
{
if (NItemName::HasTailSlash(Name, GetCodePage()))
return true;
Byte hostOS = GetHostOS();
if (Size == 0 && PackSize == 0 && !Name.IsEmpty() && Name.Back() == '\\')
{
// do we need to use CharPrevExA?
// .NET Framework 4.5 : System.IO.Compression::CreateFromDirectory() probably writes backslashes to headers?
// so we support that case
switch (hostOS)
{
case NHostOS::kFAT:
case NHostOS::kNTFS:
case NHostOS::kHPFS:
case NHostOS::kVFAT:
return true;
}
}
if (!FromCentral)
return false;
UInt16 highAttrib = (UInt16)((ExternalAttrib >> 16 ) & 0xFFFF);
Byte hostOS = GetHostOS();
switch (hostOS)
{
case NHostOS::kAMIGA:
@@ -158,4 +201,53 @@ bool CItem::GetPosixAttrib(UInt32 &attrib) const
return false;
}
void CItem::GetUnicodeString(UString &res, const AString &s, bool isComment, bool useSpecifiedCodePage, UINT codePage) const
{
bool isUtf8 = IsUtf8();
bool ignore_Utf8_Errors = true;
if (!isUtf8)
{
{
const unsigned id = isComment ?
NFileHeader::NExtraID::kIzUnicodeComment:
NFileHeader::NExtraID::kIzUnicodeName;
const CObjectVector<CExtraSubBlock> &subBlocks = GetMainExtra().SubBlocks;
FOR_VECTOR (i, subBlocks)
{
const CExtraSubBlock &sb = subBlocks[i];
if (sb.ID == id)
{
AString utf;
if (sb.ExtractIzUnicode(CrcCalc(s, s.Len()), utf))
if (ConvertUTF8ToUnicode(utf, res))
return;
break;
}
}
}
if (useSpecifiedCodePage)
isUtf8 = (codePage == CP_UTF8);
#ifdef _WIN32
else if (GetHostOS() == NFileHeader::NHostOS::kUnix)
{
/* Some ZIP archives in Unix use UTF-8 encoding without Utf8 flag in header.
We try to get name as UTF-8.
Do we need to do it in POSIX version also? */
isUtf8 = true;
ignore_Utf8_Errors = false;
}
#endif
}
if (isUtf8)
if (ConvertUTF8ToUnicode(s, res) || ignore_Utf8_Errors)
return;
MultiByteToUnicodeString2(res, s, useSpecifiedCodePage ? codePage : GetCodePage());
}
}}

View File

@@ -7,7 +7,6 @@
#include "../../../Common/MyBuffer.h"
#include "../../../Common/MyString.h"
#include "../../../Common/StringConvert.h"
#include "../../../Common/UTFConvert.h"
#include "ZipHeader.h"
@@ -28,6 +27,23 @@ struct CExtraSubBlock
bool ExtractNtfsTime(unsigned index, FILETIME &ft) const;
bool ExtractUnixTime(bool isCentral, unsigned index, UInt32 &res) const;
bool ExtractIzUnicode(UInt32 crc, AString &name) const
{
unsigned size = (unsigned)Data.Size();
if (size < 1 + 4)
return false;
const Byte *p = (const Byte *)Data;
if (p[0] > 1)
return false;
if (crc != GetUi32(p + 1))
return false;
size -= 5;
name.SetFrom_CalcLen((const char *)p + 5, size);
if (size != name.Len())
return false;
return CheckUTF8(name, false);
}
};
const unsigned k_WzAesExtra_Size = 7;
@@ -109,6 +125,8 @@ struct CStrongCryptoExtra
Flags = GetUi16(p + 6);
return (Format == 2);
}
bool CertificateIsUsed() const { return (Flags > 0x0001); }
};
struct CExtraBlock
@@ -155,27 +173,8 @@ struct CExtraBlock
}
*/
bool GetNtfsTime(unsigned index, FILETIME &ft) const
{
FOR_VECTOR (i, SubBlocks)
{
const CExtraSubBlock &sb = SubBlocks[i];
if (sb.ID == NFileHeader::NExtraID::kNTFS)
return sb.ExtractNtfsTime(index, ft);
}
return false;
}
bool GetUnixTime(bool isCentral, unsigned index, UInt32 &res) const
{
FOR_VECTOR (i, SubBlocks)
{
const CExtraSubBlock &sb = SubBlocks[i];
if (sb.ID == NFileHeader::NExtraID::kUnixTime)
return sb.ExtractUnixTime(isCentral, index, res);
}
return false;
}
bool GetNtfsTime(unsigned index, FILETIME &ft) const;
bool GetUnixTime(bool isCentral, unsigned index, UInt32 &res) const;
void RemoveUnknownSubBlocks()
{
@@ -272,45 +271,22 @@ public:
MadeByVersion.HostOS = 0;
}
const CExtraBlock &GetMainExtra() const { return *(FromCentral ? &CentralExtra : &LocalExtra); }
bool IsDir() const;
UInt32 GetWinAttrib() const;
bool GetPosixAttrib(UInt32 &attrib) const;
Byte GetHostOS() const { return FromCentral ? MadeByVersion.HostOS : ExtractVersion.HostOS; }
void GetUnicodeString(const AString &s, UString &res, bool useSpecifiedCodePage, UINT codePage) const
{
bool isUtf8 = IsUtf8();
bool ignore_Utf8_Errors = true;
#ifdef _WIN32
if (!isUtf8)
{
if (useSpecifiedCodePage)
isUtf8 = (codePage == CP_UTF8);
else if (GetHostOS() == NFileHeader::NHostOS::kUnix)
{
/* Some ZIP archives in Unix use UTF-8 encoding without Utf8 flag in header.
We try to get name as UTF-8.
Do we need to do it in POSIX version also? */
isUtf8 = true;
ignore_Utf8_Errors = false;
}
}
#endif
if (isUtf8)
if (ConvertUTF8ToUnicode(s, res) || ignore_Utf8_Errors)
return;
MultiByteToUnicodeString2(res, s, useSpecifiedCodePage ? codePage : GetCodePage());
}
void GetUnicodeString(UString &res, const AString &s, bool isComment, bool useSpecifiedCodePage, UINT codePage) const;
bool IsThereCrc() const
{
if (Method == NFileHeader::NCompressionMethod::kWzAES)
{
CWzAesExtra aesField;
if (CentralExtra.GetWzAes(aesField))
if (GetMainExtra().GetWzAes(aesField))
return aesField.NeedCrc();
}
return (Crc != 0 || !IsDir());
@@ -320,8 +296,10 @@ public:
{
Byte hostOS = GetHostOS();
return (UINT)((
hostOS == NFileHeader::NHostOS::kFAT ||
hostOS == NFileHeader::NHostOS::kNTFS) ? CP_OEMCP : CP_ACP);
hostOS == NFileHeader::NHostOS::kFAT
|| hostOS == NFileHeader::NHostOS::kNTFS
|| hostOS == NFileHeader::NHostOS::kUnix // do we need it?
) ? CP_OEMCP : CP_ACP);
}
};

View File

@@ -107,4 +107,4 @@ C_OBJS = \
!include "../../Aes.mak"
!include "../../Crc.mak"
!include "../../7zip.mak"
!include "../../7zip.mak"

View File

@@ -18,7 +18,6 @@ FILE_IO =FileIO
FILE_IO_2 =Windows/$(FILE_IO)
MT_FILES = \
System.o \
LzFindMt.o \
Threads.o \
@@ -60,6 +59,7 @@ OBJS = \
StringConvert.o \
StringToInt.o \
PropVariant.o \
System.o \
7zCrc.o \
7zCrcOpt.o \
Alloc.o \
@@ -150,10 +150,8 @@ StringToInt.o: ../../../Common/StringToInt.cpp
PropVariant.o: ../../../Windows/PropVariant.cpp
$(CXX) $(CFLAGS) ../../../Windows/PropVariant.cpp
ifdef MT_FILES
System.o: ../../../Windows/System.cpp
$(CXX) $(CFLAGS) ../../../Windows/System.cpp
endif
7zCrc.o: ../../../../C/7zCrc.c
$(CXX_C) $(CFLAGS) ../../../../C/7zCrc.c
@@ -195,4 +193,3 @@ Lzma86Enc.o: ../../../../C/Lzma86Enc.c
clean:
-$(RM) $(PROG) $(OBJS)

View File

@@ -325,14 +325,6 @@ SOURCE=..\..\UI\FileManager\ComboDialog.h
# End Source File
# Begin Source File
SOURCE=..\..\UI\FileManager\MessagesDialog.cpp
# End Source File
# Begin Source File
SOURCE=..\..\UI\FileManager\MessagesDialog.h
# End Source File
# Begin Source File
SOURCE=..\..\UI\FileManager\OverwriteDialog.cpp
# End Source File
# Begin Source File

View File

@@ -9,4 +9,4 @@
REGISTER_FILTER_E(7zAES,
NCrypto::N7z::CDecoder(),
NCrypto::N7z::CEncoder(),
0x6F10701, "7zAES")
0x6F10701, "7zAES")

View File

@@ -9,4 +9,4 @@
REGISTER_FILTER_E(AES256CBC,
NCrypto::CAesCbcDecoder(32),
NCrypto::CAesCbcEncoder(32),
0x6F00181, "AES256CBC")
0x6F00181, "AES256CBC")

View File

@@ -73,8 +73,10 @@ void CRandomGenerator::Init()
HASH_UPD(v2);
#endif
#ifdef _WIN32
DWORD tickCount = ::GetTickCount();
HASH_UPD(tickCount);
#endif
for (unsigned j = 0; j < 100; j++)
{

View File

@@ -112,25 +112,87 @@ HRESULT CDecoder::Init_and_CheckPassword(bool &passwOK)
if (algId * 64 + 128 != bitLen)
return E_NOTIMPL;
_key.KeySize = 16 + algId * 8;
if ((flags & 1) == 0)
return E_NOTIMPL;
bool cert = ((flags & 2) != 0);
if ((flags & 0x4000) != 0)
{
// Use 3DES
return E_NOTIMPL;
}
if (cert)
{
return E_NOTIMPL;
}
else
{
if ((flags & 1) == 0)
return E_NOTIMPL;
}
UInt32 rdSize = GetUi16(p + 8);
if ((rdSize & 0xF) != 0 || rdSize + 16 > _remSize)
return E_NOTIMPL;
memmove(p, p + 10, rdSize);
Byte *validData = p + rdSize + 16;
if (GetUi32(validData - 6) != 0) // reserved
return E_NOTIMPL;
UInt32 validSize = GetUi16(validData - 2);
if ((validSize & 0xF) != 0 || 16 + rdSize + validSize != _remSize)
if (rdSize + 16 > _remSize)
return E_NOTIMPL;
/*
if (cert)
{
// how to filter rd, if ((rdSize & 0xF) != 0) ?
/*
if ((rdSize & 0x7) != 0)
return E_NOTIMPL;
}
else
*/
{
if ((rdSize & 0xF) != 0)
return E_NOTIMPL;
}
memmove(p, p + 10, rdSize);
const Byte *p2 = p + rdSize + 10;
UInt32 reserved = GetUi32(p2);
p2 += 4;
/*
if (cert)
{
UInt32 numRecipients = reserved;
if (numRecipients == 0)
return E_NOTIMPL;
{
UInt32 hashAlg = GetUi16(p2);
hashAlg = hashAlg;
UInt32 hashSize = GetUi16(p2 + 2);
hashSize = hashSize;
p2 += 4;
reserved = reserved;
// return E_NOTIMPL;
for (unsigned r = 0; r < numRecipients; r++)
{
UInt32 specSize = GetUi16(p2);
p2 += 2;
p2 += specSize;
}
}
}
else
*/
{
if (reserved != 0)
return E_NOTIMPL;
}
UInt32 validSize = GetUi16(p2);
p2 += 2;
const size_t validOffset = p2 - p;
if ((validSize & 0xF) != 0 || validOffset + validSize != _remSize)
return E_NOTIMPL;
{
RINOK(SetKey(_key.MasterKey, _key.KeySize));
@@ -149,12 +211,14 @@ HRESULT CDecoder::Init_and_CheckPassword(bool &passwOK)
RINOK(SetKey(fileKey, _key.KeySize));
RINOK(SetInitVector(_iv, 16));
Init();
Filter(validData, validSize);
memmove(p, p + validOffset, validSize);
Filter(p, validSize);
if (validSize < 4)
return E_NOTIMPL;
validSize -= 4;
if (GetUi32(validData + validSize) != CrcCalc(validData, validSize))
if (GetUi32(p + validSize) != CrcCalc(p, validSize))
return S_OK;
passwOK = true;
return S_OK;

View File

@@ -248,7 +248,8 @@ HRESULT CProxyArc::Load(const CArc &arc, IProgress *progress)
unsigned len = 0;
bool isPtrName = false;
#ifdef MY_CPU_LE
#if defined(MY_CPU_LE) && defined(_WIN32)
// it works only if (sizeof(wchar_t) == 2)
if (arc.GetRawProps)
{
const void *p;

View File

@@ -271,7 +271,7 @@ static const unsigned kCommandIndex = 0;
static const char *kCannotFindListFile = "Cannot find listfile";
static const char *kIncorrectListFile = "Incorrect item in listfile.\nCheck charset encoding and -scs switch.";
static const char *kTerminalOutError = "I won't write compressed data to a terminal";
static const char *kSameTerminalError = "I won't write data and program's messages to same terminal";
static const char *kSameTerminalError = "I won't write data and program's messages to same stream";
static const char *kEmptyFilePath = "Empty file path";
static const char *kCannotFindArchive = "Cannot find archive";
@@ -917,7 +917,7 @@ void CArcCmdLineParser::Parse1(const UStringVector &commandStrings,
if (parser[NKey::kAffinity].ThereIs)
{
const UString &s = us2fs(parser[NKey::kAffinity].PostStrings[0]);
const UString &s = parser[NKey::kAffinity].PostStrings[0];
if (!s.IsEmpty())
{
UInt32 v = 0;
@@ -1219,8 +1219,26 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
if (isExtractGroupCommand)
{
if (options.StdOutMode && options.IsStdOutTerminal && options.IsStdErrTerminal)
throw CArcCmdLineException(kSameTerminalError);
if (options.StdOutMode)
{
if (
options.Number_for_Percents == k_OutStream_stdout
// || options.Number_for_Out == k_OutStream_stdout
// || options.Number_for_Errors == k_OutStream_stdout
||
(
(options.IsStdOutTerminal && options.IsStdErrTerminal)
&&
(
options.Number_for_Percents != k_OutStream_disabled
// || options.Number_for_Out != k_OutStream_disabled
// || options.Number_for_Errors != k_OutStream_disabled
)
)
)
throw CArcCmdLineException(kSameTerminalError);
}
if (parser[NKey::kOutputDir].ThereIs)
{
eo.OutputDir = us2fs(parser[NKey::kOutputDir].PostStrings[0]);
@@ -1293,8 +1311,18 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
if (updateOptions.StdOutMode && updateOptions.EMailMode)
throw CArcCmdLineException("stdout mode and email mode cannot be combined");
if (updateOptions.StdOutMode && options.IsStdOutTerminal)
throw CArcCmdLineException(kTerminalOutError);
if (updateOptions.StdOutMode)
{
if (options.IsStdOutTerminal)
throw CArcCmdLineException(kTerminalOutError);
if (options.Number_for_Percents == k_OutStream_stdout
|| options.Number_for_Out == k_OutStream_stdout
|| options.Number_for_Errors == k_OutStream_stdout)
throw CArcCmdLineException(kSameTerminalError);
}
if (updateOptions.StdInMode)
updateOptions.StdInFileName = parser[NKey::kStdIn].PostStrings.Front();

View File

@@ -451,32 +451,42 @@ static UString GetDirPrefixOf(const UString &src)
return s;
}
static bool IsSafePath(const UString &path)
#endif
bool IsSafePath(const UString &path)
{
if (NName::IsAbsolutePath(path))
return false;
UStringVector parts;
SplitPathToParts(path, parts);
int level = 0;
FOR_VECTOR(i, parts)
unsigned level = 0;
FOR_VECTOR (i, parts)
{
const UString &s = parts[i];
if (s.IsEmpty())
{
if (i == 0)
return false;
continue;
}
if (s == L".")
continue;
if (s == L"..")
{
if (level <= 0)
if (level == 0)
return false;
level--;
}
else
level++;
}
return level > 0;
}
#endif
bool CensorNode_CheckPath2(const NWildcard::CCensorNode &node, const CReadArcItem &item, bool &include)
{
@@ -1255,7 +1265,7 @@ if (askExtractMode == NArchive::NExtract::NAskMode::kExtract && !_testMode)
CReparseAttr attr;
if (!attr.Parse(data, data.Size()))
{
RINOK(SendMessageError("Internal error for symbolic link file", _item.Path));
RINOK(SendMessageError("Internal error for symbolic link file", us2fs(_item.Path)));
// return E_FAIL;
}
else

View File

@@ -73,18 +73,40 @@ struct CInFileStreamVol: public CInFileStream
}
};
// from ArchiveExtractCallback.cpp
bool IsSafePath(const UString &path);
STDMETHODIMP COpenCallbackImp::GetStream(const wchar_t *name, IInStream **inStream)
{
COM_TRY_BEGIN
*inStream = NULL;
if (_subArchiveMode)
return S_FALSE;
if (Callback)
{
RINOK(Callback->Open_CheckBreak());
}
UString name2 = name;
#ifndef _SFX
#ifdef _WIN32
name2.Replace(L'/', WCHAR_PATH_SEPARATOR);
#endif
// if (!allowAbsVolPaths)
if (!IsSafePath(name2))
return S_FALSE;
#endif
FString fullPath;
if (!NFile::NName::GetFullPath(_folderPrefix, us2fs(name), fullPath))
if (!NFile::NName::GetFullPath(_folderPrefix, us2fs(name2), fullPath))
return S_FALSE;
if (!_fileInfo.Find(fullPath))
return S_FALSE;
@@ -93,10 +115,15 @@ STDMETHODIMP COpenCallbackImp::GetStream(const wchar_t *name, IInStream **inStre
CInFileStreamVol *inFile = new CInFileStreamVol;
CMyComPtr<IInStream> inStreamTemp = inFile;
if (!inFile->Open(fullPath))
return ::GetLastError();
{
DWORD lastError = ::GetLastError();
if (lastError == 0)
return E_FAIL;
return HRESULT_FROM_WIN32(lastError);
}
FileSizes.Add(_fileInfo.Size);
FileNames.Add(name);
FileNames.Add(name2);
inFile->FileNameIndex = FileNames_WasUsed.Add(true);
inFile->OpenCallbackImp = this;
inFile->OpenCallbackRef = this;

View File

@@ -32,9 +32,7 @@
#include "../../../../C/Alloc.h"
#include "../../../../C/CpuArch.h"
#if defined(_WIN32)
#include "../../../Windows/System.h"
#endif
#ifndef _7ZIP_ST
#include "../../../Windows/Synchronization.h"
@@ -1860,11 +1858,15 @@ static void PrintTotals(IBenchPrintCallback &f, bool showFreq, UInt64 cpuFreq, c
PrintResults(f, res.Usage / numIterations2, res.RPU / numIterations2, res.Rating / numIterations2, showFreq, cpuFreq);
}
static void PrintRequirements(IBenchPrintCallback &f, const char *sizeString, UInt64 size, const char *threadsString, UInt32 numThreads)
static void PrintRequirements(IBenchPrintCallback &f, const char *sizeString,
bool size_Defined, UInt64 size, const char *threadsString, UInt32 numThreads)
{
f.Print("RAM ");
f.Print(sizeString);
PrintNumber(f, (size >> 20), 6);
if (size_Defined)
PrintNumber(f, (size >> 20), 6);
else
f.Print(" ?");
f.Print(" MB, # ");
f.Print(threadsString);
PrintNumber(f, numThreads, 3);
@@ -2450,15 +2452,13 @@ HRESULT Bench(
return S_FALSE;
UInt32 numCPUs = 1;
UInt64 ramSize = (UInt64)512 << 20;
UInt64 ramSize = (UInt64)(sizeof(size_t)) << 29;
#ifndef _7ZIP_ST
numCPUs = NSystem::GetNumberOfProcessors();
#endif
#if defined(_WIN32)
ramSize = NSystem::GetRamSize();
#endif
bool ramSize_Defined = NSystem::GetRamSize(ramSize);
UInt32 numThreadsSpecified = numCPUs;
@@ -2487,7 +2487,7 @@ HRESULT Bench(
#ifdef USE_WIN_FILE
NFile::NIO::CInFile file;
if (!file.Open(property.Value))
if (!file.Open(us2fs(property.Value)))
return E_INVALIDARG;
UInt64 len;
if (!file.GetLength(len))
@@ -2640,7 +2640,7 @@ HRESULT Bench(
{
printCallback->NewLine();
printCallback->NewLine();
PrintRequirements(*printCallback, "size: ", ramSize, "CPU hardware threads:", numCPUs);
PrintRequirements(*printCallback, "size: ", ramSize_Defined, ramSize, "CPU hardware threads:", numCPUs);
}
if (numThreadsSpecified < 1 || numThreadsSpecified > kNumThreadsMax)
@@ -2834,6 +2834,7 @@ HRESULT Bench(
dicSizeLog = (UInt64)1 << 20;
#endif
if (ramSize_Defined)
for (; dicSizeLog > kBenchMinDicLogSize; dicSizeLog--)
if (GetBenchMemoryUsage(numThreads, ((UInt32)1 << dicSizeLog), totalBenchMode) + (8 << 20) <= ramSize)
break;
@@ -2848,7 +2849,7 @@ HRESULT Bench(
}
}
PrintRequirements(f, "usage:", GetBenchMemoryUsage(numThreads, dict, totalBenchMode), "Benchmark threads: ", numThreads);
PrintRequirements(f, "usage:", true, GetBenchMemoryUsage(numThreads, dict, totalBenchMode), "Benchmark threads: ", numThreads);
f.NewLine();

View File

@@ -39,7 +39,7 @@
#endif
// increase it, if you need to support larger SFX stubs
static const UInt64 kMaxCheckStartPosition = 1 << 22;
static const UInt64 kMaxCheckStartPosition = 1 << 23;
/*
Open:

View File

@@ -142,14 +142,16 @@ void ConvertPropertyToShortString(char *dest, const PROPVARIANT &prop, PROPID pr
case kpidVa:
{
UInt64 v = 0;
if (ConvertPropVariantToUInt64(prop, v))
{
dest[0] = '0';
dest[1] = 'x';
ConvertUInt64ToHex(prop.ulVal, dest + 2);
return;
}
break;
if (prop.vt == VT_UI4)
v = prop.ulVal;
else if (prop.vt == VT_UI8)
v = (UInt64)prop.uhVal.QuadPart;
else
break;
dest[0] = '0';
dest[1] = 'x';
ConvertUInt64ToHex(v, dest + 2);
return;
}
}

View File

@@ -14,8 +14,10 @@ static int CompareStrings(const unsigned *p1, const unsigned *p2, void *param)
void SortFileNames(const UStringVector &strings, CUIntVector &indices)
{
unsigned numItems = strings.Size();
const unsigned numItems = strings.Size();
indices.ClearAndSetSize(numItems);
if (numItems == 0)
return;
unsigned *vals = &indices[0];
for (unsigned i = 0; i < numItems; i++)
vals[i] = i;

View File

@@ -17,5 +17,3 @@ void CTempFiles::Clear()
Paths.DeleteBack();
}
}

View File

@@ -757,4 +757,3 @@ void CArchiveUpdateCallback::InFileStream_On_Destroy(UINT_PTR val)
}
throw 20141125;
}

View File

@@ -92,6 +92,7 @@ void GetUpdatePairInfoList(
{
arcIndices.ClearAndSetSize(numArcItems);
if (numArcItems != 0)
{
unsigned *vals = &arcIndices[0];
for (unsigned i = 0; i < numArcItems; i++)

View File

@@ -17,7 +17,7 @@ FString GetWorkDir(const NWorkDir::CInfo &workDirInfo, const FString &path, FStr
{
NWorkDir::NMode::EEnum mode = workDirInfo.Mode;
#ifndef UNDER_CE
#if defined(_WIN32) && !defined(UNDER_CE)
if (workDirInfo.ForRemovableOnly)
{
mode = NWorkDir::NMode::kCurrent;

View File

@@ -42,6 +42,12 @@ static void Key_Get_BoolPair(CKey &key, LPCTSTR name, CBoolPair &b)
b.Def = (key.GetValue_IfOk(name, b.Val) == ERROR_SUCCESS);
}
static void Key_Get_BoolPair_true(CKey &key, LPCTSTR name, CBoolPair &b)
{
b.Val = true;
b.Def = (key.GetValue_IfOk(name, b.Val) == ERROR_SUCCESS);
}
namespace NExtract
{
@@ -112,9 +118,8 @@ void CInfo::Load()
OverwriteMode_Force = true;
}
Key_Get_BoolPair(key, kSplitDest, SplitDest);
if (!SplitDest.Def)
SplitDest.Val = true;
Key_Get_BoolPair_true(key, kSplitDest, SplitDest);
Key_Get_BoolPair(key, kElimDup, ElimDup);
// Key_Get_BoolPair(key, kAltStreams, AltStreams);
Key_Get_BoolPair(key, kNtSecur, NtSecurity);
@@ -348,27 +353,45 @@ void CInfo::Load()
static const TCHAR *kCascadedMenu = TEXT("CascadedMenu");
static const TCHAR *kContextMenu = TEXT("ContextMenu");
static const TCHAR *kMenuIcons = TEXT("MenuIcons");
static const TCHAR *kElimDup = TEXT("ElimDupExtract");
void CContextMenuInfo::Save() const
{
CS_LOCK
CKey key;
CreateMainKey(key, kOptionsInfoKeyName);
key.SetValue(kCascadedMenu, Cascaded);
key.SetValue(kMenuIcons, MenuIcons);
key.SetValue(kContextMenu, Flags);
Key_Set_BoolPair(key, kCascadedMenu, Cascaded);
Key_Set_BoolPair(key, kMenuIcons, MenuIcons);
Key_Set_BoolPair(key, kElimDup, ElimDup);
if (Flags_Def)
key.SetValue(kContextMenu, Flags);
}
void CContextMenuInfo::Load()
{
MenuIcons = false;
Cascaded = true;
Cascaded.Val = true;
Cascaded.Def = false;
MenuIcons.Val = false;
MenuIcons.Def = false;
ElimDup.Val = true;
ElimDup.Def = false;
Flags = (UInt32)(Int32)-1;
Flags_Def = false;
CS_LOCK
CKey key;
if (OpenMainKey(key, kOptionsInfoKeyName) != ERROR_SUCCESS)
return;
key.GetValue_IfOk(kCascadedMenu, Cascaded);
key.GetValue_IfOk(kMenuIcons, MenuIcons);
key.GetValue_IfOk(kContextMenu, Flags);
Key_Get_BoolPair_true(key, kCascadedMenu, Cascaded);
Key_Get_BoolPair_true(key, kElimDup, ElimDup);
Key_Get_BoolPair(key, kMenuIcons, MenuIcons);
Flags_Def = (key.GetValue_IfOk(kContextMenu, Flags) == ERROR_SUCCESS);
}

View File

@@ -111,8 +111,11 @@ namespace NWorkDir
struct CContextMenuInfo
{
bool Cascaded;
bool MenuIcons;
CBoolPair Cascaded;
CBoolPair MenuIcons;
CBoolPair ElimDup;
bool Flags_Def;
UInt32 Flags;
void Save() const;

View File

@@ -33,3 +33,4 @@ UI_COMMON_OBJS = \
$O\UpdatePair.obj \
$O\UpdateProduce.obj \
#

View File

@@ -4,11 +4,13 @@
#include "../../../Common/MyWindows.h"
#ifdef _WIN32
#include <Psapi.h>
#endif
#include "../../../../C/CpuArch.h"
#if defined( _WIN32) && defined( _7ZIP_LARGE_PAGES)
#if defined( _7ZIP_LARGE_PAGES)
#include "../../../../C/Alloc.h"
#endif
@@ -470,7 +472,7 @@ static void PrintHexId(CStdOutStream &so, UInt64 id)
int Main2(
#ifndef _WIN32
int numArgs, const char *args[]
int numArgs, char *args[]
#endif
)
{

View File

@@ -20,7 +20,7 @@ CStdOutStream *g_ErrStream = NULL;
extern int Main2(
#ifndef _WIN32
int numArgs, const char *args[]
int numArgs, char *args[]
#endif
);
@@ -49,7 +49,7 @@ static void PrintError(const char *message)
int MY_CDECL main
(
#ifndef _WIN32
int numArgs, const char *args[]
int numArgs, char *args[]
#endif
)
{

View File

@@ -241,7 +241,7 @@ static const CHashCommand g_HashCommands[] =
static int FindCommand(CZipContextMenu::ECommandInternalID &id)
{
for (int i = 0; i < ARRAY_SIZE(g_Commands); i++)
for (unsigned i = 0; i < ARRAY_SIZE(g_Commands); i++)
if (g_Commands[i].CommandInternalID == id)
return i;
return -1;
@@ -287,12 +287,10 @@ static const char * const kArcExts[] =
, "zip"
};
static bool IsItArcExt(const UString &ext2)
static bool IsItArcExt(const UString &ext)
{
UString ext = ext2;
ext.MakeLower_Ascii();
for (unsigned i = 0; i < ARRAY_SIZE(kArcExts); i++)
if (ext.IsEqualTo(kArcExts[i]))
if (ext.IsEqualTo_Ascii_NoCase(kArcExts[i]))
return true;
return false;
}
@@ -429,6 +427,7 @@ void CZipContextMenu::AddMapItem_ForSubMenu(const wchar_t *verb)
_commandMap.Add(commandMapItem);
}
STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
UINT commandIDFirst, UINT commandIDLast, UINT flags)
{
@@ -451,12 +450,15 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
CContextMenuInfo ci;
ci.Load();
_elimDup = ci.ElimDup;
HBITMAP bitmap = NULL;
if (ci.MenuIcons)
if (ci.MenuIcons.Val)
bitmap = _bitmap;
UINT subIndex = indexMenu;
if (ci.Cascaded)
if (ci.Cascaded.Val)
{
if (!popupMenu.CreatePopup())
return E_FAIL;
@@ -473,15 +475,21 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
else
{
popupMenu.Attach(hMenu);
CMenuItem mi;
mi.fType = MFT_SEPARATOR;
mi.fMask = MIIM_TYPE;
popupMenu.InsertItem(subIndex++, true, mi);
}
UInt32 contextMenuFlags = ci.Flags;
NFind::CFileInfo fi0;
FString folderPrefix;
if (_fileNames.Size() > 0)
{
const UString &fileName = _fileNames.Front();
#if defined(_WIN32) && !defined(UNDER_CE)
if (NName::IsDevicePath(us2fs(fileName)))
{
@@ -505,6 +513,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
}
UString mainString;
if (_fileNames.Size() == 1 && currentCommandID + 14 <= commandIDLast)
{
if (!fi0.IsDir() && DoNeedExtract(fi0.Name))
@@ -565,6 +574,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
if (_fileNames.Size() > 0 && currentCommandID + 10 <= commandIDLast)
{
bool needExtract = (!fi0.IsDir() && DoNeedExtract(fi0.Name));
if (!needExtract)
{
FOR_VECTOR (i, _fileNames)
@@ -579,7 +589,9 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
}
}
}
const UString &fileName = _fileNames.Front();
if (needExtract)
{
// Extract
@@ -629,6 +641,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
_commandMap.Add(commandMapItem);
}
// Test
if ((contextMenuFlags & NContextMenuFlags::kTest) != 0)
{
@@ -644,6 +657,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
arcName = CreateArchiveName(fi0, false);
else
arcName = CreateArchiveName(fileName, _fileNames.Size() > 1, false);
UString arcName7z = arcName + L".7z";
UString arcNameZip = arcName + L".zip";
@@ -745,7 +759,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
// PRB: Duplicate Menu Items In the File Menu For a Shell Context Menu Extension
// ID: Q214477
if (ci.Cascaded)
if (ci.Cascaded.Val)
{
CMenuItem mi;
mi.fType = MFT_STRING;
@@ -756,12 +770,20 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
mi.hSubMenu = popupMenu.Detach();
mi.StringValue.SetFromAscii("7-Zip"); // LangString(IDS_CONTEXT_POPUP_CAPTION);
mi.hbmpUnchecked = bitmap;
CMenu menu;
menu.Attach(hMenu);
menuDestroyer.Disable();
menu.InsertItem(indexMenu++, true, mi);
AddMapItem_ForSubMenu(kMainVerb);
}
else
{
popupMenu.Detach();
indexMenu = subIndex;
}
if (!_isMenuForFM &&
((contextMenuFlags & NContextMenuFlags::kCRC) != 0
@@ -771,6 +793,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
// CMenuDestroyer menuDestroyer_CRC;
UINT subIndex_CRC = 0;
if (subMenu.CreatePopup())
{
// menuDestroyer_CRC.Attach(subMenu);
@@ -783,13 +806,15 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
mi.hSubMenu = subMenu;
mi.StringValue.SetFromAscii("CRC SHA");
mi.hbmpUnchecked = bitmap;
CMenu menu;
menu.Attach(hMenu);
// menuDestroyer_CRC.Disable();
menu.InsertItem(indexMenu++, true, mi);
AddMapItem_ForSubMenu(kCheckSumCascadedVerb);
for (int i = 0; i < ARRAY_SIZE(g_HashCommands); i++)
for (unsigned i = 0; i < ARRAY_SIZE(g_HashCommands); i++)
{
const CHashCommand &hc = g_HashCommands[i];
CCommandMapItem commandMapItem;
@@ -799,6 +824,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
MyInsertMenu(subMenu, subIndex_CRC++, currentCommandID++, hc.UserName, bitmap);
_commandMap.Add(commandMapItem);
}
subMenu.Detach();
}
}
@@ -872,7 +898,7 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
{
ExtractArchives(_fileNames, commandMapItem.Folder,
(cmdID == kExtract), // showDialog
(cmdID == kExtractTo) // elimDup
(cmdID == kExtractTo) && _elimDup.Val // elimDup
);
break;
}
@@ -902,12 +928,14 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
_fileNames, email, showDialog, false);
break;
}
case kHash_CRC32:
case kHash_CRC64:
case kHash_SHA1:
case kHash_SHA256:
case kHash_All:
for (int i = 0; i < ARRAY_SIZE(g_HashCommands); i++)
{
for (unsigned i = 0; i < ARRAY_SIZE(g_HashCommands); i++)
{
const CHashCommand &hc = g_HashCommands[i];
if (hc.CommandInternalID == cmdID)
@@ -917,6 +945,7 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
}
}
break;
}
}
}
catch(...)

View File

@@ -74,6 +74,8 @@ private:
HBITMAP _bitmap;
CBoolPair _elimDup;
HRESULT GetFileNames(LPDATAOBJECT dataObject, UStringVector &fileNames);
int FindVerb(const UString &verb);
bool FillCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &commandMapItem);

View File

@@ -10,13 +10,11 @@
#include "../../../Common/MyWindows.h"
#include <ShlGuid.h>
#include <OleCtl.h>
#include "../../../Common/MyInitGuid.h"
#include "../../../Common/ComTry.h"
#include "../../../Common/StringConvert.h"
#include "../../../Windows/DLL.h"
#include "../../../Windows/ErrorMsg.h"
@@ -24,11 +22,15 @@
#include "../../../Windows/Registry.h"
#include "../FileManager/IFolder.h"
#include "../FileManager/LangUtils.h"
#include "ContextMenu.h"
static LPCTSTR k_ShellExtName = TEXT("7-Zip Shell Extension");
static LPCTSTR k_Approved = TEXT("Software\\Microsoft\\Windows\\CurrentVersion\\Shell Extensions\\Approved");
// {23170F69-40C1-278A-1000-000100020000}
static LPCTSTR k_Clsid = TEXT("{23170F69-40C1-278A-1000-000100020000}");
DEFINE_GUID(CLSID_CZipContextMenu,
k_7zip_GUID_Data1,
k_7zip_GUID_Data2,
@@ -42,10 +44,6 @@ HWND g_HWND = 0;
LONG g_DllRefCount = 0; // Reference count of this DLL.
static LPCWSTR kShellExtName = L"7-Zip Shell Extension";
static LPCTSTR kClsidMask = TEXT("CLSID\\%s");
static LPCTSTR kClsidInprocMask = TEXT("CLSID\\%s\\InprocServer32");
static LPCTSTR kApprovedKeyPath = TEXT("Software\\Microsoft\\Windows\\CurrentVersion\\Shell Extensions\\Approved");
// #define ODS(sz) OutputDebugString(L#sz)
@@ -77,7 +75,7 @@ STDMETHODIMP CShellExtClassFactory::CreateInstance(LPUNKNOWN pUnkOuter,
shellExt = new CZipContextMenu();
}
catch(...) { return E_OUTOFMEMORY; }
if (shellExt == NULL)
if (!shellExt)
return E_OUTOFMEMORY;
HRESULT res = shellExt->QueryInterface(riid, ppvObj);
@@ -117,7 +115,7 @@ BOOL WINAPI DllMain(
return TRUE;
}
/////////////////////////////////////////////////////////////////////////////
// Used to determine whether the DLL can be unloaded by OLE
STDAPI DllCanUnloadNow(void)
@@ -138,7 +136,7 @@ STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID* ppv)
cf = new CShellExtClassFactory;
}
catch(...) { return E_OUTOFMEMORY; }
if (cf == 0)
if (!cf)
return E_OUTOFMEMORY;
HRESULT res = cf->QueryInterface(riid, ppv);
if (res != S_OK)
@@ -149,66 +147,28 @@ STDAPI DllGetClassObject(REFCLSID rclsid, REFIID riid, LPVOID* ppv)
// return _Module.GetClassObject(rclsid, riid, ppv);
}
static BOOL GetStringFromIID(CLSID clsid, LPTSTR s, int size)
{
LPWSTR pwsz;
if (StringFromIID(clsid, &pwsz) != S_OK)
return FALSE;
if (!pwsz)
return FALSE;
#ifdef UNICODE
for (int i = 0; i < size; i++)
{
s[i] = pwsz[i];
if (pwsz[i] == 0)
break;
}
s[size - 1] = 0;
#else
WideCharToMultiByte(CP_ACP, 0, pwsz, -1, s, size, NULL, NULL);
#endif
CoTaskMemFree(pwsz);
s[size - 1] = 0;
return TRUE;
}
typedef struct
static BOOL RegisterServer()
{
HKEY hRootKey;
LPCTSTR SubKey;
LPCWSTR ValueName;
LPCWSTR Data;
} CRegItem;
static BOOL RegisterServer(CLSID clsid, LPCWSTR title)
{
TCHAR clsidString[MAX_PATH];
if (!GetStringFromIID(clsid, clsidString, MAX_PATH))
return FALSE;
FString modulePath;
if (!NDLL::MyGetModuleFileName(modulePath))
return FALSE;
UString modulePathU = fs2us(modulePath);
const UString modulePathU = fs2us(modulePath);
CRegItem clsidEntries[] =
{
HKEY_CLASSES_ROOT, kClsidMask, NULL, title,
HKEY_CLASSES_ROOT, kClsidInprocMask, NULL, modulePathU,
HKEY_CLASSES_ROOT, kClsidInprocMask, L"ThreadingModel", L"Apartment",
NULL, NULL, NULL, NULL
};
CSysString clsidString = k_Clsid;
CSysString s = TEXT("CLSID\\");
s += clsidString;
//register the CLSID entries
for (int i = 0; clsidEntries[i].hRootKey; i++)
{
TCHAR subKey[MAX_PATH];
const CRegItem &r = clsidEntries[i];
wsprintf(subKey, r.SubKey, clsidString);
NRegistry::CKey key;
if (key.Create(r.hRootKey, subKey, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) != NOERROR)
if (key.Create(HKEY_CLASSES_ROOT, s, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) != NOERROR)
return FALSE;
key.SetValue(clsidEntries[i].ValueName, clsidEntries[i].Data);
key.SetValue(NULL, k_ShellExtName);
NRegistry::CKey keyInproc;
if (keyInproc.Create(key, TEXT("InprocServer32"), NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) != NOERROR)
return FALSE;
keyInproc.SetValue(NULL, modulePathU);
keyInproc.SetValue(TEXT("ThreadingModel"), TEXT("Apartment"));
}
#if !defined(_WIN64) && !defined(UNDER_CE)
@@ -216,46 +176,45 @@ static BOOL RegisterServer(CLSID clsid, LPCWSTR title)
#endif
{
NRegistry::CKey key;
if (key.Create(HKEY_LOCAL_MACHINE, kApprovedKeyPath, NULL,
REG_OPTION_NON_VOLATILE, KEY_WRITE) == NOERROR)
key.SetValue(GetUnicodeString(clsidString), title);
if (key.Create(HKEY_LOCAL_MACHINE, k_Approved, NULL, REG_OPTION_NON_VOLATILE, KEY_WRITE) == NOERROR)
key.SetValue(clsidString, k_ShellExtName);
}
return TRUE;
}
STDAPI DllRegisterServer(void)
{
return RegisterServer(CLSID_CZipContextMenu, kShellExtName) ? S_OK: SELFREG_E_CLASS;
return RegisterServer() ? S_OK: SELFREG_E_CLASS;
}
static BOOL UnregisterServer(CLSID clsid)
static BOOL UnregisterServer()
{
TCHAR clsidString[MAX_PATH];
if (!GetStringFromIID(clsid, clsidString, MAX_PATH))
return FALSE;
const CSysString clsidString = k_Clsid;
CSysString s = TEXT("CLSID\\");
s += clsidString;
CSysString s2 = s;
s2.AddAscii("\\InprocServer32");
TCHAR subKey[MAX_PATH];
wsprintf(subKey, kClsidInprocMask, clsidString);
RegDeleteKey(HKEY_CLASSES_ROOT, subKey);
wsprintf (subKey, kClsidMask, clsidString);
RegDeleteKey(HKEY_CLASSES_ROOT, subKey);
RegDeleteKey(HKEY_CLASSES_ROOT, s2);
RegDeleteKey(HKEY_CLASSES_ROOT, s);
#if !defined(_WIN64) && !defined(UNDER_CE)
if (IsItWindowsNT())
#endif
{
HKEY hKey;
if (RegOpenKeyEx(HKEY_LOCAL_MACHINE, kApprovedKeyPath, 0, KEY_SET_VALUE, &hKey) == NOERROR)
if (RegOpenKeyEx(HKEY_LOCAL_MACHINE, k_Approved, 0, KEY_SET_VALUE, &hKey) == NOERROR)
{
RegDeleteValue(hKey, clsidString);
RegCloseKey(hKey);
}
}
return TRUE;
}
STDAPI DllUnregisterServer(void)
{
return UnregisterServer(CLSID_CZipContextMenu) ? S_OK: SELFREG_E_CLASS;
return UnregisterServer() ? S_OK: SELFREG_E_CLASS;
}

View File

@@ -538,13 +538,5 @@ SOURCE=".\7-zip.dll.manifest"
SOURCE=.\ContextMenuFlags.h
# End Source File
# Begin Source File
SOURCE=.\RegistryContextMenu.cpp
# End Source File
# Begin Source File
SOURCE=.\RegistryContextMenu.h
# End Source File
# End Target
# End Project

View File

@@ -2,114 +2,218 @@
#include "StdAfx.h"
#include "../../../Common/StringConvert.h"
#include "../../../Windows/Registry.h"
#include "../../../Windows/Synchronization.h"
#include "RegistryContextMenu.h"
using namespace NWindows;
using namespace NRegistry;
namespace NZipRootRegistry {
#ifndef UNDER_CE
static NSynchronization::CCriticalSection g_CS;
static const TCHAR *kContextMenuKeyName = TEXT("\\shellex\\ContextMenuHandlers\\7-Zip");
static const TCHAR *kDragDropMenuKeyName = TEXT("\\shellex\\DragDropHandlers\\7-Zip");
// does extension can work, if Approved is removed ?
// CLISID (and Approved ?) items are separated for 32-bit and 64-bit code.
// shellex items shared by 32-bit and 64-bit code?
static const TCHAR *kExtensionCLSID = TEXT("{23170F69-40C1-278A-1000-000100020000}");
static LPCTSTR k_Clsid = TEXT("{23170F69-40C1-278A-1000-000100020000}");
static LPCTSTR k_ShellExtName = TEXT("7-Zip Shell Extension");
static const TCHAR *kRootKeyNameForFile = TEXT("*");
static const TCHAR *kRootKeyNameForFolder = TEXT("Folder");
static const TCHAR *kRootKeyNameForDirectory = TEXT("Directory");
static const TCHAR *kRootKeyNameForDrive = TEXT("Drive");
static LPCTSTR k_Approved = TEXT("Software\\Microsoft\\Windows\\CurrentVersion\\Shell Extensions\\Approved");
static LPCTSTR k_Inproc = TEXT("InprocServer32");
static CSysString GetFullContextMenuKeyName(const CSysString &keyName)
{ return (keyName + kContextMenuKeyName); }
static LPCTSTR k_KeyPostfix_ContextMenu = TEXT("\\shellex\\ContextMenuHandlers\\7-Zip");
static LPCTSTR k_KeyPostfix_DragDrop = TEXT("\\shellex\\DragDropHandlers\\7-Zip");
static CSysString GetFullDragDropMenuKeyName(const CSysString &keyName)
{ return (keyName + kDragDropMenuKeyName); }
static LPCTSTR k_KeyName_File = TEXT("*");
static LPCTSTR k_KeyName_Folder = TEXT("Folder");
static LPCTSTR k_KeyName_Directory = TEXT("Directory");
static LPCTSTR k_KeyName_Drive = TEXT("Drive");
static bool CheckHandlerCommon(const CSysString &keyName)
static LPCTSTR const k_shellex_Prefixes[] =
{
k_KeyName_File,
k_KeyName_Folder,
k_KeyName_Directory,
k_KeyName_Drive
};
static const bool k_shellex_Statuses[2][4] =
{
{ true, true, true, false },
{ false, false, true, true }
};
// can we use static RegDeleteKeyExW in _WIN64 mode?
// is it supported by Windows 2003 x64?
/*
#ifdef _WIN64
#define INIT_REG_WOW
#else
*/
typedef WINADVAPI LONG (APIENTRY *Func_RegDeleteKeyExW)(HKEY hKey, LPCWSTR lpSubKey, REGSAM samDesired, DWORD Reserved);
static Func_RegDeleteKeyExW func_RegDeleteKeyExW;
static void Init_RegDeleteKeyExW()
{
if (!func_RegDeleteKeyExW)
func_RegDeleteKeyExW = (Func_RegDeleteKeyExW)
GetProcAddress(GetModuleHandleW(L"advapi32.dll"), "RegDeleteKeyExW");
}
#define INIT_REG_WOW if (wow != 0) Init_RegDeleteKeyExW();
// #endif
static LONG MyRegistry_DeleteKey(HKEY parentKey, LPCTSTR name, UInt32 wow)
{
if (wow == 0)
return RegDeleteKey(parentKey, name);
/*
#ifdef _WIN64
return RegDeleteKeyExW
#else
*/
if (!func_RegDeleteKeyExW)
return E_NOTIMPL;
return func_RegDeleteKeyExW
// #endif
(parentKey, GetUnicodeString(name), wow, 0);
}
static LONG MyRegistry_DeleteKey_HKCR(LPCTSTR name, UInt32 wow)
{
return MyRegistry_DeleteKey(HKEY_CLASSES_ROOT, name, wow);
}
// static NSynchronization::CCriticalSection g_CS;
static CSysString Get_ContextMenuHandler_KeyName(const CSysString &keyName)
{ return (keyName + k_KeyPostfix_ContextMenu); }
/*
static CSysString Get_DragDropHandler_KeyName(const CSysString &keyName)
{ return (keyName + k_KeyPostfix_DragDrop); }
*/
static bool CheckHandlerCommon(const CSysString &keyName, UInt32 wow)
{
NSynchronization::CCriticalSectionLock lock(g_CS);
CKey key;
if (key.Open(HKEY_CLASSES_ROOT, keyName, KEY_READ) != ERROR_SUCCESS)
if (key.Open(HKEY_CLASSES_ROOT, keyName, KEY_READ | wow) != ERROR_SUCCESS)
return false;
CSysString value;
if (key.QueryValue(NULL, value) != ERROR_SUCCESS)
return false;
return StringsAreEqualNoCase_Ascii(value, kExtensionCLSID);
return StringsAreEqualNoCase_Ascii(value, k_Clsid);
}
bool CheckContextMenuHandler()
bool CheckContextMenuHandler(const UString &path, UInt32 wow)
{
// NSynchronization::CCriticalSectionLock lock(g_CS);
CSysString s = TEXT("CLSID\\");
s += k_Clsid;
s.AddAscii("\\InprocServer32");
{
NRegistry::CKey key;
if (key.Open(HKEY_CLASSES_ROOT, s, KEY_READ | wow) != ERROR_SUCCESS)
return false;
UString regPath;
if (key.QueryValue(NULL, regPath) != ERROR_SUCCESS)
return false;
if (!path.IsEqualTo_NoCase(regPath))
return false;
}
return
// CheckHandlerCommon(GetFullContextMenuKeyName(kRootKeyNameForFolder)) &&
CheckHandlerCommon(GetFullContextMenuKeyName(kRootKeyNameForDirectory)) &&
CheckHandlerCommon(GetFullContextMenuKeyName(kRootKeyNameForFile)) &&
CheckHandlerCommon(GetFullDragDropMenuKeyName(kRootKeyNameForDirectory)) &&
CheckHandlerCommon(GetFullDragDropMenuKeyName(kRootKeyNameForDrive));
CheckHandlerCommon(Get_ContextMenuHandler_KeyName(k_KeyName_File), wow);
/*
&& CheckHandlerCommon(Get_ContextMenuHandler_KeyName(k_KeyName_Directory), wow)
// && CheckHandlerCommon(Get_ContextMenuHandler_KeyName(k_KeyName_Folder))
&& CheckHandlerCommon(Get_DragDropHandler_KeyName(k_KeyName_Directory), wow)
&& CheckHandlerCommon(Get_DragDropHandler_KeyName(k_KeyName_Drive), wow);
*/
}
static void DeleteContextMenuHandlerCommon(const CSysString &keyName)
static LONG MyCreateKey(CKey &key, HKEY parentKey, LPCTSTR keyName, UInt32 wow)
{
CKey rootKey;
rootKey.Attach(HKEY_CLASSES_ROOT);
rootKey.RecurseDeleteKey(GetFullContextMenuKeyName(keyName));
rootKey.Detach();
return key.Create(parentKey, keyName, REG_NONE,
REG_OPTION_NON_VOLATILE, KEY_ALL_ACCESS | wow);
}
static void DeleteDragDropMenuHandlerCommon(const CSysString &keyName)
LONG SetContextMenuHandler(bool setMode, const UString &path, UInt32 wow)
{
CKey rootKey;
rootKey.Attach(HKEY_CLASSES_ROOT);
rootKey.RecurseDeleteKey(GetFullDragDropMenuKeyName(keyName));
rootKey.Detach();
}
// NSynchronization::CCriticalSectionLock lock(g_CS);
void DeleteContextMenuHandler()
{
DeleteContextMenuHandlerCommon(kRootKeyNameForFile);
DeleteContextMenuHandlerCommon(kRootKeyNameForFolder);
DeleteContextMenuHandlerCommon(kRootKeyNameForDirectory);
DeleteContextMenuHandlerCommon(kRootKeyNameForDrive);
DeleteDragDropMenuHandlerCommon(kRootKeyNameForFile);
DeleteDragDropMenuHandlerCommon(kRootKeyNameForFolder);
DeleteDragDropMenuHandlerCommon(kRootKeyNameForDirectory);
DeleteDragDropMenuHandlerCommon(kRootKeyNameForDrive);
}
INIT_REG_WOW
static void AddContextMenuHandlerCommon(const CSysString &keyName)
{
DeleteContextMenuHandlerCommon(keyName);
NSynchronization::CCriticalSectionLock lock(g_CS);
CKey key;
key.Create(HKEY_CLASSES_ROOT, GetFullContextMenuKeyName(keyName));
key.SetValue(NULL, kExtensionCLSID);
}
CSysString s = TEXT("CLSID\\");
s += k_Clsid;
static void AddDragDropMenuHandlerCommon(const CSysString &keyName)
{
DeleteDragDropMenuHandlerCommon(keyName);
NSynchronization::CCriticalSectionLock lock(g_CS);
CKey key;
key.Create(HKEY_CLASSES_ROOT, GetFullDragDropMenuKeyName(keyName));
key.SetValue(NULL, kExtensionCLSID);
}
LONG res;
if (setMode)
{
{
CKey key;
res = MyCreateKey(key, HKEY_CLASSES_ROOT, s, wow);
if (res == ERROR_SUCCESS)
{
key.SetValue(NULL, k_ShellExtName);
CKey keyInproc;
res = MyCreateKey(keyInproc, key, k_Inproc, wow);
if (res == ERROR_SUCCESS)
{
res = keyInproc.SetValue(NULL, path);
keyInproc.SetValue(TEXT("ThreadingModel"), TEXT("Apartment"));
}
}
}
{
CKey key;
if (MyCreateKey(key, HKEY_LOCAL_MACHINE, k_Approved, wow) == ERROR_SUCCESS)
key.SetValue(k_Clsid, k_ShellExtName);
}
}
else
{
CSysString s2 = s;
s2.AddAscii("\\InprocServer32");
void AddContextMenuHandler()
{
AddContextMenuHandlerCommon(kRootKeyNameForFile);
// AddContextMenuHandlerCommon(kRootKeyNameForFolder);
AddContextMenuHandlerCommon(kRootKeyNameForDirectory);
MyRegistry_DeleteKey_HKCR(s2, wow);
res = MyRegistry_DeleteKey_HKCR(s, wow);
}
AddDragDropMenuHandlerCommon(kRootKeyNameForDirectory);
AddDragDropMenuHandlerCommon(kRootKeyNameForDrive);
// shellex items probably are shared beween 32-bit and 64-bit apps. So we don't delete items for delete operation.
if (setMode)
for (unsigned i = 0; i < 2; i++)
{
for (unsigned k = 0; k < ARRAY_SIZE(k_shellex_Prefixes); k++)
{
CSysString s = k_shellex_Prefixes[k];
s += (i == 0 ? k_KeyPostfix_ContextMenu : k_KeyPostfix_DragDrop);
if (k_shellex_Statuses[i][k])
{
CKey key;
MyCreateKey(key, HKEY_CLASSES_ROOT, s, wow);
key.SetValue(NULL, k_Clsid);
}
else
MyRegistry_DeleteKey_HKCR(s, wow);
}
}
return res;
}
#endif
}

View File

@@ -3,14 +3,11 @@
#ifndef __REGISTRY_CONTEXT_MENU_H
#define __REGISTRY_CONTEXT_MENU_H
namespace NZipRootRegistry {
#ifndef UNDER_CE
bool CheckContextMenuHandler();
void AddContextMenuHandler();
void DeleteContextMenuHandler();
#endif
}
bool CheckContextMenuHandler(const UString &path, UInt32 wow = 0);
LONG SetContextMenuHandler(bool setMode, const UString &path, UInt32 wow = 0);
#endif
#endif

View File

@@ -14,7 +14,6 @@ EXPLORER_OBJS = \
$O\DllExportsExplorer.obj \
$O\ContextMenu.obj \
$O\MyMessages.obj \
$O\RegistryContextMenu.obj \
COMMON_OBJS = \
$O\IntToString.obj \

View File

@@ -448,7 +448,7 @@ int PrintErrorMessage(const char *message, const char *text)
}
static void ReduceString(UString &s, unsigned size)
void ReduceString(UString &s, unsigned size)
{
if (s.Len() > size)
{

View File

@@ -190,6 +190,8 @@ int ShowLastErrorMessage();
bool WasEscPressed();
void ReduceString(UString &s, unsigned size);
}
#endif

View File

@@ -68,8 +68,17 @@ NResult::EEnum Execute(const CFileInfo &oldFileInfo, const CFileInfo &newFileInf
SetFileInfoStrings(oldFileInfo, oldFileInfoStrings);
SetFileInfoStrings(newFileInfo, newFileInfoStrings);
AString oldName = UnicodeStringToMultiByte(oldFileInfo.Name, CP_OEMCP);
AString newName = UnicodeStringToMultiByte(newFileInfo.Name, CP_OEMCP);
UString oldName2 = oldFileInfo.Name;
UString newName2 = newFileInfo.Name;
{
const unsigned maxNameLen = kXSize - 9 - 2;
ReduceString(oldName2, maxNameLen);
ReduceString(newName2, maxNameLen);
}
AString oldName = UnicodeStringToMultiByte(oldName2);
AString newName = UnicodeStringToMultiByte(newName2);
struct CInitDialogItem initItems[]={
{ DI_DOUBLEBOX, 3, 1, kXSize - 4, kYSize - 2, false, false, 0, false, NMessageID::kOverwriteTitle, NULL, NULL },

View File

@@ -3,11 +3,6 @@
#ifndef __STDAFX_H
#define __STDAFX_H
// #define _CRT_SECURE_NO_DEPRECATE
// #include <windows.h>
// #include <stdio.h>
#include "../../../Common/Common.h"
#endif

View File

@@ -72,17 +72,18 @@ void CApp::ReloadLang()
void CApp::SetListSettings()
{
bool showDots = ReadShowDots();
bool showRealFileIcons = ReadShowRealFileIcons();
CFmSettings st;
st.Load();
ShowSystemMenu = st.ShowSystemMenu;
DWORD extendedStyle = LVS_EX_HEADERDRAGDROP;
if (ReadFullRow())
if (st.FullRow)
extendedStyle |= LVS_EX_FULLROWSELECT;
if (ReadShowGrid())
if (st.ShowGrid)
extendedStyle |= LVS_EX_GRIDLINES;
bool mySelectionMode = ReadAlternativeSelection();
if (ReadSingleClick())
if (st.SingleClick)
{
extendedStyle |= LVS_EX_ONECLICKACTIVATE | LVS_EX_TRACKSELECT;
/*
@@ -91,16 +92,16 @@ void CApp::SetListSettings()
*/
}
for (int i = 0; i < kNumPanelsMax; i++)
for (unsigned i = 0; i < kNumPanelsMax; i++)
{
CPanel &panel = Panels[i];
panel._mySelectMode = mySelectionMode;
panel._showDots = showDots;
panel._showRealFileIcons = showRealFileIcons;
panel._mySelectMode = st.AlternativeSelection;
panel._showDots = st.ShowDots;
panel._showRealFileIcons = st.ShowRealFileIcons;
panel._exStyle = extendedStyle;
DWORD style = (DWORD)panel._listView.GetStyle();
if (mySelectionMode)
if (st.AlternativeSelection)
style |= LVS_SINGLESEL;
else
style &= ~LVS_SINGLESEL;
@@ -109,11 +110,6 @@ void CApp::SetListSettings()
}
}
void CApp::SetShowSystemMenu()
{
ShowSystemMenu = Read_ShowSystemMenu();
}
#ifndef ILC_COLOR32
#define ILC_COLOR32 0x0020
#endif
@@ -179,7 +175,7 @@ struct CButtonInfo
UString GetText() const { return LangString(StringResID); }
};
static CButtonInfo g_StandardButtons[] =
static const CButtonInfo g_StandardButtons[] =
{
{ IDM_COPY_TO, IDB_COPY, IDB_COPY2, IDS_BUTTON_COPY },
{ IDM_MOVE_TO, IDB_MOVE, IDB_MOVE2, IDS_BUTTON_MOVE },
@@ -187,16 +183,16 @@ static CButtonInfo g_StandardButtons[] =
{ IDM_PROPERTIES, IDB_INFO, IDB_INFO2, IDS_BUTTON_INFO }
};
static CButtonInfo g_ArchiveButtons[] =
static const CButtonInfo g_ArchiveButtons[] =
{
{ kMenuCmdID_Toolbar_Add, IDB_ADD, IDB_ADD2, IDS_ADD },
{ kMenuCmdID_Toolbar_Extract, IDB_EXTRACT, IDB_EXTRACT2, IDS_EXTRACT },
{ kMenuCmdID_Toolbar_Test, IDB_TEST, IDB_TEST2, IDS_TEST }
};
static bool SetButtonText(int commandID, CButtonInfo *buttons, int numButtons, UString &s)
static bool SetButtonText(int commandID, const CButtonInfo *buttons, unsigned numButtons, UString &s)
{
for (int i = 0; i < numButtons; i++)
for (unsigned i = 0; i < numButtons; i++)
{
const CButtonInfo &b = buttons[i];
if (b.CommandID == commandID)
@@ -218,7 +214,7 @@ static void SetButtonText(int commandID, UString &s)
static void AddButton(
NControl::CImageList &imageList,
NControl::CToolBar &toolBar,
CButtonInfo &butInfo, bool showText, bool large)
const CButtonInfo &butInfo, bool showText, bool large)
{
TBBUTTON but;
but.iBitmap = 0;
@@ -258,7 +254,7 @@ void CApp::ReloadToolbars()
if (ShowArchiveToolbar || ShowStandardToolbar)
{
CreateToolbar(_window, _buttonsImageList, _toolBar, LargeButtons);
int i;
unsigned i;
if (ShowArchiveToolbar)
for (i = 0; i < ARRAY_SIZE(g_ArchiveButtons); i++)
AddButton(_buttonsImageList, _toolBar, g_ArchiveButtons[i], ShowButtonsLables, LargeButtons);
@@ -282,10 +278,13 @@ void MyLoadMenu();
HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcFormat, int xSizes[2], bool &archiveIsOpened, bool &encrypted)
{
_window.Attach(hwnd);
#ifdef UNDER_CE
_commandBar.Create(g_hInstance, hwnd, 1);
#endif
MyLoadMenu();
#ifdef UNDER_CE
_commandBar.AutoSize();
#endif
@@ -298,14 +297,16 @@ HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcForma
PanelsCreated[i] = false;
AppState.Read();
SetListSettings();
SetShowSystemMenu();
if (LastFocusedPanel >= kNumPanelsMax)
LastFocusedPanel = 0;
// ShowDeletedFiles = Read_ShowDeleted();
CListMode listMode;
listMode.Read();
for (i = 0; i < kNumPanelsMax; i++)
{
CPanel &panel = Panels[i];
@@ -313,6 +314,7 @@ HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcForma
panel._xSize = xSizes[i];
panel._flatModeForArc = ReadFlatView(i);
}
for (i = 0; i < kNumPanelsMax; i++)
if (NumPanels > 1 || i == LastFocusedPanel)
{
@@ -328,6 +330,7 @@ HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcForma
encrypted = encrypted2;
}
}
SetFocusedPanel(LastFocusedPanel);
Panels[LastFocusedPanel].SetFocusToList();
return S_OK;
@@ -357,7 +360,8 @@ void CApp::Save()
{
AppState.Save();
CListMode listMode;
for (int i = 0; i < kNumPanelsMax; i++)
for (unsigned i = 0; i < kNumPanelsMax; i++)
{
const CPanel &panel = Panels[i];
UString path;
@@ -370,6 +374,7 @@ void CApp::Save()
listMode.Panels[i] = panel.GetListViewMode();
SaveFlatView(i, panel._flatModeForArc);
}
listMode.Save();
// Save_ShowDeleted(ShowDeletedFiles);
}
@@ -377,7 +382,7 @@ void CApp::Save()
void CApp::Release()
{
// It's for unloading COM dll's: don't change it.
for (int i = 0; i < kNumPanelsMax; i++)
for (unsigned i = 0; i < kNumPanelsMax; i++)
Panels[i].Release();
}
@@ -467,6 +472,7 @@ UString CPanel::GetItemsInfoString(const CRecordVector<UInt32> &indices)
UString info;
UInt64 numDirs, numFiles, filesSize, foldersSize;
numDirs = numFiles = filesSize = foldersSize = 0;
unsigned i;
for (i = 0; i < indices.Size(); i++)
{

View File

@@ -258,7 +258,6 @@ public:
*/
void SetListSettings();
void SetShowSystemMenu();
HRESULT SwitchOnOffOnePanel();
bool GetFlatMode() { return Panels[LastFocusedPanel].GetFlatMode(); }

View File

@@ -197,9 +197,11 @@ bool CBrowseDialog::OnInit()
#endif
#ifndef _SFX
if (ReadSingleClick())
CFmSettings st;
st.Load();
if (st.SingleClick)
_list.SetExtendedListViewStyle(LVS_EX_ONECLICKACTIVATE | LVS_EX_TRACKSELECT);
_showDots = ReadShowDots();
_showDots = st.ShowDots;
#endif
{
@@ -999,11 +1001,13 @@ bool CorrectFsPath(const UString &relBase, const UString &path2, UString &result
}
#else
bool CorrectFsPath(const UString & /* relBase */, const UString &path, UString &result)
{
result = path;
return true;
}
#endif
bool Dlg_CreateFolder(HWND wnd, UString &destName)

View File

@@ -27,48 +27,50 @@ static LPCWSTR kEditTopic = L"FM/options.htm#editor";
bool CEditPage::OnInit()
{
_initMode = true;
LangSetDlgItems(*this, kLangIDs, ARRAY_SIZE(kLangIDs));
LangSetDlgItems_Colon(*this, kLangIDs_Colon, ARRAY_SIZE(kLangIDs_Colon));
_viewer.Attach(GetItem(IDE_EDIT_VIEWER));
_editor.Attach(GetItem(IDE_EDIT_EDITOR));
_diff.Attach(GetItem(IDE_EDIT_DIFF));
_ctrls[0].Ctrl = IDE_EDIT_VIEWER; _ctrls[0].Button = IDB_EDIT_VIEWER;
_ctrls[1].Ctrl = IDE_EDIT_EDITOR; _ctrls[1].Button = IDB_EDIT_EDITOR;
_ctrls[2].Ctrl = IDE_EDIT_DIFF; _ctrls[2].Button = IDB_EDIT_DIFF;
for (unsigned i = 0; i < 3; i++)
{
CEditPageCtrl &c = _ctrls[i];
c.WasChanged = false;
c.Edit.Attach(GetItem(c.Ctrl));
UString path;
ReadRegEditor(false, path);
_viewer.SetText(path);
}
{
UString path;
ReadRegEditor(true, path);
_editor.SetText(path);
}
{
UString path;
ReadRegDiff(path);
_diff.SetText(path);
if (i < 2)
ReadRegEditor(i > 0, path);
else
ReadRegDiff(path);
c.Edit.SetText(path);
}
_initMode = false;
return CPropertyPage::OnInit();
}
LONG CEditPage::OnApply()
{
for (unsigned i = 0; i < 3; i++)
{
UString path;
_viewer.GetText(path);
SaveRegEditor(false, path);
}
{
UString path;
_editor.GetText(path);
SaveRegEditor(true, path);
}
{
UString path;
_diff.GetText(path);
SaveRegDiff(path);
CEditPageCtrl &c = _ctrls[i];
if (c.WasChanged)
{
UString path;
c.Edit.GetText(path);
if (i < 2)
SaveRegEditor(i > 0, path);
else
SaveRegDiff(path);
c.WasChanged = false;
}
}
return PSNRET_NOERROR;
}
@@ -91,24 +93,34 @@ static void Edit_BrowseForFile(NWindows::NControl::CEdit &edit, HWND hwnd)
bool CEditPage::OnButtonClicked(int buttonID, HWND buttonHWND)
{
switch (buttonID)
for (unsigned i = 0; i < 3; i++)
{
case IDB_EDIT_VIEWER: Edit_BrowseForFile(_viewer, *this); return true;
case IDB_EDIT_EDITOR: Edit_BrowseForFile(_editor, *this); return true;
case IDB_EDIT_DIFF: Edit_BrowseForFile(_diff, *this); return true;
CEditPageCtrl &c = _ctrls[i];
if (buttonID == c.Button)
{
Edit_BrowseForFile(c.Edit, *this);
return true;
}
}
return CPropertyPage::OnButtonClicked(buttonID, buttonHWND);
}
bool CEditPage::OnCommand(int code, int itemID, LPARAM param)
{
if (code == EN_CHANGE && (
itemID == IDE_EDIT_VIEWER ||
itemID == IDE_EDIT_EDITOR ||
itemID == IDE_EDIT_DIFF))
if (!_initMode && code == EN_CHANGE)
{
Changed();
return true;
for (unsigned i = 0; i < 3; i++)
{
CEditPageCtrl &c = _ctrls[i];
if (itemID == c.Ctrl)
{
c.WasChanged = true;
Changed();
return true;
}
}
}
return CPropertyPage::OnCommand(code, itemID, param);
}

View File

@@ -6,11 +6,19 @@
#include "../../../Windows/Control/PropertyPage.h"
#include "../../../Windows/Control/Edit.h"
struct CEditPageCtrl
{
NWindows::NControl::CEdit Edit;
bool WasChanged;
int Ctrl;
int Button;
};
class CEditPage: public NWindows::NControl::CPropertyPage
{
NWindows::NControl::CEdit _viewer;
NWindows::NControl::CEdit _editor;
NWindows::NControl::CEdit _diff;
CEditPageCtrl _ctrls[3];
bool _initMode;
public:
virtual bool OnInit();
virtual void OnNotifyHelp();

View File

@@ -42,6 +42,7 @@ using namespace NFind;
#define MENU_HEIGHT 26
bool g_RAM_Size_Defined;
UInt64 g_RAM_Size;
#ifdef _WIN32
@@ -323,42 +324,44 @@ static void GetCommands(const UString &aCommandLine, UString &aCommands)
}
*/
/*
#ifndef _WIN64
typedef BOOL (WINAPI *LPFN_ISWOW64PROCESS) (HANDLE, PBOOL);
#if defined(_WIN32) && !defined(_WIN64) && !defined(UNDER_CE)
static bool IsWow64()
bool g_Is_Wow64;
typedef BOOL (WINAPI *Func_IsWow64Process)(HANDLE, PBOOL);
static void Set_Wow64()
{
LPFN_ISWOW64PROCESS fnIsWow64Process = (LPFN_ISWOW64PROCESS)GetProcAddress(
GetModuleHandle("kernel32"), "IsWow64Process");
if (fnIsWow64Process == NULL)
return false;
BOOL isWow;
if (!fnIsWow64Process(GetCurrentProcess(),&isWow))
return false;
return isWow != FALSE;
g_Is_Wow64 = false;
Func_IsWow64Process fnIsWow64Process = (Func_IsWow64Process)GetProcAddress(
GetModuleHandleA("kernel32.dll"), "IsWow64Process");
if (fnIsWow64Process)
{
BOOL isWow;
if (fnIsWow64Process(GetCurrentProcess(), &isWow))
g_Is_Wow64 = (isWow != FALSE);
}
}
#endif
*/
bool IsLargePageSupported()
{
#ifdef _WIN64
return true;
#else
OSVERSIONINFO versionInfo;
versionInfo.dwOSVersionInfoSize = sizeof(versionInfo);
if (!::GetVersionEx(&versionInfo))
OSVERSIONINFO vi;
vi.dwOSVersionInfoSize = sizeof(vi);
if (!::GetVersionEx(&vi))
return false;
if (versionInfo.dwPlatformId != VER_PLATFORM_WIN32_NT || versionInfo.dwMajorVersion < 5)
if (vi.dwPlatformId != VER_PLATFORM_WIN32_NT)
return false;
if (versionInfo.dwMajorVersion > 5)
return true;
if (versionInfo.dwMinorVersion < 1)
return false;
if (versionInfo.dwMinorVersion > 1)
return true;
// return IsWow64();
if (vi.dwMajorVersion < 5) return false;
if (vi.dwMajorVersion > 5) return true;
if (vi.dwMinorVersion < 1) return false;
if (vi.dwMinorVersion > 1) return true;
// return g_Is_Wow64;
return false;
#endif
}
@@ -381,11 +384,11 @@ bool g_SymLink_Supported = false;
static void Set_SymLink_Supported()
{
g_SymLink_Supported = false;
OSVERSIONINFO versionInfo;
versionInfo.dwOSVersionInfoSize = sizeof(versionInfo);
if (!::GetVersionEx(&versionInfo))
OSVERSIONINFO vi;
vi.dwOSVersionInfoSize = sizeof(vi);
if (!::GetVersionEx(&vi))
return;
if (versionInfo.dwPlatformId != VER_PLATFORM_WIN32_NT || versionInfo.dwMajorVersion < 6)
if (vi.dwPlatformId != VER_PLATFORM_WIN32_NT || vi.dwMajorVersion < 6)
return;
g_SymLink_Supported = true;
// if (g_SymLink_Supported)
@@ -425,7 +428,7 @@ static void ErrorMessage(const wchar_t *s)
static int WINAPI WinMain2(int nCmdShow)
{
g_RAM_Size = NSystem::GetRamSize();
g_RAM_Size_Defined = NSystem::GetRamSize(g_RAM_Size);
#ifdef _WIN32
@@ -467,6 +470,11 @@ static int WINAPI WinMain2(int nCmdShow)
g_LVN_ITEMACTIVATE_Support = (g_ComCtl32Version >= MAKELONG(71, 4));
#endif
#if defined(_WIN32) && !defined(_WIN64) && !defined(UNDER_CE)
Set_Wow64();
#endif
g_IsSmallScreen = !NWindows::NControl::IsDialogSizeOK(200, 200);
// OleInitialize is required for drag and drop.
@@ -634,7 +642,15 @@ int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE /* hPrevInstance */,
try
{
return WinMain2(nCmdShow);
try
{
return WinMain2(nCmdShow);
}
catch (...)
{
g_ExitEventLauncher.Exit(true);
throw;
}
}
catch(const CNewException &)
{
@@ -854,15 +870,14 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
g_App.Save();
g_App.Release();
SaveWindowInfo(hWnd);
g_ExitEventLauncher.Exit(true);
PostQuitMessage(0);
break;
}
/*
case WM_MOVE:
{
break;
}
*/
// case WM_MOVE: break;
case WM_LBUTTONDOWN:
g_StartCaptureMousePos = LOWORD(lParam);
g_StartCaptureSplitterPos = g_Splitter.GetPos();
@@ -992,6 +1007,7 @@ void CApp::MoveSubWindows()
if (xSize == 0)
return;
int headerSize = 0;
#ifdef UNDER_CE
_commandBar.AutoSize();
{
@@ -999,6 +1015,7 @@ void CApp::MoveSubWindows()
headerSize += _commandBar.Height();
}
#endif
if (_toolBar)
{
_toolBar.AutoSize();
@@ -1008,6 +1025,7 @@ void CApp::MoveSubWindows()
#endif
headerSize += Window_GetRealHeight(_toolBar);
}
int ySize = MyMax((int)(rect.bottom - headerSize), 0);
if (NumPanels > 1)

View File

@@ -208,7 +208,6 @@ struct CCopyState
{
CProgressInfo ProgressInfo;
IFolderOperationsExtractCallback *Callback;
UInt64 TotalSize;
bool MoveMode;
bool UseReadWriteMode;
@@ -423,7 +422,7 @@ static HRESULT CopyFile_Ask(
NFsFolder::CCopyStateIO state2;
state2.Progress = state.Callback;
state2.DeleteSrcFile = state.MoveMode;
state2.TotalSize = state.TotalSize;
state2.TotalSize = state.ProgressInfo.TotalSize;
state2.StartPos = state.ProgressInfo.StartPos;
RINOK(state2.MyCopyFile(srcPath, destPathNew));
if (state2.ErrorFileIndex >= 0)
@@ -460,10 +459,10 @@ static HRESULT CopyFile_Ask(
}
else
{
if (state.TotalSize >= srcFileInfo.Size)
if (state.ProgressInfo.TotalSize >= srcFileInfo.Size)
{
state.TotalSize -= srcFileInfo.Size;
RINOK(state.ProgressInfo.Progress->SetTotal(state.TotalSize));
state.ProgressInfo.TotalSize -= srcFileInfo.Size;
RINOK(state.ProgressInfo.Progress->SetTotal(state.ProgressInfo.TotalSize));
}
}
return state.CallProgress();

View File

@@ -27,10 +27,13 @@ static const int kWorkModeButtons[] =
IDR_FOLDERS_WORK_SPECIFIED
};
static const int kNumWorkModeButtons = ARRAY_SIZE(kWorkModeButtons);
static const unsigned kNumWorkModeButtons = ARRAY_SIZE(kWorkModeButtons);
bool CFoldersPage::OnInit()
{
_initMode = true;
_needSave = false;
LangSetDlgItems(*this, kLangIDs, ARRAY_SIZE(kLangIDs));
m_WorkDirInfo.Load();
@@ -40,18 +43,18 @@ bool CFoldersPage::OnInit()
kWorkModeButtons[m_WorkDirInfo.Mode]);
m_WorkPath.Init(*this, IDE_FOLDERS_WORK_PATH);
m_ButtonSetWorkPath.Init(*this, IDB_FOLDERS_WORK_PATH);
m_WorkPath.SetText(fs2us(m_WorkDirInfo.Path));
MyEnableControls();
_initMode = false;
return CPropertyPage::OnInit();
}
int CFoldersPage::GetWorkMode() const
{
for (int i = 0; i < kNumWorkModeButtons; i++)
for (unsigned i = 0; i < kNumWorkModeButtons; i++)
if (IsButtonCheckedBool(kWorkModeButtons[i]))
return i;
throw 0;
@@ -61,7 +64,7 @@ void CFoldersPage::MyEnableControls()
{
bool enablePath = (GetWorkMode() == NWorkDir::NMode::kSpecified);
m_WorkPath.Enable(enablePath);
m_ButtonSetWorkPath.Enable(enablePath);
EnableItem(IDB_FOLDERS_WORK_PATH, enablePath);
}
void CFoldersPage::GetWorkDir(NWorkDir::CInfo &workDirInfo)
@@ -86,7 +89,11 @@ bool CFoldersPage::WasChanged()
void CFoldersPage::ModifiedEvent()
{
Changed();
if (!_initMode)
{
_needSave = true;
Changed();
}
/*
if (WasChanged())
Changed();
@@ -97,23 +104,25 @@ void CFoldersPage::ModifiedEvent()
bool CFoldersPage::OnButtonClicked(int buttonID, HWND buttonHWND)
{
for (int i = 0; i < kNumWorkModeButtons; i++)
for (unsigned i = 0; i < kNumWorkModeButtons; i++)
if (buttonID == kWorkModeButtons[i])
{
MyEnableControls();
ModifiedEvent();
return true;
}
switch (buttonID)
{
case IDB_FOLDERS_WORK_PATH:
OnFoldersWorkButtonPath();
break;
return true;
case IDX_FOLDERS_WORK_FOR_REMOVABLE:
break;
default:
return CPropertyPage::OnButtonClicked(buttonID, buttonHWND);
}
ModifiedEvent();
return true;
}
@@ -140,8 +149,12 @@ void CFoldersPage::OnFoldersWorkButtonPath()
LONG CFoldersPage::OnApply()
{
GetWorkDir(m_WorkDirInfo);
m_WorkDirInfo.Save();
if (_needSave)
{
GetWorkDir(m_WorkDirInfo);
m_WorkDirInfo.Save();
_needSave = false;
}
return PSNRET_NOERROR;
}

View File

@@ -10,11 +10,14 @@
class CFoldersPage : public NWindows::NControl::CPropertyPage
{
NWorkDir::CInfo m_WorkDirInfo;
NWindows::NControl::CDialogChildControl m_WorkPath;
bool _needSave;
bool _initMode;
void MyEnableControls();
void ModifiedEvent();
NWindows::NControl::CDialogChildControl m_WorkPath;
NWindows::NControl::CDialogChildControl m_ButtonSetWorkPath;
void OnFoldersWorkButtonPath();
int GetWorkMode() const;
void GetWorkDir(NWorkDir::CInfo &workDirInfo);

View File

@@ -84,14 +84,16 @@ bool CLangPage::OnInit()
}
if (!error.IsEmpty())
MessageBoxW(0, error, L"Error in Lang file", MB_OK | MB_ICONSTOP);
MessageBoxW(0, error, L"Error in Lang file", MB_ICONERROR);
return CPropertyPage::OnInit();
}
LONG CLangPage::OnApply()
{
int pathIndex = (int)_langCombo.GetItemData_of_CurSel();
SaveRegLang(_paths[pathIndex]);
if (_needSave)
SaveRegLang(_paths[pathIndex]);
_needSave = false;
ReloadLang();
LangWasChanged = true;
return PSNRET_NOERROR;
@@ -106,6 +108,7 @@ bool CLangPage::OnCommand(int code, int itemID, LPARAM param)
{
if (code == CBN_SELCHANGE && itemID == IDC_LANG_LANG)
{
_needSave = true;
Changed();
return true;
}

View File

@@ -10,10 +10,12 @@ class CLangPage: public NWindows::NControl::CPropertyPage
{
NWindows::NControl::CComboBox _langCombo;
UStringVector _paths;
bool _needSave;
public:
bool LangWasChanged;
CLangPage() { LangWasChanged = false; }
CLangPage(): _needSave(false), LangWasChanged(false) {}
virtual bool OnInit();
virtual void OnNotifyHelp();
virtual bool OnCommand(int code, int itemID, LPARAM param);

View File

@@ -140,13 +140,18 @@ void LangString_OnlyFromLangFile(UInt32 langID, UString &dest)
}
static const char *kLangs =
"ar.bg.ca.zh.-tw.-cn.cs.da.de.el.en.es.fi.fr.he.hu.is.it.ja.ko.nl.no.=nb.=nn."
"pl.pt.-br.rm.ro.ru.sr.=hr.-spl.-spc.sk.sq.sv.th.tr.ur.id.uk.be.sl.et.lv.lt.tg."
"fa.vi.hy.az.eu.hsb.mk...tn..xh.zu.af.ka.fo.hi.mt.se.ga."
".ms.kk.ky.sw.tk.uz.tt.bn.pa.-in.gu.or.ta.te.kn.ml.as.mr.sa.mn.=mn.=mng"
"bo.cy.kh.lo..gl.kok..sd.syr.si..iu.am.tzm.ks.ne.fy.ps.fil."
"dv...ha..yo.quz.nso.ba.lb.kl.ig...ti.....ii."
".arn..moh..br..ug.mi.oc.co.gsw.sah.qut.rw.wo....prs.";
"ar.bg.ca.zh.-tw.-cn.cs.da.de.el.en.es.fi.fr.he.hu.is."
"it.ja.ko.nl.no.=nb.=nn.pl.pt.-br.rm.ro.ru.sr.=hr.-spl.-spc.sk.sq.sv.th.tr."
"ur.id.uk.be.sl.et.lv.lt.tg.fa.vi.hy.az.eu.hsb.mk."
"st.ts.tn.ve.xh.zu.af.ka.fo.hi.mt.se.ga.yi.ms.kk."
"ky.sw.tk.uz.tt.bn.pa.-in.gu.or.ta.te.kn.ml.as.mr.sa."
"mn.=mn.=mng.bo.cy.kh.lo.my.gl.kok..sd.syr.si..iu.am.tzm."
"ks.ne.fy.ps.tl.dv..ff.ha..yo.qu.st.ba.lb.kl."
"ig.kr.om.ti.gn..la.so.ii..arn..moh..br.."
"ug.mi.oc.co."
// "gsw.sah.qut.rw.wo....prs...."
// ".gd."
;
static void FindShortNames(UInt32 primeLang, UStringVector &names)
{
@@ -158,10 +163,10 @@ static void FindShortNames(UInt32 primeLang, UStringVector &names)
bool isSub = (p[0] == '-' || p[0] == '=');
if (!isSub)
index++;
if (index > primeLang)
break;
if (index == primeLang)
if (index >= primeLang)
{
if (index > primeLang)
break;
UString s;
if (isSub)
{
@@ -178,6 +183,33 @@ static void FindShortNames(UInt32 primeLang, UStringVector &names)
}
}
/*
#include "../../../Common/IntToString.h"
static struct CC1Lang
{
CC1Lang()
{
for (int i = 1; i < 150; i++)
{
UString s;
char ttt[32];
ConvertUInt32ToHex(i, ttt);
s.AddAscii(ttt);
UStringVector names;
FindShortNames(i, names);
FOR_VECTOR (k, names)
{
s.Add_Space();
s += names[k];
}
OutputDebugStringW(s);
}
}
} g_cc1;
*/
// typedef LANGID (WINAPI *GetUserDefaultUILanguageP)();
static void OpenDefaultLang()

View File

@@ -18,7 +18,9 @@ bool CListViewDialog::OnInit()
#endif
_listView.Attach(GetItem(IDL_LISTVIEW));
if (ReadSingleClick())
CFmSettings st;
st.Load();
if (st.SingleClick)
_listView.SetExtendedListViewStyle(LVS_EX_ONECLICKACTIVATE | LVS_EX_TRACKSELECT);
SetText(Title);

View File

@@ -4,25 +4,34 @@
#include "../Common/ZipRegistry.h"
#include "../../../Windows/DLL.h"
#include "../../../Windows/ErrorMsg.h"
#include "../../../Windows/FileFind.h"
#include "../Explorer/ContextMenuFlags.h"
#include "../Explorer/RegistryContextMenu.h"
#include "../Explorer/resource.h"
#include "../FileManager/PropertyNameRes.h"
#include "../GUI/ExtractDialogRes.h"
#include "FormatUtils.h"
#include "HelpUtils.h"
#include "LangUtils.h"
#include "MenuPage.h"
#include "MenuPageRes.h"
#include "FormatUtils.h"
#include "../FileManager/PropertyNameRes.h"
using namespace NWindows;
using namespace NContextMenuFlags;
static const UInt32 kLangIDs[] =
{
IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU,
IDX_SYSTEM_INTEGRATE_TO_MENU,
IDX_SYSTEM_CASCADED_MENU,
IDX_SYSTEM_ICON_IN_MENU,
IDX_EXTRACT_ELIM_DUP,
IDT_SYSTEM_CONTEXT_MENU_ITEMS
};
@@ -34,64 +43,147 @@ struct CContextMenuItem
UInt32 Flag;
};
static CContextMenuItem kMenuItems[] =
static const CContextMenuItem kMenuItems[] =
{
{ IDS_CONTEXT_OPEN, kOpen},
{ IDS_CONTEXT_OPEN, kOpenAs},
{ IDS_CONTEXT_EXTRACT, kExtract},
{ IDS_CONTEXT_OPEN, kOpen },
{ IDS_CONTEXT_OPEN, kOpenAs },
{ IDS_CONTEXT_EXTRACT, kExtract },
{ IDS_CONTEXT_EXTRACT_HERE, kExtractHere },
{ IDS_CONTEXT_EXTRACT_TO, kExtractTo },
{ IDS_CONTEXT_TEST, kTest},
{ IDS_CONTEXT_TEST, kTest },
{ IDS_CONTEXT_COMPRESS, kCompress },
{ IDS_CONTEXT_COMPRESS_TO, kCompressTo7z },
{ IDS_CONTEXT_COMPRESS_TO, kCompressToZip }
{ IDS_CONTEXT_COMPRESS_TO, kCompressToZip },
#ifndef UNDER_CE
,
{ IDS_CONTEXT_COMPRESS_EMAIL, kCompressEmail },
{ IDS_CONTEXT_COMPRESS_TO_EMAIL, kCompressTo7zEmail },
{ IDS_CONTEXT_COMPRESS_TO_EMAIL, kCompressToZipEmail }
{ IDS_CONTEXT_COMPRESS_TO_EMAIL, kCompressToZipEmail },
#endif
, { IDS_PROP_CHECKSUM, kCRC }
{ IDS_PROP_CHECKSUM, kCRC }
};
#if !defined(_WIN64)
extern bool g_Is_Wow64;
#endif
bool CMenuPage::OnInit()
{
_initMode = true;
Clear_MenuChanged();
LangSetDlgItems(*this, kLangIDs, ARRAY_SIZE(kLangIDs));
#ifdef UNDER_CE
EnableItem(IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU, false);
HideItem(IDX_SYSTEM_INTEGRATE_TO_MENU);
HideItem(IDX_SYSTEM_INTEGRATE_TO_MENU_2);
#else
CheckButton(IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU, NZipRootRegistry::CheckContextMenuHandler());
{
UString s;
{
CWindow window(GetItem(IDX_SYSTEM_INTEGRATE_TO_MENU));
window.GetText(s);
}
UString bit64 = LangString(IDS_PROP_BIT64);
if (bit64.IsEmpty())
bit64.SetFromAscii("64-bit");
#ifdef _WIN64
bit64.Replace(L"64", L"32");
#endif
s.Add_Space();
s += L'(';
s += bit64;
s += L')';
SetItemText(IDX_SYSTEM_INTEGRATE_TO_MENU_2, s);
}
const FString prefix = NDLL::GetModuleDirPrefix();
_dlls[0].ctrl = IDX_SYSTEM_INTEGRATE_TO_MENU;
_dlls[1].ctrl = IDX_SYSTEM_INTEGRATE_TO_MENU_2;
_dlls[0].wow = 0;
_dlls[1].wow =
#ifdef _WIN64
KEY_WOW64_32KEY
#else
KEY_WOW64_64KEY
#endif
;
for (unsigned d = 0; d < 2; d++)
{
CShellDll &dll = _dlls[d];
dll.wasChanged = false;
#ifndef _WIN64
if (d != 0 && !g_Is_Wow64)
{
HideItem(dll.ctrl);
continue;
}
#endif
FString &path = dll.Path;
path = prefix;
path.AddAscii(d == 0 ? "7-zip.dll" :
#ifdef _WIN64
"7-zip32.dll"
#else
"7-zip64.dll"
#endif
);
if (!NFile::NFind::DoesFileExist(path))
{
path.Empty();
EnableItem(dll.ctrl, false);
}
else
{
dll.prevValue = CheckContextMenuHandler(fs2us(path), dll.wow);
CheckButton(dll.ctrl, dll.prevValue);
}
}
#endif
CContextMenuInfo ci;
ci.Load();
CheckButton(IDX_SYSTEM_CASCADED_MENU, ci.Cascaded);
CheckButton(IDX_SYSTEM_ICON_IN_MENU, ci.MenuIcons);
CheckButton(IDX_SYSTEM_CASCADED_MENU, ci.Cascaded.Val);
CheckButton(IDX_SYSTEM_ICON_IN_MENU, ci.MenuIcons.Val);
CheckButton(IDX_EXTRACT_ELIM_DUP, ci.ElimDup.Val);
_listView.Attach(GetItem(IDL_SYSTEM_OPTIONS));
UInt32 newFlags = LVS_EX_CHECKBOXES | LVS_EX_FULLROWSELECT;
const UInt32 newFlags = LVS_EX_CHECKBOXES | LVS_EX_FULLROWSELECT;
_listView.SetExtendedListViewStyle(newFlags, newFlags);
_listView.InsertColumn(0, L"", 100);
_listView.InsertColumn(0, L"", 200);
for (int i = 0; i < ARRAY_SIZE(kMenuItems); i++)
for (unsigned i = 0; i < ARRAY_SIZE(kMenuItems); i++)
{
CContextMenuItem &menuItem = kMenuItems[i];
const CContextMenuItem &menuItem = kMenuItems[i];
UString s = LangString(menuItem.ControlID);
if (menuItem.Flag == kCRC)
s = L"CRC SHA";
s.SetFromAscii("CRC SHA");
if (menuItem.Flag == kOpenAs ||
menuItem.Flag == kCRC)
s += L" >";
s.AddAscii(" >");
switch (menuItem.ControlID)
{
@@ -108,11 +200,11 @@ bool CMenuPage::OnInit()
{
case kCompressTo7z:
case kCompressTo7zEmail:
s2 += L".7z";
s2.AddAscii(".7z");
break;
case kCompressToZip:
case kCompressToZipEmail:
s2 += L".zip";
s2.AddAscii(".zip");
break;
}
s = MyFormatNew(s, s2);
@@ -126,39 +218,68 @@ bool CMenuPage::OnInit()
_listView.SetColumnWidthAuto(0);
_initMode = false;
return CPropertyPage::OnInit();
}
#ifndef UNDER_CE
STDAPI DllRegisterServer(void);
STDAPI DllUnregisterServer(void);
HWND g_MenuPageHWND = 0;
static void ShowMenuErrorMessage(const wchar_t *m, HWND hwnd)
{
MessageBoxW(hwnd, m, L"7-Zip", MB_ICONERROR);
}
#endif
LONG CMenuPage::OnApply()
{
#ifndef UNDER_CE
g_MenuPageHWND = *this;
if (IsButtonCheckedBool(IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU))
for (unsigned d = 2; d != 0;)
{
DllRegisterServer();
NZipRootRegistry::AddContextMenuHandler();
}
else
{
DllUnregisterServer();
NZipRootRegistry::DeleteContextMenuHandler();
d--;
CShellDll &dll = _dlls[d];
if (dll.wasChanged && !dll.Path.IsEmpty())
{
bool newVal = IsButtonCheckedBool(dll.ctrl);
LONG res = SetContextMenuHandler(newVal, fs2us(dll.Path), dll.wow);
if (res != ERROR_SUCCESS && (dll.prevValue != newVal || newVal))
ShowMenuErrorMessage(NError::MyFormatMessage(res), *this);
dll.prevValue = CheckContextMenuHandler(fs2us(dll.Path), dll.wow);
CheckButton(dll.ctrl, dll.prevValue);
dll.wasChanged = false;
}
}
#endif
CContextMenuInfo ci;
ci.Cascaded = IsButtonCheckedBool(IDX_SYSTEM_CASCADED_MENU);
ci.MenuIcons = IsButtonCheckedBool(IDX_SYSTEM_ICON_IN_MENU);
ci.Flags = 0;
for (int i = 0; i < ARRAY_SIZE(kMenuItems); i++)
if (_listView.GetCheckState(i))
ci.Flags |= kMenuItems[i].Flag;
ci.Save();
if (_cascaded_Changed || _menuIcons_Changed || _elimDup_Changed || _flags_Changed)
{
CContextMenuInfo ci;
ci.Cascaded.Val = IsButtonCheckedBool(IDX_SYSTEM_CASCADED_MENU);
ci.Cascaded.Def = _cascaded_Changed;
ci.MenuIcons.Val = IsButtonCheckedBool(IDX_SYSTEM_ICON_IN_MENU);
ci.MenuIcons.Def = _menuIcons_Changed;
ci.ElimDup.Val = IsButtonCheckedBool(IDX_EXTRACT_ELIM_DUP);
ci.ElimDup.Def = _elimDup_Changed;
ci.Flags = 0;
for (unsigned i = 0; i < ARRAY_SIZE(kMenuItems); i++)
if (_listView.GetCheckState(i))
ci.Flags |= kMenuItems[i].Flag;
ci.Flags_Def = _flags_Changed;
ci.Save();
Clear_MenuChanged();
}
// UnChanged();
return PSNRET_NOERROR;
}
@@ -172,14 +293,30 @@ bool CMenuPage::OnButtonClicked(int buttonID, HWND buttonHWND)
{
switch (buttonID)
{
case IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU:
case IDX_SYSTEM_CASCADED_MENU:
case IDX_SYSTEM_ICON_IN_MENU:
Changed();
return true;
}
return CPropertyPage::OnButtonClicked(buttonID, buttonHWND);
#ifndef UNDER_CE
case IDX_SYSTEM_INTEGRATE_TO_MENU:
case IDX_SYSTEM_INTEGRATE_TO_MENU_2:
{
for (unsigned d = 0; d < 2; d++)
{
CShellDll &dll = _dlls[d];
if (buttonID == dll.ctrl && !dll.Path.IsEmpty())
dll.wasChanged = true;
}
break;
}
#endif
case IDX_SYSTEM_CASCADED_MENU: _cascaded_Changed = true; break;
case IDX_SYSTEM_ICON_IN_MENU: _menuIcons_Changed = true; break;
case IDX_EXTRACT_ELIM_DUP: _elimDup_Changed = true; break;
default:
return CPropertyPage::OnButtonClicked(buttonID, buttonHWND);
}
Changed();
return true;
}
bool CMenuPage::OnNotify(UINT controlID, LPNMHDR lParam)
@@ -205,7 +342,10 @@ bool CMenuPage::OnItemChanged(const NMLISTVIEW *info)
UINT oldState = info->uOldState & LVIS_STATEIMAGEMASK;
UINT newState = info->uNewState & LVIS_STATEIMAGEMASK;
if (oldState != newState)
{
_flags_Changed = true;
Changed();
}
}
return true;
}

View File

@@ -6,11 +6,38 @@
#include "../../../Windows/Control/PropertyPage.h"
#include "../../../Windows/Control/ListView.h"
#include "../Common/LoadCodecs.h"
struct CShellDll
{
FString Path;
bool wasChanged;
bool prevValue;
int ctrl;
UInt32 wow;
CShellDll(): wasChanged (false), prevValue(false), ctrl(0), wow(0) {}
};
class CMenuPage: public NWindows::NControl::CPropertyPage
{
bool _initMode;
bool _cascaded_Changed;
bool _menuIcons_Changed;
bool _elimDup_Changed;
bool _flags_Changed;
void Clear_MenuChanged()
{
_cascaded_Changed = false;
_menuIcons_Changed = false;
_elimDup_Changed = false;
_flags_Changed = false;
}
#ifndef UNDER_CE
CShellDll _dlls[2];
#endif
NWindows::NControl::CListView _listView;
virtual bool OnInit();

View File

@@ -2,7 +2,7 @@
#include "../../GuiCommon.rc"
#define xc 240
#define yc 196
#define yc 224
IDD_MENU MY_PAGE
#include "MenuPage2.rc"

View File

@@ -1,12 +1,16 @@
#define y 54
#include "../GUI/ExtractDialogRes.h"
#define y 82
CAPTION "7-Zip"
BEGIN
CONTROL "Integrate 7-Zip to shell context menu", IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU, MY_CHECKBOX, m, m, xc, 10
CONTROL "Cascaded context menu", IDX_SYSTEM_CASCADED_MENU, MY_CHECKBOX, m, m + 14, xc, 10
CONTROL "Icons in context menu", IDX_SYSTEM_ICON_IN_MENU, MY_CHECKBOX, m, m + 28, xc, 10
CONTROL "Integrate 7-Zip to shell context menu", IDX_SYSTEM_INTEGRATE_TO_MENU, MY_CHECKBOX, m, m, xc, 10
CONTROL "(32-bit)", IDX_SYSTEM_INTEGRATE_TO_MENU_2, MY_CHECKBOX, m, m + 14, xc, 10
CONTROL "Cascaded context menu", IDX_SYSTEM_CASCADED_MENU, MY_CHECKBOX, m, m + 28, xc, 10
CONTROL "Icons in context menu", IDX_SYSTEM_ICON_IN_MENU, MY_CHECKBOX, m, m + 42, xc, 10
CONTROL "Eliminate duplication of root folder", IDX_EXTRACT_ELIM_DUP, MY_CHECKBOX, m, m + 56, xc, 10
LTEXT "Context menu items:", IDT_SYSTEM_CONTEXT_MENU_ITEMS, m, m + 42, xc, 8
LTEXT "Context menu items:", IDT_SYSTEM_CONTEXT_MENU_ITEMS, m, m + 70, xc, 8
CONTROL "List", IDL_SYSTEM_OPTIONS, "SysListView32",
LVS_REPORT | LVS_SINGLESEL | LVS_NOCOLUMNHEADER | WS_BORDER | WS_TABSTOP,
m, m + y, xc, yc - y

View File

@@ -1,9 +1,11 @@
#define IDD_MENU 2300
#define IDD_MENU_2 12300
#define IDX_SYSTEM_INTEGRATE_TO_CONTEXT_MENU 2301
#define IDX_SYSTEM_CASCADED_MENU 2302
#define IDT_SYSTEM_CONTEXT_MENU_ITEMS 2303
#define IDX_SYSTEM_ICON_IN_MENU 2304
#define IDX_SYSTEM_INTEGRATE_TO_MENU 2301
#define IDX_SYSTEM_CASCADED_MENU 2302
#define IDT_SYSTEM_CONTEXT_MENU_ITEMS 2303
#define IDX_SYSTEM_ICON_IN_MENU 2304
#define IDX_SYSTEM_INTEGRATE_TO_MENU_2 2310
#define IDL_SYSTEM_OPTIONS 100

View File

@@ -512,7 +512,8 @@ bool OnMenuCommand(HWND hWnd, int id)
// File
case IDCLOSE:
SendMessage(hWnd, WM_ACTIVATE, MAKEWPARAM(WA_INACTIVE, 0), (LPARAM)hWnd);
SendMessage (hWnd, WM_CLOSE, 0, 0);
g_ExitEventLauncher.Exit(false);
SendMessage(hWnd, WM_CLOSE, 0, 0);
break;
// Edit

View File

@@ -6,6 +6,7 @@
#include "../../../Windows/Control/PropertyPage.h"
#include "DialogSize.h"
#include "EditPage.h"
#include "EditPageRes.h"
#include "FoldersPage.h"
@@ -14,8 +15,6 @@
#include "LangPageRes.h"
#include "MenuPage.h"
#include "MenuPageRes.h"
// #include "PluginsPage.h"
// #include "PluginsPageRes.h"
#include "SettingsPage.h"
#include "SettingsPageRes.h"
#include "SystemPage.h"
@@ -29,90 +28,38 @@
using namespace NWindows;
#ifndef UNDER_CE
typedef UINT32 (WINAPI * DllRegisterServerPtr)();
extern HWND g_MenuPageHWND;
static void ShowMenuErrorMessage(const wchar_t *m)
{
MessageBoxW(g_MenuPageHWND, m, L"7-Zip", MB_ICONERROR);
}
static int DllRegisterServer2(const char *name)
{
NDLL::CLibrary lib;
FString prefix = NDLL::GetModuleDirPrefix();
if (!lib.Load(prefix + FTEXT("7-zip.dll")))
{
ShowMenuErrorMessage(L"7-Zip cannot load 7-zip.dll");
return E_FAIL;
}
DllRegisterServerPtr f = (DllRegisterServerPtr)lib.GetProc(name);
if (f == NULL)
{
ShowMenuErrorMessage(L"Incorrect plugin");
return E_FAIL;
}
HRESULT res = f();
if (res != S_OK)
ShowMenuErrorMessage(HResultToMessage(res));
return (int)res;
}
STDAPI DllRegisterServer(void)
{
#ifdef UNDER_CE
return S_OK;
#else
return DllRegisterServer2("DllRegisterServer");
#endif
}
STDAPI DllUnregisterServer(void)
{
#ifdef UNDER_CE
return S_OK;
#else
return DllRegisterServer2("DllUnregisterServer");
#endif
}
#endif
void OptionsDialog(HWND hwndOwner, HINSTANCE /* hInstance */)
{
CSystemPage systemPage;
// CPluginsPage pluginsPage;
CMenuPage menuPage;
CFoldersPage foldersPage;
CEditPage editPage;
CSettingsPage settingsPage;
CLangPage langPage;
CMenuPage menuPage;
CFoldersPage foldersPage;
CObjectVector<NControl::CPageInfo> pages;
BIG_DIALOG_SIZE(200, 200);
UINT pageIDs[] = {
const UINT pageIDs[] = {
SIZED_DIALOG(IDD_SYSTEM),
SIZED_DIALOG(IDD_MENU),
SIZED_DIALOG(IDD_FOLDERS),
SIZED_DIALOG(IDD_EDIT),
SIZED_DIALOG(IDD_SETTINGS),
SIZED_DIALOG(IDD_LANG) };
NControl::CPropertyPage *pagePinters[] = { &systemPage, &menuPage, &foldersPage, &editPage, &settingsPage, &langPage };
const int kNumPages = ARRAY_SIZE(pageIDs);
for (int i = 0; i < kNumPages; i++)
NControl::CPropertyPage *pagePointers[] = { &systemPage, &menuPage, &foldersPage, &editPage, &settingsPage, &langPage };
for (unsigned i = 0; i < ARRAY_SIZE(pageIDs); i++)
{
NControl::CPageInfo page;
NControl::CPageInfo &page = pages.AddNew();
page.ID = pageIDs[i];
LangString_OnlyFromLangFile(page.ID, page.Title);
page.Page = pagePinters[i];
pages.Add(page);
page.Page = pagePointers[i];
}
INT_PTR res = NControl::MyPropertySheet(pages, hwndOwner, LangString(IDS_OPTIONS));
if (res != -1 && res != 0)
{
if (langPage.LangWasChanged)
@@ -120,9 +67,10 @@ void OptionsDialog(HWND hwndOwner, HINSTANCE /* hInstance */)
// g_App._window.SetText(LangString(IDS_APP_TITLE, 0x03000000));
MyLoadMenu();
g_App.ReloadToolbars();
g_App.MoveSubWindows();
g_App.MoveSubWindows(); // we need it to change list window aafter _toolBar.AutoSize();
g_App.ReloadLang();
}
/*
if (systemPage.WasChanged)
{
@@ -130,8 +78,8 @@ void OptionsDialog(HWND hwndOwner, HINSTANCE /* hInstance */)
g_App.SysIconsWereChanged();
}
*/
g_App.SetListSettings();
g_App.SetShowSystemMenu();
g_App.RefreshAllPanels();
// ::PostMessage(hwndOwner, kLangWasChangedMessage, 0 , 0);
}

View File

@@ -69,31 +69,67 @@ struct CPanelCallback
void PanelCopyItems();
struct CItemProperty
struct CPropColumn
{
UString Name;
int Order;
PROPID ID;
VARTYPE Type;
int Order;
bool IsVisible;
bool IsRawProp;
UInt32 Width;
UString Name;
int Compare(const CItemProperty &a) const { return MyCompare(Order, a.Order); }
bool IsEqualTo(const CPropColumn &a) const
{
return Order == a.Order
&& ID == a.ID
&& Type == a.Type
&& IsVisible == a.IsVisible
&& IsRawProp == a.IsRawProp
&& Width == a.Width
&& Name == a.Name;
}
int Compare(const CPropColumn &a) const { return MyCompare(Order, a.Order); }
int Compare_NameFirst(const CPropColumn &a) const
{
if (ID == kpidName)
{
if (a.ID != kpidName)
return -1;
}
else if (a.ID == kpidName)
return 1;
return MyCompare(Order, a.Order);
}
};
class CItemProperties: public CObjectVector<CItemProperty>
class CPropColumns: public CObjectVector<CPropColumn>
{
public:
int FindItemWithID(PROPID id)
int FindItem_for_PropID(PROPID id) const
{
FOR_VECTOR (i, (*this))
if ((*this)[i].ID == id)
return i;
return -1;
}
bool IsEqualTo(const CPropColumns &props) const
{
if (Size() != props.Size())
return false;
FOR_VECTOR (i, (*this))
if (!(*this)[i].IsEqualTo(props[i]))
return false;
return true;
}
};
struct CTempFileInfo
{
UInt32 FileIndex; // index of file in folder
@@ -284,8 +320,8 @@ private:
void ChangeWindowSize(int xSize, int ySize);
HRESULT InitColumns();
// void InitColumns2(PROPID sortID);
void InsertColumn(unsigned index);
void DeleteColumn(unsigned index);
void AddColumn(const CPropColumn &prop);
void SetFocusedSelectedItem(int index, bool select);
HRESULT RefreshListCtrl(const UString &focusedName, int focusedPos, bool selectFocused,
@@ -446,7 +482,6 @@ public:
void SetFocusToLastRememberedItem();
void ReadListViewInfo();
void SaveListViewInfo();
CPanel() :
@@ -484,8 +519,9 @@ public:
bool _needSaveInfo;
UString _typeIDString;
CListViewInfo _listViewInfo;
CItemProperties _properties;
CItemProperties _visibleProperties;
CPropColumns _columns;
CPropColumns _visibleColumns;
PROPID _sortID;
// int _sortIndex;
@@ -805,4 +841,28 @@ public:
~CMyBuffer() { ::MidFree(_data); }
};
class CExitEventLauncher
{
public:
NWindows::NSynchronization::CManualResetEvent _exitEvent;
bool _needExit;
CRecordVector< ::CThread > _threads;
unsigned _numActiveThreads;
CExitEventLauncher()
{
_needExit = false;
if (_exitEvent.Create(false) != S_OK)
throw 9387173;
_needExit = true;
_numActiveThreads = 0;
};
~CExitEventLauncher() { Exit(true); }
void Exit(bool hardExit);
};
extern CExitEventLauncher g_ExitEventLauncher;
#endif

View File

@@ -209,7 +209,23 @@ STDMETHODIMP CDropSource::QueryContinueDrag(BOOL escapePressed, DWORD keyState)
{
CCopyToOptions options;
options.folder = Folder;
// 15.13: fixed problem with mouse cursor for password window.
// DoDragDrop() probably calls SetCapture() to some hidden window.
// But it's problem, if we show some modal window, like MessageBox.
// So we return capture to our window.
// If you know better way to solve the problem, please notify 7-Zip developer.
// MessageBoxW(*Panel, L"test", L"test", 0);
/* HWND oldHwnd = */ SetCapture(*Panel);
Result = Panel->CopyTo(options, Indices, &Messages);
// do we need to restore capture?
// ReleaseCapture();
// oldHwnd = SetCapture(oldHwnd);
if (Result != S_OK || !Messages.IsEmpty())
return DRAGDROP_S_CANCEL;
}
@@ -357,10 +373,14 @@ void CPanel::OnDrag(LPNMLISTVIEW /* nmListView */)
effectsOK |= DROPEFFECT_MOVE;
DWORD effect;
_panelCallback->DragBegin();
HRESULT res = DoDragDrop(dataObject, dropSource, effectsOK, &effect);
_panelCallback->DragEnd();
bool canceled = (res == DRAGDROP_S_CANCEL);
CDisableNotify disableNotify(*this);
if (res == DRAGDROP_S_DROP)
{
res = dropSourceSpec->Result;

Some files were not shown because too many files have changed in this diff Show More