mirror of
https://github.com/Xevion/easy7zip.git
synced 2025-12-06 15:14:59 -06:00
21.02
This commit is contained in:
@@ -27,8 +27,10 @@ CCodecs *g_CodecsObj;
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
CExternalCodecs g_ExternalCodecs;
|
||||
CCodecs::CReleaser g_CodecsReleaser;
|
||||
static CCodecs::CReleaser g_CodecsReleaser;
|
||||
#else
|
||||
extern
|
||||
CMyComPtr<IUnknown> g_CodecsRef;
|
||||
CMyComPtr<IUnknown> g_CodecsRef;
|
||||
#endif
|
||||
|
||||
@@ -1245,7 +1247,7 @@ STDMETHODIMP CAgentFolder::GetFolderProperty(PROPID propID, PROPVARIANT *value)
|
||||
// case kpidName: prop = dir.Name; break;
|
||||
// case kpidPath: prop = _proxy2->GetFullPathPrefix(_proxyDirIndex); break;
|
||||
case kpidType: prop = UString("7-Zip.") + _agentSpec->ArchiveType; break;
|
||||
case kpidCRC: if (dir.CrcIsDefined) prop = dir.Crc; break;
|
||||
case kpidCRC: if (dir.CrcIsDefined) { prop = dir.Crc; } break;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1533,8 +1535,8 @@ STDMETHODIMP CAgentFolder::Extract(const UInt32 *indices,
|
||||
CAgent::CAgent():
|
||||
_proxy(NULL),
|
||||
_proxy2(NULL),
|
||||
_isDeviceFile(false),
|
||||
_updatePathPrefix_is_AltFolder(false)
|
||||
_updatePathPrefix_is_AltFolder(false),
|
||||
_isDeviceFile(false)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -1611,24 +1613,30 @@ STDMETHODIMP CAgent::Open(
|
||||
options.filePath = _archiveFilePath;
|
||||
options.callback = openArchiveCallback;
|
||||
|
||||
RINOK(_archiveLink.Open(options));
|
||||
HRESULT res = _archiveLink.Open(options);
|
||||
|
||||
CArc &arc = _archiveLink.Arcs.Back();
|
||||
if (!inStream)
|
||||
if (!_archiveLink.Arcs.IsEmpty())
|
||||
{
|
||||
arc.MTimeDefined = !fi.IsDevice;
|
||||
arc.MTime = fi.MTime;
|
||||
CArc &arc = _archiveLink.Arcs.Back();
|
||||
if (!inStream)
|
||||
{
|
||||
arc.MTimeDefined = !fi.IsDevice;
|
||||
arc.MTime = fi.MTime;
|
||||
}
|
||||
|
||||
ArchiveType = GetTypeOfArc(arc);
|
||||
if (archiveType)
|
||||
{
|
||||
RINOK(StringToBstr(ArchiveType, archiveType));
|
||||
}
|
||||
}
|
||||
|
||||
ArchiveType = GetTypeOfArc(arc);
|
||||
if (archiveType)
|
||||
{
|
||||
RINOK(StringToBstr(ArchiveType, archiveType));
|
||||
}
|
||||
return S_OK;
|
||||
return res;
|
||||
|
||||
COM_TRY_END
|
||||
}
|
||||
|
||||
|
||||
STDMETHODIMP CAgent::ReOpen(IArchiveOpenCallback *openArchiveCallback)
|
||||
{
|
||||
COM_TRY_BEGIN
|
||||
@@ -1717,7 +1725,10 @@ HRESULT CAgent::ReadItems()
|
||||
STDMETHODIMP CAgent::BindToRootFolder(IFolderFolder **resultFolder)
|
||||
{
|
||||
COM_TRY_BEGIN
|
||||
RINOK(ReadItems());
|
||||
if (!_archiveLink.Arcs.IsEmpty())
|
||||
{
|
||||
RINOK(ReadItems());
|
||||
}
|
||||
CAgentFolder *folderSpec = new CAgentFolder;
|
||||
CMyComPtr<IFolderFolder> rootFolder = folderSpec;
|
||||
folderSpec->Init(_proxy, _proxy2, k_Proxy_RootDirIndex, /* NULL, */ this);
|
||||
@@ -1813,6 +1824,20 @@ STDMETHODIMP CAgent::GetArcProp(UInt32 level, PROPID propID, PROPVARIANT *value)
|
||||
if (_archiveLink.NonOpen_ErrorInfo.ErrorFormatIndex >= 0)
|
||||
prop = g_CodecsObj->Formats[_archiveLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name;
|
||||
break;
|
||||
case kpidErrorFlags:
|
||||
{
|
||||
UInt32 flags = _archiveLink.NonOpen_ErrorInfo.GetErrorFlags();
|
||||
if (flags != 0)
|
||||
prop = flags;
|
||||
break;
|
||||
}
|
||||
case kpidWarningFlags:
|
||||
{
|
||||
UInt32 flags = _archiveLink.NonOpen_ErrorInfo.GetWarningFlags();
|
||||
if (flags != 0)
|
||||
prop = flags;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -1822,7 +1847,10 @@ STDMETHODIMP CAgent::GetArcProp(UInt32 level, PROPID propID, PROPVARIANT *value)
|
||||
{
|
||||
case kpidType: prop = GetTypeOfArc(arc); break;
|
||||
case kpidPath: prop = arc.Path; break;
|
||||
case kpidErrorType: if (arc.ErrorInfo.ErrorFormatIndex >= 0) prop = g_CodecsObj->Formats[arc.ErrorInfo.ErrorFormatIndex].Name; break;
|
||||
case kpidErrorType:
|
||||
if (arc.ErrorInfo.ErrorFormatIndex >= 0)
|
||||
prop = g_CodecsObj->Formats[arc.ErrorInfo.ErrorFormatIndex].Name;
|
||||
break;
|
||||
case kpidErrorFlags:
|
||||
{
|
||||
UInt32 flags = arc.ErrorInfo.GetErrorFlags();
|
||||
|
||||
@@ -292,7 +292,7 @@ public:
|
||||
s2 += "Warning: The archive is open with offset";
|
||||
else
|
||||
{
|
||||
s2 += "Can not open the file as [";
|
||||
s2 += "Cannot open the file as [";
|
||||
s2 += g_CodecsObj->GetFormatNamePtr(arc.ErrorInfo.ErrorFormatIndex);
|
||||
s2 += "] archive";
|
||||
}
|
||||
|
||||
@@ -166,7 +166,7 @@ struct CDirItemsCallback_AgentOut: public IDirItemsCallback
|
||||
IFolderArchiveUpdateCallback *FolderArchiveUpdateCallback;
|
||||
HRESULT ErrorCode;
|
||||
|
||||
CDirItemsCallback_AgentOut(): ErrorCode(S_OK), FolderArchiveUpdateCallback(NULL) {}
|
||||
CDirItemsCallback_AgentOut(): FolderArchiveUpdateCallback(NULL), ErrorCode(S_OK) {}
|
||||
|
||||
HRESULT ScanError(const FString &name, DWORD systemError)
|
||||
{
|
||||
|
||||
@@ -51,6 +51,18 @@ int CProxyArc::FindSubDir(unsigned dirIndex, const wchar_t *name) const
|
||||
return FindSubDir(dirIndex, name, insertPos);
|
||||
}
|
||||
|
||||
static const wchar_t *AllocStringAndCopy(const wchar_t *s, size_t len)
|
||||
{
|
||||
wchar_t *p = new wchar_t[len + 1];
|
||||
MyStringCopy(p, s);
|
||||
return p;
|
||||
}
|
||||
|
||||
static const wchar_t *AllocStringAndCopy(const UString &s)
|
||||
{
|
||||
return AllocStringAndCopy(s, s.Len());
|
||||
}
|
||||
|
||||
unsigned CProxyArc::AddDir(unsigned dirIndex, int arcIndex, const UString &name)
|
||||
{
|
||||
unsigned insertPos;
|
||||
@@ -70,8 +82,7 @@ unsigned CProxyArc::AddDir(unsigned dirIndex, int arcIndex, const UString &name)
|
||||
CProxyDir &item = Dirs.AddNew();
|
||||
|
||||
item.NameLen = name.Len();
|
||||
item.Name = new wchar_t[item.NameLen + 1];
|
||||
MyStringCopy((wchar_t *)item.Name, name);
|
||||
item.Name = AllocStringAndCopy(name);
|
||||
|
||||
item.ArcIndex = arcIndex;
|
||||
item.ParentDir = dirIndex;
|
||||
@@ -248,6 +259,10 @@ HRESULT CProxyArc::Load(const CArc &arc, IProgress *progress)
|
||||
unsigned len = 0;
|
||||
bool isPtrName = false;
|
||||
|
||||
#if WCHAR_PATH_SEPARATOR != L'/'
|
||||
wchar_t replaceFromChar = 0;
|
||||
#endif
|
||||
|
||||
#if defined(MY_CPU_LE) && defined(_WIN32)
|
||||
// it works only if (sizeof(wchar_t) == 2)
|
||||
if (arc.GetRawProps)
|
||||
@@ -263,6 +278,9 @@ HRESULT CProxyArc::Load(const CArc &arc, IProgress *progress)
|
||||
len = size / 2 - 1;
|
||||
s = (const wchar_t *)p;
|
||||
isPtrName = true;
|
||||
#if WCHAR_PATH_SEPARATOR != L'/'
|
||||
replaceFromChar = L'\\';
|
||||
#endif
|
||||
}
|
||||
}
|
||||
if (!s)
|
||||
@@ -309,9 +327,17 @@ HRESULT CProxyArc::Load(const CArc &arc, IProgress *progress)
|
||||
|
||||
for (unsigned j = 0; j < len; j++)
|
||||
{
|
||||
wchar_t c = s[j];
|
||||
const wchar_t c = s[j];
|
||||
if (c == WCHAR_PATH_SEPARATOR || c == L'/')
|
||||
{
|
||||
#if WCHAR_PATH_SEPARATOR != L'/'
|
||||
if (c == replaceFromChar)
|
||||
{
|
||||
// s.ReplaceOneCharAtPos(j, WCHAR_IN_FILE_NAME_BACKSLASH_REPLACEMENT);
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
||||
const unsigned kLevelLimit = 1 << 10;
|
||||
if (numLevels <= kLevelLimit)
|
||||
{
|
||||
@@ -351,9 +377,8 @@ HRESULT CProxyArc::Load(const CArc &arc, IProgress *progress)
|
||||
f.Name = s;
|
||||
else
|
||||
{
|
||||
f.Name = new wchar_t[f.NameLen + 1];
|
||||
f.Name = AllocStringAndCopy(s, f.NameLen);
|
||||
f.NeedDeleteName = true;
|
||||
MyStringCopy((wchar_t *)f.Name, s);
|
||||
}
|
||||
|
||||
if (isDir)
|
||||
@@ -382,15 +407,15 @@ void CProxyArc2::GetDirPathParts(int dirIndex, UStringVector &pathParts, bool &i
|
||||
|
||||
isAltStreamDir = false;
|
||||
|
||||
if (dirIndex == k_Proxy2_RootDirIndex)
|
||||
if (dirIndex == (int)k_Proxy2_RootDirIndex)
|
||||
return;
|
||||
if (dirIndex == k_Proxy2_AltRootDirIndex)
|
||||
if (dirIndex == (int)k_Proxy2_AltRootDirIndex)
|
||||
{
|
||||
isAltStreamDir = true;
|
||||
return;
|
||||
}
|
||||
|
||||
while (dirIndex >= k_Proxy2_NumRootDirs)
|
||||
while (dirIndex >= (int)k_Proxy2_NumRootDirs)
|
||||
{
|
||||
const CProxyDir2 &dir = Dirs[dirIndex];
|
||||
const CProxyFile2 &file = Files[dir.ArcIndex];
|
||||
@@ -608,9 +633,8 @@ HRESULT CProxyArc2::Load(const CArc &arc, IProgress *progress)
|
||||
tempAString = (const char *)p;
|
||||
ConvertUTF8ToUnicode(tempAString, tempUString);
|
||||
file.NameLen = tempUString.Len();
|
||||
file.Name = new wchar_t[file.NameLen + 1];
|
||||
file.Name = AllocStringAndCopy(tempUString);
|
||||
file.NeedDeleteName = true;
|
||||
wmemcpy((wchar_t *)file.Name, tempUString.Ptr(), file.NameLen + 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -624,9 +648,8 @@ HRESULT CProxyArc2::Load(const CArc &arc, IProgress *progress)
|
||||
else
|
||||
return E_FAIL;
|
||||
file.NameLen = MyStringLen(s);
|
||||
file.Name = new wchar_t[file.NameLen + 1];
|
||||
file.Name = AllocStringAndCopy(s, file.NameLen);
|
||||
file.NeedDeleteName = true;
|
||||
wmemcpy((wchar_t *)file.Name, s, file.NameLen + 1);
|
||||
}
|
||||
|
||||
UInt32 parent = (UInt32)(Int32)-1;
|
||||
|
||||
@@ -12,7 +12,7 @@ struct CProxyFile
|
||||
bool NeedDeleteName;
|
||||
|
||||
CProxyFile(): Name(NULL), NameLen(0), NeedDeleteName(false) {}
|
||||
~CProxyFile() { if (NeedDeleteName) delete [](wchar_t *)Name; }
|
||||
~CProxyFile() { if (NeedDeleteName) delete [](wchar_t *)(void *)Name; } // delete [](wchar_t *)Name;
|
||||
};
|
||||
|
||||
const unsigned k_Proxy_RootDirIndex = 0;
|
||||
@@ -35,7 +35,7 @@ struct CProxyDir
|
||||
bool CrcIsDefined;
|
||||
|
||||
CProxyDir(): Name(NULL), NameLen(0), ParentDir(-1) {};
|
||||
~CProxyDir() { delete [](wchar_t *)Name; }
|
||||
~CProxyDir() { delete [](wchar_t *)(void *)Name; }
|
||||
|
||||
void Clear();
|
||||
bool IsLeaf() const { return ArcIndex >= 0; }
|
||||
@@ -93,7 +93,7 @@ struct CProxyFile2
|
||||
~CProxyFile2()
|
||||
{
|
||||
if (NeedDeleteName)
|
||||
delete [](wchar_t *)Name;
|
||||
delete [](wchar_t *)(void *)Name;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -31,8 +31,21 @@ STDMETHODIMP CArchiveFolderManager::OpenFolderFile(IInStream *inStream,
|
||||
}
|
||||
CAgent *agent = new CAgent();
|
||||
CMyComPtr<IInFolderArchive> archive = agent;
|
||||
RINOK(agent->Open(inStream, filePath, arcFormat, NULL, openArchiveCallback));
|
||||
return agent->BindToRootFolder(resultFolder);
|
||||
|
||||
HRESULT res = agent->Open(inStream, filePath, arcFormat, NULL, openArchiveCallback);
|
||||
|
||||
if (res != S_OK)
|
||||
{
|
||||
if (res != S_FALSE)
|
||||
return res;
|
||||
/* 20.01: we create folder even for Non-Open cases, if there is NonOpen_ErrorInfo information.
|
||||
So we can get error information from that IFolderFolder later. */
|
||||
if (!agent->_archiveLink.NonOpen_ErrorInfo.IsThereErrorOrWarning())
|
||||
return res;
|
||||
}
|
||||
|
||||
RINOK(agent->BindToRootFolder(resultFolder));
|
||||
return res;
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -27,30 +27,41 @@ void CAgentFolder::GetPathParts(UStringVector &pathParts, bool &isAltStreamFolde
|
||||
_proxy->GetDirPathParts(_proxyDirIndex, pathParts);
|
||||
}
|
||||
|
||||
static bool DeleteEmptyFolderAndEmptySubFolders(const FString &path)
|
||||
static bool Delete_EmptyFolder_And_EmptySubFolders(const FString &path)
|
||||
{
|
||||
NFind::CFileInfo fileInfo;
|
||||
FString pathPrefix = path;
|
||||
pathPrefix.Add_PathSepar();
|
||||
{
|
||||
NFind::CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(pathPrefix);
|
||||
while (enumerator.Next(fileInfo))
|
||||
const FString pathPrefix = path + FCHAR_PATH_SEPARATOR;
|
||||
CObjectVector<FString> names;
|
||||
{
|
||||
if (fileInfo.IsDir())
|
||||
if (!DeleteEmptyFolderAndEmptySubFolders(pathPrefix + fileInfo.Name))
|
||||
NFind::CDirEntry fileInfo;
|
||||
NFind::CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(pathPrefix);
|
||||
for (;;)
|
||||
{
|
||||
bool found;
|
||||
if (!enumerator.Next(fileInfo, found))
|
||||
return false;
|
||||
if (!found)
|
||||
break;
|
||||
if (fileInfo.IsDir())
|
||||
names.Add(fileInfo.Name);
|
||||
}
|
||||
}
|
||||
bool res = true;
|
||||
FOR_VECTOR (i, names)
|
||||
{
|
||||
if (!Delete_EmptyFolder_And_EmptySubFolders(pathPrefix + names[i]))
|
||||
res = false;
|
||||
}
|
||||
if (!res)
|
||||
return false;
|
||||
}
|
||||
/*
|
||||
// we don't need clear readonly for folders
|
||||
// we clear read-only attrib to remove read-only dir
|
||||
if (!SetFileAttrib(path, 0))
|
||||
return false;
|
||||
*/
|
||||
return RemoveDir(path);
|
||||
}
|
||||
|
||||
|
||||
HRESULT CAgentFolder::CommonUpdateOperation(
|
||||
AGENT_OP operation,
|
||||
bool moveMode,
|
||||
@@ -123,7 +134,7 @@ HRESULT CAgentFolder::CommonUpdateOperation(
|
||||
case AGENT_OP_Uni:
|
||||
{
|
||||
Byte actionSetByte[NUpdateArchive::NPairState::kNumValues];
|
||||
for (int i = 0; i < NUpdateArchive::NPairState::kNumValues; i++)
|
||||
for (unsigned i = 0; i < NUpdateArchive::NPairState::kNumValues; i++)
|
||||
actionSetByte[i] = (Byte)actionSet->StateActions[i];
|
||||
result = _agentSpec->DoOperation2(
|
||||
moveMode ? &requestedPaths : NULL,
|
||||
@@ -162,7 +173,7 @@ HRESULT CAgentFolder::CommonUpdateOperation(
|
||||
{
|
||||
const FString &fs = requestedPaths[i];
|
||||
if (NFind::DoesDirExist(fs))
|
||||
DeleteEmptyFolderAndEmptySubFolders(fs);
|
||||
Delete_EmptyFolder_And_EmptySubFolders(fs);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -28,10 +28,12 @@
|
||||
#include "../../../../C/7zVersion.h"
|
||||
|
||||
#ifdef _WIN32
|
||||
extern
|
||||
HINSTANCE g_hInstance;
|
||||
HINSTANCE g_hInstance = 0;
|
||||
#endif
|
||||
|
||||
// Tou can find the list of all GUIDs in Guid.txt file.
|
||||
// You can find the list of all GUIDs in Guid.txt file.
|
||||
// use another CLSIDs, if you want to support other formats (zip, rar, ...).
|
||||
// {23170F69-40C1-278A-1000-000110070000}
|
||||
|
||||
@@ -47,7 +49,11 @@ using namespace NWindows;
|
||||
using namespace NFile;
|
||||
using namespace NDir;
|
||||
|
||||
#ifdef _WIN32
|
||||
#define kDllName "7z.dll"
|
||||
#else
|
||||
#define kDllName "7z.so"
|
||||
#endif
|
||||
|
||||
static const char * const kCopyrightString =
|
||||
"\n"
|
||||
@@ -383,7 +389,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index,
|
||||
{
|
||||
if (!DeleteFileAlways(fullProcessedPath))
|
||||
{
|
||||
PrintError("Can not delete output file", fullProcessedPath);
|
||||
PrintError("Cannot delete output file", fullProcessedPath);
|
||||
return E_ABORT;
|
||||
}
|
||||
}
|
||||
@@ -392,7 +398,7 @@ STDMETHODIMP CArchiveExtractCallback::GetStream(UInt32 index,
|
||||
CMyComPtr<ISequentialOutStream> outStreamLoc(_outFileStreamSpec);
|
||||
if (!_outFileStreamSpec->Open(fullProcessedPath, CREATE_ALWAYS))
|
||||
{
|
||||
PrintError("Can not open output file", fullProcessedPath);
|
||||
PrintError("Cannot open output file", fullProcessedPath);
|
||||
return E_ABORT;
|
||||
}
|
||||
_outFileStream = outStreamLoc;
|
||||
@@ -556,7 +562,11 @@ public:
|
||||
FStringVector FailedFiles;
|
||||
CRecordVector<HRESULT> FailedCodes;
|
||||
|
||||
CArchiveUpdateCallback(): PasswordIsDefined(false), AskPassword(false), DirItems(0) {};
|
||||
CArchiveUpdateCallback():
|
||||
DirItems(NULL),
|
||||
PasswordIsDefined(false),
|
||||
AskPassword(false)
|
||||
{}
|
||||
|
||||
~CArchiveUpdateCallback() { Finilize(); }
|
||||
HRESULT Finilize();
|
||||
@@ -726,12 +736,18 @@ STDMETHODIMP CArchiveUpdateCallback::CryptoGetTextPassword2(Int32 *passwordIsDef
|
||||
|
||||
// Main function
|
||||
|
||||
#if defined(_UNICODE) && !defined(_WIN64) && !defined(UNDER_CE)
|
||||
#define NT_CHECK_FAIL_ACTION PrintError("Unsupported Windows version"); return 1;
|
||||
#endif
|
||||
|
||||
int MY_CDECL main(int numArgs, const char *args[])
|
||||
{
|
||||
NT_CHECK
|
||||
|
||||
#ifdef ENV_HAVE_LOCALE
|
||||
MY_SetLocale();
|
||||
#endif
|
||||
|
||||
PrintStringLn(kCopyrightString);
|
||||
|
||||
if (numArgs < 2)
|
||||
@@ -740,55 +756,96 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (numArgs < 3)
|
||||
{
|
||||
PrintError(kIncorrectCommand);
|
||||
return 1;
|
||||
}
|
||||
FString dllPrefix;
|
||||
|
||||
|
||||
NDLL::CLibrary lib;
|
||||
if (!lib.Load(NDLL::GetModuleDirPrefix() + FTEXT(kDllName)))
|
||||
#ifdef _WIN32
|
||||
dllPrefix = NDLL::GetModuleDirPrefix();
|
||||
#else
|
||||
{
|
||||
PrintError("Can not load 7-zip library");
|
||||
AString s (args[0]);
|
||||
int sep = s.ReverseFind_PathSepar();
|
||||
s.DeleteFrom(sep + 1);
|
||||
dllPrefix = s;
|
||||
}
|
||||
#endif
|
||||
|
||||
NDLL::CLibrary lib;
|
||||
if (!lib.Load(dllPrefix + FTEXT(kDllName)))
|
||||
{
|
||||
PrintError("Cannot load 7-zip library");
|
||||
return 1;
|
||||
}
|
||||
|
||||
Func_CreateObject createObjectFunc = (Func_CreateObject)lib.GetProc("CreateObject");
|
||||
if (!createObjectFunc)
|
||||
{
|
||||
PrintError("Can not get CreateObject");
|
||||
PrintError("Cannot get CreateObject");
|
||||
return 1;
|
||||
}
|
||||
|
||||
char c;
|
||||
char c = 0;
|
||||
UString password;
|
||||
bool passwordIsDefined = false;
|
||||
CObjectVector<FString> params;
|
||||
|
||||
for (int curCmd = 1; curCmd < numArgs; curCmd++)
|
||||
{
|
||||
AString command (args[1]);
|
||||
if (command.Len() != 1)
|
||||
AString a(args[curCmd]);
|
||||
|
||||
if (!a.IsEmpty())
|
||||
{
|
||||
if (a[0] == '-')
|
||||
{
|
||||
if (!passwordIsDefined && a[1] == 'p')
|
||||
{
|
||||
password = GetUnicodeString(a.Ptr(2));
|
||||
passwordIsDefined = true;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (c)
|
||||
{
|
||||
params.Add(CmdStringToFString(a));
|
||||
continue;
|
||||
}
|
||||
if (a.Len() == 1)
|
||||
{
|
||||
c = (char)MyCharLower_Ascii(a[0]);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
{
|
||||
PrintError(kIncorrectCommand);
|
||||
return 1;
|
||||
}
|
||||
c = (char)MyCharLower_Ascii(command[0]);
|
||||
}
|
||||
|
||||
FString archiveName = CmdStringToFString(args[2]);
|
||||
if (!c || params.Size() < 1)
|
||||
{
|
||||
PrintError(kIncorrectCommand);
|
||||
return 1;
|
||||
}
|
||||
|
||||
const FString &archiveName = params[0];
|
||||
|
||||
if (c == 'a')
|
||||
{
|
||||
// create archive command
|
||||
if (numArgs < 4)
|
||||
if (params.Size() < 2)
|
||||
{
|
||||
PrintError(kIncorrectCommand);
|
||||
return 1;
|
||||
}
|
||||
CObjectVector<CDirItem> dirItems;
|
||||
{
|
||||
int i;
|
||||
for (i = 3; i < numArgs; i++)
|
||||
unsigned i;
|
||||
for (i = 1; i < params.Size(); i++)
|
||||
{
|
||||
CDirItem di;
|
||||
FString name = CmdStringToFString(args[i]);
|
||||
const FString &name = params[i];
|
||||
|
||||
NFind::CFileInfo fi;
|
||||
if (!fi.Find(name))
|
||||
@@ -819,15 +876,15 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
CMyComPtr<IOutArchive> outArchive;
|
||||
if (createObjectFunc(&CLSID_Format, &IID_IOutArchive, (void **)&outArchive) != S_OK)
|
||||
{
|
||||
PrintError("Can not get class object");
|
||||
PrintError("Cannot get class object");
|
||||
return 1;
|
||||
}
|
||||
|
||||
CArchiveUpdateCallback *updateCallbackSpec = new CArchiveUpdateCallback;
|
||||
CMyComPtr<IArchiveUpdateCallback2> updateCallback(updateCallbackSpec);
|
||||
updateCallbackSpec->Init(&dirItems);
|
||||
// updateCallbackSpec->PasswordIsDefined = true;
|
||||
// updateCallbackSpec->Password = L"1";
|
||||
updateCallbackSpec->PasswordIsDefined = passwordIsDefined;
|
||||
updateCallbackSpec->Password = password;
|
||||
|
||||
/*
|
||||
{
|
||||
@@ -874,7 +931,7 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
}
|
||||
else
|
||||
{
|
||||
if (numArgs != 3)
|
||||
if (params.Size() != 1)
|
||||
{
|
||||
PrintError(kIncorrectCommand);
|
||||
return 1;
|
||||
@@ -895,7 +952,7 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
CMyComPtr<IInArchive> archive;
|
||||
if (createObjectFunc(&CLSID_Format, &IID_IInArchive, (void **)&archive) != S_OK)
|
||||
{
|
||||
PrintError("Can not get class object");
|
||||
PrintError("Cannot get class object");
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -904,21 +961,20 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
|
||||
if (!fileSpec->Open(archiveName))
|
||||
{
|
||||
PrintError("Can not open archive file", archiveName);
|
||||
PrintError("Cannot open archive file", archiveName);
|
||||
return 1;
|
||||
}
|
||||
|
||||
{
|
||||
CArchiveOpenCallback *openCallbackSpec = new CArchiveOpenCallback;
|
||||
CMyComPtr<IArchiveOpenCallback> openCallback(openCallbackSpec);
|
||||
openCallbackSpec->PasswordIsDefined = false;
|
||||
// openCallbackSpec->PasswordIsDefined = true;
|
||||
// openCallbackSpec->Password = L"1";
|
||||
openCallbackSpec->PasswordIsDefined = passwordIsDefined;
|
||||
openCallbackSpec->Password = password;
|
||||
|
||||
const UInt64 scanSize = 1 << 23;
|
||||
if (archive->Open(file, &scanSize, openCallback) != S_OK)
|
||||
{
|
||||
PrintError("Can not open file as archive", archiveName);
|
||||
PrintError("Cannot open file as archive", archiveName);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
@@ -957,9 +1013,8 @@ int MY_CDECL main(int numArgs, const char *args[])
|
||||
CArchiveExtractCallback *extractCallbackSpec = new CArchiveExtractCallback;
|
||||
CMyComPtr<IArchiveExtractCallback> extractCallback(extractCallbackSpec);
|
||||
extractCallbackSpec->Init(archive, FString()); // second parameter is output folder path
|
||||
extractCallbackSpec->PasswordIsDefined = false;
|
||||
// extractCallbackSpec->PasswordIsDefined = true;
|
||||
// extractCallbackSpec->Password = "1";
|
||||
extractCallbackSpec->PasswordIsDefined = passwordIsDefined;
|
||||
extractCallbackSpec->Password = password;
|
||||
|
||||
/*
|
||||
const wchar_t *names[] =
|
||||
|
||||
@@ -8,9 +8,9 @@ COMMON_OBJS = \
|
||||
$O\IntToString.obj \
|
||||
$O\NewHandler.obj \
|
||||
$O\MyString.obj \
|
||||
$O\MyVector.obj \
|
||||
$O\StringConvert.obj \
|
||||
$O\StringToInt.obj \
|
||||
$O\MyVector.obj \
|
||||
$O\Wildcard.obj \
|
||||
|
||||
WIN_OBJS = \
|
||||
|
||||
59
CPP/7zip/UI/Client7z/makefile.gcc
Normal file
59
CPP/7zip/UI/Client7z/makefile.gcc
Normal file
@@ -0,0 +1,59 @@
|
||||
PROG = 7zcl
|
||||
IS_NOT_STANDALONE = 1
|
||||
|
||||
# IS_X64 = 1
|
||||
|
||||
|
||||
|
||||
ifdef SystemDrive
|
||||
|
||||
SYS_OBJS = \
|
||||
$O/resource.o \
|
||||
|
||||
else
|
||||
|
||||
SYS_OBJS = \
|
||||
$O/MyWindows.o \
|
||||
$O/TimeUtils.o \
|
||||
|
||||
endif
|
||||
|
||||
|
||||
LOCAL_FLAGS = \
|
||||
|
||||
|
||||
CURRENT_OBJS = \
|
||||
$O/Client7z.o \
|
||||
|
||||
COMMON_OBJS = \
|
||||
$O/IntToString.o \
|
||||
$O/MyString.o \
|
||||
$O/MyVector.o \
|
||||
$O/NewHandler.o \
|
||||
$O/StringConvert.o \
|
||||
$O/StringToInt.o \
|
||||
$O/UTFConvert.o \
|
||||
$O/Wildcard.o \
|
||||
|
||||
WIN_OBJS = \
|
||||
$O/DLL.o \
|
||||
$O/FileDir.o \
|
||||
$O/FileFind.o \
|
||||
$O/FileIO.o \
|
||||
$O/FileName.o \
|
||||
$O/PropVariant.o \
|
||||
$O/PropVariantConv.o \
|
||||
|
||||
7ZIP_COMMON_OBJS = \
|
||||
$O/FileStreams.o \
|
||||
|
||||
|
||||
OBJS = \
|
||||
$(COMMON_OBJS) \
|
||||
$(WIN_OBJS) \
|
||||
$(SYS_OBJS) \
|
||||
$(7ZIP_COMMON_OBJS) \
|
||||
$(CURRENT_OBJS) \
|
||||
|
||||
|
||||
include ../../7zip_gcc.mak
|
||||
@@ -19,6 +19,7 @@
|
||||
#include "../../../../C/Alloc.h"
|
||||
#endif
|
||||
|
||||
#include "../../../Common/IntToString.h"
|
||||
#include "../../../Common/ListFileUtils.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "../../../Common/StringToInt.h"
|
||||
@@ -26,6 +27,7 @@
|
||||
#include "../../../Windows/ErrorMsg.h"
|
||||
#include "../../../Windows/FileDir.h"
|
||||
#include "../../../Windows/FileName.h"
|
||||
#include "../../../Windows/System.h"
|
||||
#ifdef _WIN32
|
||||
#include "../../../Windows/FileMapping.h"
|
||||
#include "../../../Windows/MemoryLock.h"
|
||||
@@ -41,22 +43,37 @@ extern bool g_CaseSensitive;
|
||||
extern bool g_PathTrailReplaceMode;
|
||||
|
||||
#ifdef _7ZIP_LARGE_PAGES
|
||||
extern
|
||||
bool g_LargePagesMode;
|
||||
bool g_LargePagesMode = false;
|
||||
#endif
|
||||
|
||||
/*
|
||||
#ifdef ENV_HAVE_LSTAT
|
||||
EXTERN_C_BEGIN
|
||||
extern int global_use_lstat;
|
||||
EXTERN_C_END
|
||||
#endif
|
||||
*/
|
||||
|
||||
#ifdef UNDER_CE
|
||||
|
||||
#define MY_IS_TERMINAL(x) false;
|
||||
|
||||
#else
|
||||
|
||||
#if _MSC_VER >= 1400
|
||||
#define MY_isatty_fileno(x) _isatty(_fileno(x))
|
||||
#else
|
||||
#define MY_isatty_fileno(x) isatty(fileno(x))
|
||||
#endif
|
||||
|
||||
#define MY_IS_TERMINAL(x) (MY_isatty_fileno(x) != 0);
|
||||
// #define MY_isatty_fileno(x) (isatty(fileno(x)))
|
||||
// #define MY_IS_TERMINAL(x) (MY_isatty_fileno(x) != 0);
|
||||
static inline bool MY_IS_TERMINAL(FILE *x)
|
||||
{
|
||||
return (
|
||||
#if defined(_MSC_VER) && (_MSC_VER >= 1400)
|
||||
_isatty(_fileno(x))
|
||||
#else
|
||||
isatty(fileno(x))
|
||||
#endif
|
||||
!= 0);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -74,8 +91,6 @@ static bool StringToUInt32(const wchar_t *s, UInt32 &v)
|
||||
}
|
||||
|
||||
|
||||
int g_CodePage = -1;
|
||||
|
||||
namespace NKey {
|
||||
enum Enum
|
||||
{
|
||||
@@ -127,6 +142,7 @@ enum Enum
|
||||
kConsoleCharSet,
|
||||
kTechMode,
|
||||
|
||||
kPreserveATime,
|
||||
kShareForWrite,
|
||||
kStopAfterOpenError,
|
||||
kCaseSensitive,
|
||||
@@ -137,6 +153,7 @@ enum Enum
|
||||
kFullPathMode,
|
||||
|
||||
kHardLinks,
|
||||
kSymLinks_AllowDangerous,
|
||||
kSymLinks,
|
||||
kNtSecurity,
|
||||
|
||||
@@ -164,7 +181,7 @@ static const char * const k_ArcNameMode_PostCharSet = "sea";
|
||||
|
||||
static const char * const k_Stream_PostCharSet = "012";
|
||||
|
||||
static inline const EArcNameMode ParseArcNameMode(int postCharIndex)
|
||||
static inline EArcNameMode ParseArcNameMode(int postCharIndex)
|
||||
{
|
||||
switch (postCharIndex)
|
||||
{
|
||||
@@ -182,12 +199,15 @@ namespace NRecursedPostCharIndex {
|
||||
};
|
||||
}
|
||||
|
||||
static const char kImmediateNameID = '!';
|
||||
static const char kMapNameID = '#';
|
||||
static const char kFileListID = '@';
|
||||
// static const char
|
||||
#define kImmediateNameID '!'
|
||||
#ifdef _WIN32
|
||||
#define kMapNameID '#'
|
||||
#endif
|
||||
#define kFileListID '@'
|
||||
|
||||
static const char kSomeCludePostStringMinSize = 2; // at least <@|!><N>ame must be
|
||||
static const char kSomeCludeAfterRecursedPostStringMinSize = 2; // at least <@|!><N>ame must be
|
||||
static const Byte kSomeCludePostStringMinSize = 2; // at least <@|!><N>ame must be
|
||||
static const Byte kSomeCludeAfterRecursedPostStringMinSize = 2; // at least <@|!><N>ame must be
|
||||
|
||||
static const char * const kOverwritePostCharSet = "asut";
|
||||
|
||||
@@ -199,80 +219,95 @@ static const NExtract::NOverwriteMode::EEnum k_OverwriteModes[] =
|
||||
NExtract::NOverwriteMode::kRenameExisting
|
||||
};
|
||||
|
||||
|
||||
|
||||
#define SWFRM_3(t, mu, mi) t, mu, mi, NULL
|
||||
|
||||
#define SWFRM_1(t) SWFRM_3(t, false, 0)
|
||||
#define SWFRM_SIMPLE SWFRM_1(NSwitchType::kSimple)
|
||||
#define SWFRM_MINUS SWFRM_1(NSwitchType::kMinus)
|
||||
#define SWFRM_STRING SWFRM_1(NSwitchType::kString)
|
||||
|
||||
#define SWFRM_STRING_SINGL(mi) SWFRM_3(NSwitchType::kString, false, mi)
|
||||
#define SWFRM_STRING_MULT(mi) SWFRM_3(NSwitchType::kString, true, mi)
|
||||
|
||||
|
||||
static const CSwitchForm kSwitchForms[] =
|
||||
{
|
||||
{ "?" },
|
||||
{ "h" },
|
||||
{ "-help" },
|
||||
{ "?", SWFRM_SIMPLE },
|
||||
{ "h", SWFRM_SIMPLE },
|
||||
{ "-help", SWFRM_SIMPLE },
|
||||
|
||||
{ "ba" },
|
||||
{ "bd" },
|
||||
{ "bt" },
|
||||
{ "bb", NSwitchType::kString, false, 0 },
|
||||
{ "ba", SWFRM_SIMPLE },
|
||||
{ "bd", SWFRM_SIMPLE },
|
||||
{ "bt", SWFRM_SIMPLE },
|
||||
{ "bb", SWFRM_STRING_SINGL(0) },
|
||||
|
||||
{ "bso", NSwitchType::kChar, false, 1, k_Stream_PostCharSet },
|
||||
{ "bse", NSwitchType::kChar, false, 1, k_Stream_PostCharSet },
|
||||
{ "bsp", NSwitchType::kChar, false, 1, k_Stream_PostCharSet },
|
||||
|
||||
{ "y" },
|
||||
{ "y", SWFRM_SIMPLE },
|
||||
|
||||
{ "ad" },
|
||||
{ "ad", SWFRM_SIMPLE },
|
||||
{ "ao", NSwitchType::kChar, false, 1, kOverwritePostCharSet},
|
||||
|
||||
{ "t", NSwitchType::kString, false, 1 },
|
||||
{ "stx", NSwitchType::kString, true, 1 },
|
||||
{ "t", SWFRM_STRING_SINGL(1) },
|
||||
{ "stx", SWFRM_STRING_MULT(1) },
|
||||
|
||||
{ "m", NSwitchType::kString, true, 1 },
|
||||
{ "o", NSwitchType::kString, false, 1 },
|
||||
{ "w", NSwitchType::kString },
|
||||
{ "m", SWFRM_STRING_MULT(1) },
|
||||
{ "o", SWFRM_STRING_SINGL(1) },
|
||||
{ "w", SWFRM_STRING },
|
||||
|
||||
{ "i", NSwitchType::kString, true, kSomeCludePostStringMinSize},
|
||||
{ "x", NSwitchType::kString, true, kSomeCludePostStringMinSize},
|
||||
{ "ai", NSwitchType::kString, true, kSomeCludePostStringMinSize},
|
||||
{ "ax", NSwitchType::kString, true, kSomeCludePostStringMinSize},
|
||||
{ "an" },
|
||||
{ "i", SWFRM_STRING_MULT(kSomeCludePostStringMinSize) },
|
||||
{ "x", SWFRM_STRING_MULT(kSomeCludePostStringMinSize) },
|
||||
{ "ai", SWFRM_STRING_MULT(kSomeCludePostStringMinSize) },
|
||||
{ "ax", SWFRM_STRING_MULT(kSomeCludePostStringMinSize) },
|
||||
{ "an", SWFRM_SIMPLE },
|
||||
|
||||
{ "u", NSwitchType::kString, true, 1},
|
||||
{ "v", NSwitchType::kString, true, 1},
|
||||
{ "u", SWFRM_STRING_MULT(1) },
|
||||
{ "v", SWFRM_STRING_MULT(1) },
|
||||
{ "r", NSwitchType::kChar, false, 0, kRecursedPostCharSet },
|
||||
|
||||
{ "stm", NSwitchType::kString },
|
||||
{ "sfx", NSwitchType::kString },
|
||||
{ "seml", NSwitchType::kString, false, 0},
|
||||
{ "scrc", NSwitchType::kString, true, 0 },
|
||||
{ "stm", SWFRM_STRING },
|
||||
{ "sfx", SWFRM_STRING },
|
||||
{ "seml", SWFRM_STRING_SINGL(0) },
|
||||
{ "scrc", SWFRM_STRING_MULT(0) },
|
||||
|
||||
{ "si", NSwitchType::kString },
|
||||
{ "so" },
|
||||
{ "si", SWFRM_STRING },
|
||||
{ "so", SWFRM_SIMPLE },
|
||||
|
||||
{ "slp", NSwitchType::kString },
|
||||
{ "scs", NSwitchType::kString },
|
||||
{ "scc", NSwitchType::kString },
|
||||
{ "slt" },
|
||||
{ "slp", SWFRM_STRING },
|
||||
{ "scs", SWFRM_STRING },
|
||||
{ "scc", SWFRM_STRING },
|
||||
{ "slt", SWFRM_SIMPLE },
|
||||
|
||||
{ "ssw" },
|
||||
{ "sse" },
|
||||
{ "ssc", NSwitchType::kMinus },
|
||||
{ "ssp", SWFRM_SIMPLE },
|
||||
{ "ssw", SWFRM_SIMPLE },
|
||||
{ "sse", SWFRM_SIMPLE },
|
||||
{ "ssc", SWFRM_MINUS },
|
||||
{ "sa", NSwitchType::kChar, false, 1, k_ArcNameMode_PostCharSet },
|
||||
|
||||
{ "spd" },
|
||||
{ "spe", NSwitchType::kMinus },
|
||||
{ "spf", NSwitchType::kString, false, 0 },
|
||||
{ "spd", SWFRM_SIMPLE },
|
||||
{ "spe", SWFRM_MINUS },
|
||||
{ "spf", SWFRM_STRING_SINGL(0) },
|
||||
|
||||
{ "snh", NSwitchType::kMinus },
|
||||
{ "snl", NSwitchType::kMinus },
|
||||
{ "sni" },
|
||||
{ "snh", SWFRM_MINUS },
|
||||
{ "snld", SWFRM_MINUS },
|
||||
{ "snl", SWFRM_MINUS },
|
||||
{ "sni", SWFRM_SIMPLE },
|
||||
|
||||
{ "sns", NSwitchType::kMinus },
|
||||
{ "snr" },
|
||||
{ "snc" },
|
||||
{ "sns", SWFRM_MINUS },
|
||||
{ "snr", SWFRM_SIMPLE },
|
||||
{ "snc", SWFRM_SIMPLE },
|
||||
|
||||
{ "snt", NSwitchType::kMinus },
|
||||
{ "snt", SWFRM_MINUS },
|
||||
|
||||
{ "sdel" },
|
||||
{ "stl" }
|
||||
{ "sdel", SWFRM_SIMPLE },
|
||||
{ "stl", SWFRM_SIMPLE }
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
, { "p", NSwitchType::kString }
|
||||
, { "p", SWFRM_STRING }
|
||||
#endif
|
||||
};
|
||||
|
||||
@@ -281,7 +316,7 @@ static const unsigned kMinNonSwitchWords = 1;
|
||||
static const unsigned kCommandIndex = 0;
|
||||
|
||||
// static const char * const kUserErrorMessage = "Incorrect command line";
|
||||
static const char * const kCannotFindListFile = "Cannot find listfile";
|
||||
// static const char * const kCannotFindListFile = "Cannot find listfile";
|
||||
static const char * const kIncorrectListFile = "Incorrect item in listfile.\nCheck charset encoding and -scs switch.";
|
||||
static const char * const kTerminalOutError = "I won't write compressed data to a terminal";
|
||||
static const char * const kSameTerminalError = "I won't write data and program's messages to same stream";
|
||||
@@ -295,8 +330,9 @@ bool CArcCommand::IsFromExtractGroup() const
|
||||
case NCommandType::kExtract:
|
||||
case NCommandType::kExtractFull:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
NExtract::NPathMode::EEnum CArcCommand::GetPathMode() const
|
||||
@@ -306,8 +342,9 @@ NExtract::NPathMode::EEnum CArcCommand::GetPathMode() const
|
||||
case NCommandType::kTest:
|
||||
case NCommandType::kExtractFull:
|
||||
return NExtract::NPathMode::kFullPaths;
|
||||
default:
|
||||
return NExtract::NPathMode::kNoPaths;
|
||||
}
|
||||
return NExtract::NPathMode::kNoPaths;
|
||||
}
|
||||
|
||||
bool CArcCommand::IsFromUpdateGroup() const
|
||||
@@ -319,8 +356,9 @@ bool CArcCommand::IsFromUpdateGroup() const
|
||||
case NCommandType::kDelete:
|
||||
case NCommandType::kRename:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static NRecursedType::EEnum GetRecursedTypeFromIndex(int index)
|
||||
@@ -376,6 +414,8 @@ static void AddNameToCensor(NWildcard::CCensor &censor,
|
||||
case NRecursedType::kRecursed:
|
||||
recursed = true;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
censor.AddPreItem(include, name, recursed, wildcardMatching);
|
||||
}
|
||||
@@ -408,11 +448,13 @@ static void AddRenamePair(CObjectVector<CRenamePair> *renamePairs,
|
||||
static void AddToCensorFromListFile(
|
||||
CObjectVector<CRenamePair> *renamePairs,
|
||||
NWildcard::CCensor &censor,
|
||||
LPCWSTR fileName, bool include, NRecursedType::EEnum type, bool wildcardMatching, Int32 codePage)
|
||||
LPCWSTR fileName, bool include, NRecursedType::EEnum type, bool wildcardMatching, UInt32 codePage)
|
||||
{
|
||||
UStringVector names;
|
||||
if (!NFind::DoesFileExist(us2fs(fileName)))
|
||||
/*
|
||||
if (!NFind::DoesFileExist_FollowLink(us2fs(fileName)))
|
||||
throw CArcCmdLineException(kCannotFindListFile, fileName);
|
||||
*/
|
||||
DWORD lastError = 0;
|
||||
if (!ReadNamesFromListFile2(us2fs(fileName), names, codePage, lastError))
|
||||
{
|
||||
@@ -449,7 +491,7 @@ static void AddToCensorFromNonSwitchesStrings(
|
||||
int stopSwitchIndex,
|
||||
NRecursedType::EEnum type,
|
||||
bool wildcardMatching,
|
||||
bool thereAreSwitchIncludes, Int32 codePage)
|
||||
bool thereAreSwitchIncludes, UInt32 codePage)
|
||||
{
|
||||
if ((renamePairs || nonSwitchStrings.Size() == startIndex) && !thereAreSwitchIncludes)
|
||||
AddNameToCensor(censor, UString(kUniversalWildcard), true, type,
|
||||
@@ -459,7 +501,7 @@ static void AddToCensorFromNonSwitchesStrings(
|
||||
int oldIndex = -1;
|
||||
|
||||
if (stopSwitchIndex < 0)
|
||||
stopSwitchIndex = nonSwitchStrings.Size();
|
||||
stopSwitchIndex = (int)nonSwitchStrings.Size();
|
||||
|
||||
for (unsigned i = startIndex; i < nonSwitchStrings.Size(); i++)
|
||||
{
|
||||
@@ -471,11 +513,11 @@ static void AddToCensorFromNonSwitchesStrings(
|
||||
else if (renamePairs)
|
||||
{
|
||||
if (oldIndex == -1)
|
||||
oldIndex = i;
|
||||
oldIndex = (int)i;
|
||||
else
|
||||
{
|
||||
// NRecursedType::EEnum type is used for global wildcard (-i! switches)
|
||||
AddRenamePair(renamePairs, nonSwitchStrings[oldIndex], s, NRecursedType::kNonRecursed, wildcardMatching);
|
||||
AddRenamePair(renamePairs, nonSwitchStrings[(unsigned)oldIndex], s, NRecursedType::kNonRecursed, wildcardMatching);
|
||||
// AddRenamePair(renamePairs, nonSwitchStrings[oldIndex], s, type);
|
||||
oldIndex = -1;
|
||||
}
|
||||
@@ -486,7 +528,7 @@ static void AddToCensorFromNonSwitchesStrings(
|
||||
|
||||
if (oldIndex != -1)
|
||||
{
|
||||
throw CArcCmdLineException("There is no second file name for rename pair:", nonSwitchStrings[oldIndex]);
|
||||
throw CArcCmdLineException("There is no second file name for rename pair:", nonSwitchStrings[(unsigned)oldIndex]);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -517,23 +559,23 @@ static const char *ParseMapWithPaths(
|
||||
int pos = s.Find(L':');
|
||||
if (pos < 0)
|
||||
return k_IncorrectMapCommand;
|
||||
int pos2 = s.Find(L':', pos + 1);
|
||||
int pos2 = s.Find(L':', (unsigned)(pos + 1));
|
||||
if (pos2 < 0)
|
||||
return k_IncorrectMapCommand;
|
||||
|
||||
CEventSetEnd eventSetEnd((const wchar_t *)s + ((unsigned)pos2 + 1));
|
||||
s.DeleteFrom(pos2);
|
||||
CEventSetEnd eventSetEnd((const wchar_t *)s + (unsigned)(pos2 + 1));
|
||||
s.DeleteFrom((unsigned)pos2);
|
||||
UInt32 size;
|
||||
if (!StringToUInt32(s.Ptr(pos + 1), size)
|
||||
if (!StringToUInt32(s.Ptr((unsigned)(pos + 1)), size)
|
||||
|| size < sizeof(wchar_t)
|
||||
|| size > ((UInt32)1 << 31)
|
||||
|| size % sizeof(wchar_t) != 0)
|
||||
return "Unsupported Map data size";
|
||||
|
||||
s.DeleteFrom(pos);
|
||||
s.DeleteFrom((unsigned)pos);
|
||||
CFileMapping map;
|
||||
if (map.Open(FILE_MAP_READ, GetSystemString(s)) != 0)
|
||||
return "Can not open mapping";
|
||||
return "Cannot open mapping";
|
||||
LPVOID data = map.Map(FILE_MAP_READ, 0, size);
|
||||
if (!data)
|
||||
return "MapViewOfFile error";
|
||||
@@ -569,7 +611,7 @@ static void AddSwitchWildcardsToCensor(
|
||||
const UStringVector &strings, bool include,
|
||||
NRecursedType::EEnum commonRecursedType,
|
||||
bool wildcardMatching,
|
||||
Int32 codePage)
|
||||
UInt32 codePage)
|
||||
{
|
||||
const char *errorMessage = NULL;
|
||||
unsigned i;
|
||||
@@ -667,9 +709,9 @@ static bool ParseUpdateCommandString2(const UString &command,
|
||||
if (i >= command.Len())
|
||||
return false;
|
||||
c = command[i];
|
||||
if (c < '0' || c >= '0' + kNumUpdatePairActions)
|
||||
if (c < '0' || c >= (wchar_t)('0' + kNumUpdatePairActions))
|
||||
return false;
|
||||
unsigned actionPos = c - '0';
|
||||
unsigned actionPos = (unsigned)(c - '0');
|
||||
actionSet.StateActions[(unsigned)statePos] = (NUpdateArchive::NPairAction::EEnum)(actionPos);
|
||||
if (kUpdatePairStateNotSupportedActions[(unsigned)statePos] == (int)actionPos)
|
||||
return false;
|
||||
@@ -791,8 +833,8 @@ static void SetMethodOptions(const CParser &parser, CObjectVector<CProperty> &pr
|
||||
int index = prop.Name.Find(L'=');
|
||||
if (index >= 0)
|
||||
{
|
||||
prop.Value = prop.Name.Ptr(index + 1);
|
||||
prop.Name.DeleteFrom(index);
|
||||
prop.Value = prop.Name.Ptr((unsigned)(index + 1));
|
||||
prop.Name.DeleteFrom((unsigned)index);
|
||||
}
|
||||
properties.Add(prop);
|
||||
}
|
||||
@@ -803,13 +845,24 @@ static void SetMethodOptions(const CParser &parser, CObjectVector<CProperty> &pr
|
||||
static inline void SetStreamMode(const CSwitchResult &sw, unsigned &res)
|
||||
{
|
||||
if (sw.ThereIs)
|
||||
res = sw.PostCharIndex;
|
||||
res = (unsigned)sw.PostCharIndex;
|
||||
}
|
||||
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
static void PrintHex(UString &s, UInt64 v)
|
||||
{
|
||||
char temp[32];
|
||||
ConvertUInt64ToHex(v, temp);
|
||||
s += temp;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void CArcCmdLineParser::Parse1(const UStringVector &commandStrings,
|
||||
CArcCmdLineOptions &options)
|
||||
{
|
||||
Parse1Log.Empty();
|
||||
if (!parser.ParseStrings(kSwitchForms, ARRAY_SIZE(kSwitchForms), commandStrings))
|
||||
throw CArcCmdLineException(parser.ErrorMessage, parser.ErrorLine);
|
||||
|
||||
@@ -879,14 +932,16 @@ void CArcCmdLineParser::Parse1(const UStringVector &commandStrings,
|
||||
|
||||
#ifdef _7ZIP_LARGE_PAGES
|
||||
if (slp >
|
||||
#ifndef UNDER_CE
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
(unsigned)NSecurity::Get_LargePages_RiskLevel()
|
||||
#else
|
||||
0
|
||||
#endif
|
||||
)
|
||||
{
|
||||
#ifdef _WIN32 // change it !
|
||||
SetLargePageSize();
|
||||
#endif
|
||||
// note: this process also can inherit that Privilege from parent process
|
||||
g_LargePagesMode =
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
@@ -906,32 +961,83 @@ void CArcCmdLineParser::Parse1(const UStringVector &commandStrings,
|
||||
const UString &s = parser[NKey::kAffinity].PostStrings[0];
|
||||
if (!s.IsEmpty())
|
||||
{
|
||||
UInt32 v = 0;
|
||||
AString a;
|
||||
a.SetFromWStr_if_Ascii(s);
|
||||
if (!a.IsEmpty())
|
||||
Parse1Log += "Set process affinity mask: ";
|
||||
|
||||
#ifdef _WIN32
|
||||
|
||||
UInt64 v = 0;
|
||||
{
|
||||
const char *end;
|
||||
v = ConvertHexStringToUInt32(a, &end);
|
||||
v = ConvertHexStringToUInt64(a, &end);
|
||||
if (*end != 0)
|
||||
a.Empty();
|
||||
}
|
||||
if (a.IsEmpty())
|
||||
throw CArcCmdLineException("Unsupported switch postfix -stm", s);
|
||||
|
||||
{
|
||||
#ifndef _WIN64
|
||||
if (v >= ((UInt64)1 << 32))
|
||||
throw CArcCmdLineException("unsupported value -stm", s);
|
||||
#endif
|
||||
{
|
||||
PrintHex(Parse1Log, v);
|
||||
if (!SetProcessAffinityMask(GetCurrentProcess(), (DWORD_PTR)v))
|
||||
{
|
||||
DWORD lastError = GetLastError();
|
||||
Parse1Log += " : ERROR : ";
|
||||
Parse1Log += NError::MyFormatMessage(lastError);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
SetProcessAffinityMask(GetCurrentProcess(), v);
|
||||
#endif
|
||||
#else // _WIN32
|
||||
|
||||
{
|
||||
Parse1Log += a;
|
||||
NSystem::CProcessAffinity aff;
|
||||
aff.CpuZero();
|
||||
for (unsigned i = 0; i < a.Len(); i++)
|
||||
{
|
||||
char c = a[i];
|
||||
unsigned v;
|
||||
if (c >= '0' && c <= '9') v = (unsigned)(c - '0');
|
||||
else if (c >= 'A' && c <= 'F') v = 10 + (unsigned)(c - 'A');
|
||||
else if (c >= 'a' && c <= 'f') v = 10 + (unsigned)(c - 'a');
|
||||
else
|
||||
throw CArcCmdLineException("Unsupported switch postfix -stm", s);
|
||||
for (unsigned k = 0; k < 4; k++)
|
||||
{
|
||||
const unsigned cpu = (a.Len() - 1 - i) * 4 + k;
|
||||
if (v & ((unsigned)1 << k))
|
||||
aff.CpuSet(cpu);
|
||||
}
|
||||
}
|
||||
|
||||
if (!aff.SetProcAffinity())
|
||||
{
|
||||
DWORD lastError = GetLastError();
|
||||
Parse1Log += " : ERROR : ";
|
||||
Parse1Log += NError::MyFormatMessage(lastError);
|
||||
}
|
||||
}
|
||||
#endif // _WIN32
|
||||
|
||||
Parse1Log.Add_LF();
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
||||
struct CCodePagePair
|
||||
{
|
||||
const char *Name;
|
||||
Int32 CodePage;
|
||||
UInt32 CodePage;
|
||||
};
|
||||
|
||||
static const unsigned kNumByteOnlyCodePages = 3;
|
||||
@@ -964,7 +1070,7 @@ static Int32 FindCharset(const NCommandLineParser::CParser &parser, unsigned key
|
||||
throw CArcCmdLineException("Unsupported charset:", name);
|
||||
const CCodePagePair &pair = g_CodePagePairs[i];
|
||||
if (name.IsEqualTo(pair.Name))
|
||||
return pair.CodePage;
|
||||
return (Int32)pair.CodePage;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1023,8 +1129,9 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
if (parser[NKey::kDisableWildcardParsing].ThereIs)
|
||||
wildcardMatching = false;
|
||||
|
||||
g_CodePage = FindCharset(parser, NKey::kConsoleCharSet, true, -1);
|
||||
Int32 codePage = FindCharset(parser, NKey::kListfileCharSet, false, CP_UTF8);
|
||||
options.ConsoleCodePage = FindCharset(parser, NKey::kConsoleCharSet, true, -1);
|
||||
|
||||
UInt32 codePage = (UInt32)FindCharset(parser, NKey::kListfileCharSet, false, CP_UTF8);
|
||||
|
||||
bool thereAreSwitchIncludes = false;
|
||||
|
||||
@@ -1097,6 +1204,30 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
SetBoolPair(parser, NKey::kHardLinks, options.HardLinks);
|
||||
SetBoolPair(parser, NKey::kSymLinks, options.SymLinks);
|
||||
|
||||
CBoolPair symLinks_AllowDangerous;
|
||||
SetBoolPair(parser, NKey::kSymLinks_AllowDangerous, symLinks_AllowDangerous);
|
||||
|
||||
|
||||
/*
|
||||
bool supportSymLink = options.SymLinks.Val;
|
||||
|
||||
if (!options.SymLinks.Def)
|
||||
{
|
||||
if (isExtractOrList)
|
||||
supportSymLink = true;
|
||||
else
|
||||
supportSymLink = false;
|
||||
}
|
||||
|
||||
#ifdef ENV_HAVE_LSTAT
|
||||
if (supportSymLink)
|
||||
global_use_lstat = 1;
|
||||
else
|
||||
global_use_lstat = 0;
|
||||
#endif
|
||||
*/
|
||||
|
||||
|
||||
if (isExtractOrList)
|
||||
{
|
||||
CExtractOptionsBase &eo = options.ExtractOptions;
|
||||
@@ -1117,6 +1248,8 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
if (!options.SymLinks.Def)
|
||||
nt.SymLinks.Val = true;
|
||||
|
||||
nt.SymLinks_AllowDangerous = symLinks_AllowDangerous;
|
||||
|
||||
nt.ReplaceColonForAltStream = parser[NKey::kReplaceColonForAltStream].ThereIs;
|
||||
nt.WriteToAltStreamIfColon = parser[NKey::kWriteToAltStreamIfColon].ThereIs;
|
||||
}
|
||||
@@ -1174,6 +1307,9 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
if (parser[NKey::kOutputDir].ThereIs)
|
||||
{
|
||||
eo.OutputDir = us2fs(parser[NKey::kOutputDir].PostStrings[0]);
|
||||
#ifdef _WIN32
|
||||
NFile::NName::NormalizeDirSeparators(eo.OutputDir);
|
||||
#endif
|
||||
NFile::NName::NormalizeDirPathPrefix(eo.OutputDir);
|
||||
}
|
||||
|
||||
@@ -1213,6 +1349,8 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
|
||||
updateOptions.MethodMode.Properties = options.Properties;
|
||||
|
||||
if (parser[NKey::kPreserveATime].ThereIs)
|
||||
updateOptions.PreserveATime = true;
|
||||
if (parser[NKey::kShareForWrite].ThereIs)
|
||||
updateOptions.OpenShareForWrite = true;
|
||||
if (parser[NKey::kStopAfterOpenError].ThereIs)
|
||||
@@ -1270,7 +1408,7 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
if (curCommandIndex < numNonSwitchStrings)
|
||||
{
|
||||
if (!StringToUInt32(nonSwitchStrings[curCommandIndex], options.NumIterations))
|
||||
throw CArcCmdLineException("Incorrect Number of benmchmark iterations", nonSwitchStrings[curCommandIndex]);
|
||||
throw CArcCmdLineException("Incorrect number of benchmark iterations", nonSwitchStrings[curCommandIndex]);
|
||||
curCommandIndex++;
|
||||
}
|
||||
}
|
||||
@@ -1282,10 +1420,13 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
CHashOptions &hashOptions = options.HashOptions;
|
||||
hashOptions.PathMode = censorPathMode;
|
||||
hashOptions.Methods = options.HashMethods;
|
||||
if (parser[NKey::kPreserveATime].ThereIs)
|
||||
hashOptions.PreserveATime = true;
|
||||
if (parser[NKey::kShareForWrite].ThereIs)
|
||||
hashOptions.OpenShareForWrite = true;
|
||||
hashOptions.StdInMode = options.StdInMode;
|
||||
hashOptions.AltStreamsMode = options.AltStreams.Val;
|
||||
hashOptions.SymLinks = options.SymLinks;
|
||||
}
|
||||
else if (options.Command.CommandType == NCommandType::kInfo)
|
||||
{
|
||||
@@ -1293,3 +1434,45 @@ void CArcCmdLineParser::Parse2(CArcCmdLineOptions &options)
|
||||
else
|
||||
throw 20150919;
|
||||
}
|
||||
|
||||
|
||||
|
||||
#ifndef _WIN32
|
||||
|
||||
static AString g_ModuleDirPrefix;
|
||||
|
||||
void Set_ModuleDirPrefix_From_ProgArg0(const char *s);
|
||||
void Set_ModuleDirPrefix_From_ProgArg0(const char *s)
|
||||
{
|
||||
AString a (s);
|
||||
int sep = a.ReverseFind_PathSepar();
|
||||
a.DeleteFrom((unsigned)(sep + 1));
|
||||
g_ModuleDirPrefix = a;
|
||||
}
|
||||
|
||||
namespace NWindows {
|
||||
namespace NDLL {
|
||||
|
||||
FString GetModuleDirPrefix();
|
||||
FString GetModuleDirPrefix()
|
||||
{
|
||||
FString s;
|
||||
|
||||
s = g_ModuleDirPrefix;
|
||||
if (s.IsEmpty())
|
||||
s = FTEXT(".") FSTRING_PATH_SEPARATOR;
|
||||
return s;
|
||||
/*
|
||||
setenv("_7ZIP_HOME_DIR", "/test/", 0);
|
||||
const char *home = getenv("_7ZIP_HOME_DIR");
|
||||
if (home)
|
||||
s = home;
|
||||
else
|
||||
s = FTEXT(".") FSTRING_PATH_SEPARATOR;
|
||||
return s;
|
||||
*/
|
||||
}
|
||||
|
||||
}}
|
||||
|
||||
#endif // ! _WIN32
|
||||
|
||||
@@ -63,6 +63,11 @@ struct CArcCmdLineOptions
|
||||
|
||||
bool YesToAll;
|
||||
bool ShowDialog;
|
||||
bool TechMode;
|
||||
bool ShowTime;
|
||||
|
||||
int ConsoleCodePage;
|
||||
|
||||
NWildcard::CCensor Censor;
|
||||
|
||||
CArcCommand Command;
|
||||
@@ -73,9 +78,6 @@ struct CArcCmdLineOptions
|
||||
UString Password;
|
||||
#endif
|
||||
|
||||
bool TechMode;
|
||||
bool ShowTime;
|
||||
|
||||
UStringVector HashMethods;
|
||||
|
||||
bool AppendName;
|
||||
@@ -109,13 +111,27 @@ struct CArcCmdLineOptions
|
||||
UInt32 NumIterations;
|
||||
|
||||
CArcCmdLineOptions():
|
||||
HelpMode(false),
|
||||
// LargePages(false),
|
||||
CaseSensitiveChange(false),
|
||||
CaseSensitive(false),
|
||||
|
||||
IsInTerminal(false),
|
||||
IsStdOutTerminal(false),
|
||||
IsStdErrTerminal(false),
|
||||
|
||||
StdInMode(false),
|
||||
StdOutMode(false),
|
||||
|
||||
EnableHeaders(false),
|
||||
|
||||
YesToAll(false),
|
||||
ShowDialog(false),
|
||||
TechMode(false),
|
||||
ShowTime(false),
|
||||
|
||||
ConsoleCodePage(-1),
|
||||
|
||||
Number_for_Out(k_OutStream_stdout),
|
||||
Number_for_Errors(k_OutStream_stderr),
|
||||
Number_for_Percents(k_OutStream_stdout),
|
||||
@@ -129,6 +145,7 @@ class CArcCmdLineParser
|
||||
{
|
||||
NCommandLineParser::CParser parser;
|
||||
public:
|
||||
UString Parse1Log;
|
||||
void Parse1(const UStringVector &commandStrings, CArcCmdLineOptions &options);
|
||||
void Parse2(CArcCmdLineOptions &options);
|
||||
};
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -4,12 +4,14 @@
|
||||
#define __ARCHIVE_EXTRACT_CALLBACK_H
|
||||
|
||||
#include "../../../Common/MyCom.h"
|
||||
#include "../../../Common/MyLinux.h"
|
||||
#include "../../../Common/Wildcard.h"
|
||||
|
||||
#include "../../IPassword.h"
|
||||
|
||||
#include "../../Common/FileStreams.h"
|
||||
#include "../../Common/ProgressUtils.h"
|
||||
#include "../../Common/StreamObjects.h"
|
||||
|
||||
#include "../../Archive/IArchive.h"
|
||||
|
||||
@@ -52,6 +54,7 @@ struct CExtractNtOptions
|
||||
{
|
||||
CBoolPair NtSecurity;
|
||||
CBoolPair SymLinks;
|
||||
CBoolPair SymLinks_AllowDangerous;
|
||||
CBoolPair HardLinks;
|
||||
CBoolPair AltStreams;
|
||||
bool ReplaceColonForAltStream;
|
||||
@@ -64,9 +67,10 @@ struct CExtractNtOptions
|
||||
WriteToAltStreamIfColon(false)
|
||||
{
|
||||
SymLinks.Val = true;
|
||||
SymLinks_AllowDangerous.Val = false;
|
||||
HardLinks.Val = true;
|
||||
AltStreams.Val = true;
|
||||
|
||||
|
||||
PreAllocateOutFile =
|
||||
#ifdef _WIN32
|
||||
true;
|
||||
@@ -165,10 +169,36 @@ struct CDirPathTime
|
||||
|
||||
FString Path;
|
||||
|
||||
bool SetDirTime();
|
||||
bool SetDirTime() const;
|
||||
};
|
||||
|
||||
|
||||
#ifdef SUPPORT_LINKS
|
||||
|
||||
struct CLinkInfo
|
||||
{
|
||||
// bool isCopyLink;
|
||||
bool isHardLink;
|
||||
bool isJunction;
|
||||
bool isRelative;
|
||||
bool isWSL;
|
||||
UString linkPath;
|
||||
|
||||
void Clear()
|
||||
{
|
||||
// IsCopyLink = false;
|
||||
isHardLink = false;
|
||||
isJunction = false;
|
||||
isRelative = false;
|
||||
isWSL = false;
|
||||
linkPath.Empty();
|
||||
}
|
||||
|
||||
bool Parse(const Byte *data, size_t dataSize, bool isLinuxData);
|
||||
};
|
||||
|
||||
#endif // SUPPORT_LINKS
|
||||
|
||||
|
||||
class CArchiveExtractCallback:
|
||||
public IArchiveExtractCallback,
|
||||
@@ -225,15 +255,53 @@ class CArchiveExtractCallback:
|
||||
bool ATimeDefined;
|
||||
bool MTimeDefined;
|
||||
bool AttribDefined;
|
||||
|
||||
bool IsReparse() const
|
||||
{
|
||||
return (AttribDefined && (Attrib & FILE_ATTRIBUTE_REPARSE_POINT) != 0);
|
||||
}
|
||||
|
||||
bool IsLinuxSymLink() const
|
||||
{
|
||||
return (AttribDefined && MY_LIN_S_ISLNK(Attrib >> 16));
|
||||
}
|
||||
|
||||
void SetFromPosixAttrib(UInt32 a)
|
||||
{
|
||||
// here we set only part of combined attribute required by SetFileAttrib() call
|
||||
#ifdef _WIN32
|
||||
// Windows sets FILE_ATTRIBUTE_NORMAL, if we try to set 0 as attribute.
|
||||
Attrib = MY_LIN_S_ISDIR(a) ?
|
||||
FILE_ATTRIBUTE_DIRECTORY :
|
||||
FILE_ATTRIBUTE_ARCHIVE;
|
||||
if ((a & 0222) == 0) // (& S_IWUSR) in p7zip
|
||||
Attrib |= FILE_ATTRIBUTE_READONLY;
|
||||
#else
|
||||
Attrib = (a << 16) | FILE_ATTRIBUTE_UNIX_EXTENSION;
|
||||
#endif
|
||||
AttribDefined = true;
|
||||
}
|
||||
} _fi;
|
||||
|
||||
bool _is_SymLink_in_Data;
|
||||
bool _is_SymLink_in_Data_Linux; // false = WIN32, true = LINUX
|
||||
|
||||
bool _fileWasExtracted;
|
||||
|
||||
UInt32 _index;
|
||||
UInt64 _curSize;
|
||||
bool _curSizeDefined;
|
||||
bool _fileLengthWasSet;
|
||||
UInt64 _fileLength_that_WasSet;
|
||||
|
||||
COutFileStream *_outFileStreamSpec;
|
||||
CMyComPtr<ISequentialOutStream> _outFileStream;
|
||||
|
||||
CByteBuffer _outMemBuf;
|
||||
CBufPtrSeqOutStream *_bufPtrSeqOutStream_Spec;
|
||||
CMyComPtr<ISequentialOutStream> _bufPtrSeqOutStream;
|
||||
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
COutStreamWithHash *_hashStreamSpec;
|
||||
@@ -261,6 +329,10 @@ class CArchiveExtractCallback:
|
||||
bool _progressTotal_Defined;
|
||||
|
||||
CObjectVector<CDirPathTime> _extractedFolders;
|
||||
|
||||
#ifndef _WIN32
|
||||
// CObjectVector<NWindows::NFile::NDir::CDelayedSymLink> _delayedSymLinks;
|
||||
#endif
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE) && !defined(_SFX)
|
||||
bool _saclEnabled;
|
||||
@@ -272,7 +344,7 @@ class CArchiveExtractCallback:
|
||||
|
||||
HRESULT SendMessageError(const char *message, const FString &path);
|
||||
HRESULT SendMessageError_with_LastError(const char *message, const FString &path);
|
||||
HRESULT SendMessageError2(const char *message, const FString &path1, const FString &path2);
|
||||
HRESULT SendMessageError2(HRESULT errorCode, const char *message, const FString &path1, const FString &path2);
|
||||
|
||||
public:
|
||||
|
||||
@@ -335,10 +407,12 @@ public:
|
||||
|
||||
private:
|
||||
CHardLinks _hardLinks;
|
||||
UString linkPath;
|
||||
CLinkInfo _link;
|
||||
|
||||
// FString _CopyFile_Path;
|
||||
// HRESULT MyCopyFile(ISequentialOutStream *outStream);
|
||||
HRESULT Link(const FString &fullProcessedPath);
|
||||
HRESULT ReadLink();
|
||||
|
||||
public:
|
||||
// call PrepareHardLinks() after Init()
|
||||
@@ -367,10 +441,33 @@ private:
|
||||
void ClearExtractedDirsInfo()
|
||||
{
|
||||
_extractedFolders.Clear();
|
||||
#ifndef _WIN32
|
||||
// _delayedSymLinks.Clear();
|
||||
#endif
|
||||
}
|
||||
|
||||
HRESULT Read_fi_Props();
|
||||
void CorrectPathParts();
|
||||
void CreateFolders();
|
||||
|
||||
bool _isRenamed;
|
||||
HRESULT CheckExistFile(FString &fullProcessedPath, bool &needExit);
|
||||
HRESULT GetExtractStream(CMyComPtr<ISequentialOutStream> &outStreamLoc, bool &needExit);
|
||||
|
||||
HRESULT CloseFile();
|
||||
HRESULT CloseReparseAndFile();
|
||||
HRESULT CloseReparseAndFile2();
|
||||
HRESULT SetDirsTimes();
|
||||
|
||||
const void *NtReparse_Data;
|
||||
UInt32 NtReparse_Size;
|
||||
|
||||
#ifdef SUPPORT_LINKS
|
||||
HRESULT SetFromLinkPath(
|
||||
const FString &fullProcessedPath,
|
||||
const CLinkInfo &linkInfo,
|
||||
bool &linkWasSet);
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ static UString CreateArchiveName(const NFind::CFileInfo &fi, bool keepName)
|
||||
int dotPos = resultName.ReverseFind_Dot();
|
||||
if (dotPos > 0)
|
||||
{
|
||||
FString archiveName2 = resultName.Left(dotPos);
|
||||
FString archiveName2 = resultName.Left((unsigned)dotPos);
|
||||
if (archiveName2.ReverseFind_Dot() < 0)
|
||||
resultName = archiveName2;
|
||||
}
|
||||
@@ -64,7 +64,7 @@ static FString CreateArchiveName2(const FString &path, bool fromPrev, bool keepN
|
||||
int dotPos = resultName.ReverseFind_Dot();
|
||||
if (dotPos > 0)
|
||||
{
|
||||
FString name2 = resultName.Left(dotPos);
|
||||
FString name2 = resultName.Left((unsigned)dotPos);
|
||||
if (name2.ReverseFind_Dot() < 0)
|
||||
resultName = name2;
|
||||
}
|
||||
|
||||
@@ -63,7 +63,7 @@ STDMETHODIMP COpenCallbackImp::GetProperty(PROPID propID, PROPVARIANT *value)
|
||||
|
||||
struct CInFileStreamVol: public CInFileStream
|
||||
{
|
||||
int FileNameIndex;
|
||||
unsigned FileNameIndex;
|
||||
COpenCallbackImp *OpenCallbackImp;
|
||||
CMyComPtr<IArchiveOpenCallback> OpenCallbackRef;
|
||||
|
||||
@@ -116,7 +116,7 @@ STDMETHODIMP COpenCallbackImp::GetStream(const wchar_t *name, IInStream **inStre
|
||||
FString fullPath;
|
||||
if (!NFile::NName::GetFullPath(_folderPrefix, us2fs(name2), fullPath))
|
||||
return S_FALSE;
|
||||
if (!_fileInfo.Find(fullPath))
|
||||
if (!_fileInfo.Find_FollowLink(fullPath))
|
||||
return S_FALSE;
|
||||
if (_fileInfo.IsDir())
|
||||
return S_FALSE;
|
||||
@@ -124,10 +124,7 @@ STDMETHODIMP COpenCallbackImp::GetStream(const wchar_t *name, IInStream **inStre
|
||||
CMyComPtr<IInStream> inStreamTemp = inFile;
|
||||
if (!inFile->Open(fullPath))
|
||||
{
|
||||
DWORD lastError = ::GetLastError();
|
||||
if (lastError == 0)
|
||||
return E_FAIL;
|
||||
return HRESULT_FROM_WIN32(lastError);
|
||||
return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
|
||||
FileSizes.Add(_fileInfo.Size);
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
#include "../../../Common/MyCom.h"
|
||||
|
||||
#include "../../../Windows/FileFind.h"
|
||||
#include "../../../Windows/FileIO.h"
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
#include "../../IPassword.h"
|
||||
@@ -88,24 +89,28 @@ public:
|
||||
CMyComPtr<IArchiveOpenCallback> ReOpenCallback;
|
||||
// UInt64 TotalSize;
|
||||
|
||||
COpenCallbackImp(): Callback(NULL), _subArchiveMode(false) {}
|
||||
COpenCallbackImp(): _subArchiveMode(false), Callback(NULL) {}
|
||||
|
||||
void Init(const FString &folderPrefix, const FString &fileName)
|
||||
HRESULT Init2(const FString &folderPrefix, const FString &fileName)
|
||||
{
|
||||
_folderPrefix = folderPrefix;
|
||||
if (!_fileInfo.Find(_folderPrefix + fileName))
|
||||
throw 20121118;
|
||||
FileNames.Clear();
|
||||
FileNames_WasUsed.Clear();
|
||||
FileSizes.Clear();
|
||||
_subArchiveMode = false;
|
||||
// TotalSize = 0;
|
||||
PasswordWasAsked = false;
|
||||
_folderPrefix = folderPrefix;
|
||||
if (!_fileInfo.Find_FollowLink(_folderPrefix + fileName))
|
||||
{
|
||||
// throw 20121118;
|
||||
return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
bool SetSecondFileInfo(CFSTR newName)
|
||||
{
|
||||
return _fileInfo.Find(newName) && !_fileInfo.IsDir();
|
||||
return _fileInfo.Find_FollowLink(newName) && !_fileInfo.IsDir();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -66,7 +66,7 @@ AString GetProcessThreadsInfo(const NWindows::NSystem::CProcessAffinity &ti);
|
||||
|
||||
void GetSysInfo(AString &s1, AString &s2);
|
||||
void GetCpuName(AString &s);
|
||||
void GetCpuFeatures(AString &s);
|
||||
void AddCpuFeatures(AString &s);
|
||||
|
||||
#ifdef _7ZIP_LARGE_PAGES
|
||||
void Add_LargePages_String(AString &s);
|
||||
|
||||
@@ -76,11 +76,12 @@ static HRESULT Call7zGui(const UString ¶ms,
|
||||
imageName += k7zGui;
|
||||
|
||||
CProcess process;
|
||||
WRes res = process.Create(imageName, params, NULL); // curDir);
|
||||
if (res != 0)
|
||||
const WRes wres = process.Create(imageName, params, NULL); // curDir);
|
||||
if (wres != 0)
|
||||
{
|
||||
ErrorMessageHRESULT(res, imageName);
|
||||
return res;
|
||||
HRESULT hres = HRESULT_FROM_WIN32(wres);
|
||||
ErrorMessageHRESULT(hres, imageName);
|
||||
return hres;
|
||||
}
|
||||
if (waitFinish)
|
||||
process.Wait();
|
||||
@@ -130,12 +131,11 @@ static HRESULT CreateMap(const UStringVector &names,
|
||||
for (;;)
|
||||
{
|
||||
random.GenerateName(mappingName, "7zMap");
|
||||
|
||||
WRes res = fileMapping.Create(PAGE_READWRITE, totalSize, GetSystemString(mappingName));
|
||||
if (fileMapping.IsCreated() && res == 0)
|
||||
const WRes wres = fileMapping.Create(PAGE_READWRITE, totalSize, GetSystemString(mappingName));
|
||||
if (fileMapping.IsCreated() && wres == 0)
|
||||
break;
|
||||
if (res != ERROR_ALREADY_EXISTS)
|
||||
return res;
|
||||
if (wres != ERROR_ALREADY_EXISTS)
|
||||
return HRESULT_FROM_WIN32(wres);
|
||||
fileMapping.Close();
|
||||
}
|
||||
|
||||
@@ -143,11 +143,11 @@ static HRESULT CreateMap(const UStringVector &names,
|
||||
for (;;)
|
||||
{
|
||||
random.GenerateName(eventName, "7zEvent");
|
||||
WRes res = event.CreateWithName(false, GetSystemString(eventName));
|
||||
if (event.IsCreated() && res == 0)
|
||||
const WRes wres = event.CreateWithName(false, GetSystemString(eventName));
|
||||
if (event.IsCreated() && wres == 0)
|
||||
break;
|
||||
if (res != ERROR_ALREADY_EXISTS)
|
||||
return res;
|
||||
if (wres != ERROR_ALREADY_EXISTS)
|
||||
return HRESULT_FROM_WIN32(wres);
|
||||
event.Close();
|
||||
}
|
||||
|
||||
|
||||
@@ -6,6 +6,8 @@
|
||||
|
||||
#include "../../UI/Common/EnumDirItems.h"
|
||||
|
||||
#include "../../UI/FileManager/LangUtils.h"
|
||||
|
||||
#include "../../UI/GUI/BenchmarkDialog.h"
|
||||
#include "../../UI/GUI/ExtractGUI.h"
|
||||
#include "../../UI/GUI/UpdateGUI.h"
|
||||
|
||||
@@ -20,7 +20,7 @@ static UString GetDefaultName3(const UString &fileName,
|
||||
|
||||
int dotPos = fileName.ReverseFind_Dot();
|
||||
if (dotPos > 0)
|
||||
return fileName.Left(dotPos) + addSubExtension;
|
||||
return fileName.Left((unsigned)dotPos) + addSubExtension;
|
||||
|
||||
if (addSubExtension.IsEmpty())
|
||||
return fileName + L'~';
|
||||
|
||||
@@ -3,6 +3,10 @@
|
||||
#ifndef __DIR_ITEM_H
|
||||
#define __DIR_ITEM_H
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "../../../Common/MyLinux.h"
|
||||
#endif
|
||||
|
||||
#include "../../../Common/MyString.h"
|
||||
|
||||
#include "../../../Windows/FileFind.h"
|
||||
@@ -84,13 +88,18 @@ struct CDirItem
|
||||
FILETIME MTime;
|
||||
UString Name;
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
// UString ShortName;
|
||||
#ifndef UNDER_CE
|
||||
CByteBuffer ReparseData;
|
||||
CByteBuffer ReparseData2; // fixed (reduced) absolute links
|
||||
|
||||
#ifdef _WIN32
|
||||
// UString ShortName;
|
||||
CByteBuffer ReparseData2; // fixed (reduced) absolute links for WIM format
|
||||
bool AreReparseData() const { return ReparseData.Size() != 0 || ReparseData2.Size() != 0; }
|
||||
#endif
|
||||
#else
|
||||
bool AreReparseData() const { return ReparseData.Size() != 0; }
|
||||
#endif // _WIN32
|
||||
|
||||
#endif // !UNDER_CE
|
||||
|
||||
UInt32 Attrib;
|
||||
int PhyParent;
|
||||
@@ -100,9 +109,23 @@ struct CDirItem
|
||||
bool IsAltStream;
|
||||
|
||||
CDirItem(): PhyParent(-1), LogParent(-1), SecureIndex(-1), IsAltStream(false) {}
|
||||
bool IsDir() const { return (Attrib & FILE_ATTRIBUTE_DIRECTORY) != 0 ; }
|
||||
|
||||
bool IsDir() const { return (Attrib & FILE_ATTRIBUTE_DIRECTORY) != 0; }
|
||||
bool IsReadOnly() const { return (Attrib & FILE_ATTRIBUTE_READONLY) != 0; }
|
||||
bool Has_Attrib_ReparsePoint() const { return (Attrib & FILE_ATTRIBUTE_REPARSE_POINT) != 0; }
|
||||
|
||||
#ifdef _WIN32
|
||||
UInt32 GetPosixAttrib() const
|
||||
{
|
||||
UInt32 v = IsDir() ? MY_LIN_S_IFDIR : MY_LIN_S_IFREG;
|
||||
v |= (IsReadOnly() ? 0555 : 0777);
|
||||
return v;
|
||||
}
|
||||
#endif
|
||||
};
|
||||
|
||||
|
||||
|
||||
class CDirItems
|
||||
{
|
||||
UStringVector Prefixes;
|
||||
@@ -117,17 +140,15 @@ public:
|
||||
CObjectVector<CDirItem> Items;
|
||||
|
||||
bool SymLinks;
|
||||
|
||||
bool ScanAltStreams;
|
||||
|
||||
CDirItemsStat Stat;
|
||||
|
||||
#ifndef UNDER_CE
|
||||
#if !defined(UNDER_CE)
|
||||
HRESULT SetLinkInfo(CDirItem &dirItem, const NWindows::NFile::NFind::CFileInfo &fi,
|
||||
const FString &phyPrefix);
|
||||
#endif
|
||||
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
|
||||
CUniqBlocks SecureBlocks;
|
||||
@@ -136,6 +157,7 @@ public:
|
||||
bool ReadSecure;
|
||||
|
||||
HRESULT AddSecurityItem(const FString &path, int &secureIndex);
|
||||
HRESULT FillFixedReparse();
|
||||
|
||||
#endif
|
||||
|
||||
@@ -157,6 +179,9 @@ public:
|
||||
|
||||
unsigned AddPrefix(int phyParent, int logParent, const UString &prefix);
|
||||
void DeleteLastPrefix();
|
||||
|
||||
// HRESULT EnumerateOneDir(const FString &phyPrefix, CObjectVector<NWindows::NFile::NFind::CDirEntry> &files);
|
||||
HRESULT EnumerateOneDir(const FString &phyPrefix, CObjectVector<NWindows::NFile::NFind::CFileInfo> &files);
|
||||
|
||||
HRESULT EnumerateItems2(
|
||||
const FString &phyPrefix,
|
||||
@@ -164,13 +189,10 @@ public:
|
||||
const FStringVector &filePaths,
|
||||
FStringVector *requestedPaths);
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
void FillFixedReparse();
|
||||
#endif
|
||||
|
||||
void ReserveDown();
|
||||
};
|
||||
|
||||
|
||||
struct CArcItem
|
||||
{
|
||||
UInt64 Size;
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -5,12 +5,8 @@
|
||||
|
||||
#include "../../../Common/Wildcard.h"
|
||||
|
||||
#include "../../../Windows/FileFind.h"
|
||||
|
||||
#include "DirItem.h"
|
||||
|
||||
void AddDirFileInfo(int phyParent, int logParent, int secureIndex,
|
||||
const NWindows::NFile::NFind::CFileInfo &fi, CObjectVector<CDirItem> &dirItems);
|
||||
|
||||
HRESULT EnumerateItems(
|
||||
const NWildcard::CCensor &censor,
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
#include "../../../Common/StringConvert.h"
|
||||
|
||||
#include "../../../Windows/FileDir.h"
|
||||
#include "../../../Windows/ErrorMsg.h"
|
||||
#include "../../../Windows/PropVariant.h"
|
||||
#include "../../../Windows/PropVariantConv.h"
|
||||
|
||||
@@ -19,6 +20,19 @@ using namespace NWindows;
|
||||
using namespace NFile;
|
||||
using namespace NDir;
|
||||
|
||||
|
||||
static void SetErrorMessage(const char *message,
|
||||
const FString &path, HRESULT errorCode,
|
||||
UString &s)
|
||||
{
|
||||
s = message;
|
||||
s += " : ";
|
||||
s += NError::MyFormatMessage(errorCode);
|
||||
s += " : ";
|
||||
s += fs2us(path);
|
||||
}
|
||||
|
||||
|
||||
static HRESULT DecompressArchive(
|
||||
CCodecs *codecs,
|
||||
const CArchiveLink &arcLink,
|
||||
@@ -47,7 +61,7 @@ static HRESULT DecompressArchive(
|
||||
// So it extracts different archives to one folder.
|
||||
// We will use top level archive name
|
||||
const CArc &arc0 = arcLink.Arcs[0];
|
||||
if (StringsAreEqualNoCase_Ascii(codecs->Formats[arc0.FormatIndex].Name, "pe"))
|
||||
if (arc0.FormatIndex >= 0 && StringsAreEqualNoCase_Ascii(codecs->Formats[(unsigned)arc0.FormatIndex].Name, "pe"))
|
||||
replaceName = arc0.DefaultName;
|
||||
}
|
||||
|
||||
@@ -164,11 +178,8 @@ static HRESULT DecompressArchive(
|
||||
*/
|
||||
else if (!CreateComplexDir(outDir))
|
||||
{
|
||||
HRESULT res = ::GetLastError();
|
||||
if (res == S_OK)
|
||||
res = E_FAIL;
|
||||
errorMessage = "Can not create output directory: ";
|
||||
errorMessage += fs2us(outDir);
|
||||
const HRESULT res = GetLastError_noZero_HRESULT();
|
||||
SetErrorMessage("Cannot create output directory", outDir, res, errorMessage);
|
||||
return res;
|
||||
}
|
||||
|
||||
@@ -221,6 +232,7 @@ static HRESULT DecompressArchive(
|
||||
Sorted list for file paths was sorted with case insensitive compare function.
|
||||
But FindInSorted function did binary search via case sensitive compare function */
|
||||
|
||||
int Find_FileName_InSortedVector(const UStringVector &fileName, const UString &name);
|
||||
int Find_FileName_InSortedVector(const UStringVector &fileName, const UString &name)
|
||||
{
|
||||
unsigned left = 0, right = fileName.Size();
|
||||
@@ -230,7 +242,7 @@ int Find_FileName_InSortedVector(const UStringVector &fileName, const UString &n
|
||||
const UString &midValue = fileName[mid];
|
||||
int compare = CompareFileNames(name, midValue);
|
||||
if (compare == 0)
|
||||
return mid;
|
||||
return (int)mid;
|
||||
if (compare < 0)
|
||||
right = mid;
|
||||
else
|
||||
@@ -239,6 +251,8 @@ int Find_FileName_InSortedVector(const UStringVector &fileName, const UString &n
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
|
||||
HRESULT Extract(
|
||||
CCodecs *codecs,
|
||||
const CObjectVector<COpenType> &types,
|
||||
@@ -268,11 +282,19 @@ HRESULT Extract(
|
||||
fi.Size = 0;
|
||||
if (!options.StdInMode)
|
||||
{
|
||||
const FString &arcPath = us2fs(arcPaths[i]);
|
||||
if (!fi.Find(arcPath))
|
||||
throw "there is no such archive";
|
||||
const FString arcPath = us2fs(arcPaths[i]);
|
||||
if (!fi.Find_FollowLink(arcPath))
|
||||
{
|
||||
const HRESULT errorCode = GetLastError_noZero_HRESULT();
|
||||
SetErrorMessage("Cannot find archive file", arcPath, errorCode, errorMessage);
|
||||
return errorCode;
|
||||
}
|
||||
if (fi.IsDir())
|
||||
throw "can't decompress folder";
|
||||
{
|
||||
HRESULT errorCode = E_FAIL;
|
||||
SetErrorMessage("The item is a directory", arcPath, errorCode, errorMessage);
|
||||
return errorCode;
|
||||
}
|
||||
}
|
||||
arcSizes.Add(fi.Size);
|
||||
totalPackSize += fi.Size;
|
||||
@@ -314,8 +336,12 @@ HRESULT Extract(
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!fi.Find(us2fs(arcPath)) || fi.IsDir())
|
||||
throw "there is no such archive";
|
||||
if (!fi.Find_FollowLink(us2fs(arcPath)) || fi.IsDir())
|
||||
{
|
||||
const HRESULT errorCode = GetLastError_noZero_HRESULT();
|
||||
SetErrorMessage("Cannot find archive file", us2fs(arcPath), errorCode, errorMessage);
|
||||
return errorCode;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -379,12 +405,7 @@ HRESULT Extract(
|
||||
{
|
||||
thereAreNotOpenArcs = true;
|
||||
if (!options.StdInMode)
|
||||
{
|
||||
NFind::CFileInfo fi2;
|
||||
if (fi2.Find(us2fs(arcPath)))
|
||||
if (!fi2.IsDir())
|
||||
totalPackProcessed += fi2.Size;
|
||||
}
|
||||
totalPackProcessed += fi.Size;
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -397,7 +418,7 @@ HRESULT Extract(
|
||||
// numArcs = arcPaths.Size();
|
||||
if (arcLink.VolumePaths.Size() != 0)
|
||||
{
|
||||
Int64 correctionSize = arcLink.VolumesSize;
|
||||
Int64 correctionSize = (Int64)arcLink.VolumesSize;
|
||||
FOR_VECTOR (v, arcLink.VolumePaths)
|
||||
{
|
||||
int index = Find_FileName_InSortedVector(arcPathsFull, arcLink.VolumePaths[v]);
|
||||
@@ -415,7 +436,7 @@ HRESULT Extract(
|
||||
Int64 newPackSize = (Int64)totalPackSize + correctionSize;
|
||||
if (newPackSize < 0)
|
||||
newPackSize = 0;
|
||||
totalPackSize = newPackSize;
|
||||
totalPackSize = (UInt64)newPackSize;
|
||||
RINOK(extractCallback->SetTotal(totalPackSize));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,10 +53,10 @@ struct CExtractOptions: public CExtractOptionsBase
|
||||
#endif
|
||||
|
||||
CExtractOptions():
|
||||
TestMode(false),
|
||||
StdInMode(false),
|
||||
StdOutMode(false),
|
||||
YesToAll(false)
|
||||
YesToAll(false),
|
||||
TestMode(false)
|
||||
{}
|
||||
};
|
||||
|
||||
|
||||
@@ -8,6 +8,8 @@
|
||||
|
||||
#include "ExtractingFilePath.h"
|
||||
|
||||
extern
|
||||
bool g_PathTrailReplaceMode;
|
||||
bool g_PathTrailReplaceMode =
|
||||
#ifdef _WIN32
|
||||
true
|
||||
@@ -17,6 +19,7 @@ bool g_PathTrailReplaceMode =
|
||||
;
|
||||
|
||||
|
||||
#ifdef _WIN32
|
||||
static void ReplaceIncorrectChars(UString &s)
|
||||
{
|
||||
{
|
||||
@@ -31,7 +34,10 @@ static void ReplaceIncorrectChars(UString &s)
|
||||
||
|
||||
#endif
|
||||
c == WCHAR_PATH_SEPARATOR)
|
||||
s.ReplaceOneCharAtPos(i, '_');
|
||||
s.ReplaceOneCharAtPos(i,
|
||||
'_' // default
|
||||
// (wchar_t)(0xf000 + c) // 21.02 debug: WSL encoding for unsupported characters
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -72,8 +78,7 @@ static void ReplaceIncorrectChars(UString &s)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
#endif
|
||||
|
||||
/* WinXP-64 doesn't support ':', '\\' and '/' symbols in name of alt stream.
|
||||
But colon in postfix ":$DATA" is allowed.
|
||||
@@ -98,6 +103,8 @@ void Correct_AltStream_Name(UString &s)
|
||||
s = '_';
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
|
||||
static const unsigned g_ReservedWithNum_Index = 4;
|
||||
|
||||
static const char * const g_ReservedNames[] =
|
||||
@@ -149,7 +156,7 @@ static void Correct_PathPart(UString &s)
|
||||
if (s.IsEmpty())
|
||||
return;
|
||||
|
||||
if (s[0] == '.' && (s[1] == 0 || s[1] == '.' && s[2] == 0))
|
||||
if (s[0] == '.' && (s[1] == 0 || (s[1] == '.' && s[2] == 0)))
|
||||
s.Empty();
|
||||
#ifdef _WIN32
|
||||
else
|
||||
|
||||
@@ -5,9 +5,9 @@
|
||||
|
||||
#include "../../../Common/MyString.h"
|
||||
|
||||
#ifdef _WIN32
|
||||
// #ifdef _WIN32
|
||||
void Correct_AltStream_Name(UString &s);
|
||||
#endif
|
||||
// #endif
|
||||
|
||||
// replaces unsuported characters, and replaces "." , ".." and "" to "[]"
|
||||
UString Get_Correct_FsFile_Name(const UString &name);
|
||||
|
||||
@@ -8,6 +8,7 @@
|
||||
|
||||
#include "../../Common/FileStreams.h"
|
||||
#include "../../Common/StreamUtils.h"
|
||||
#include "../../Common/StreamObjects.h"
|
||||
|
||||
#include "EnumDirItems.h"
|
||||
#include "HashCalc.h"
|
||||
@@ -211,6 +212,8 @@ HRESULT HashCalc(
|
||||
else
|
||||
{
|
||||
RINOK(callback->StartScanning());
|
||||
|
||||
dirItems.SymLinks = options.SymLinks.Val;
|
||||
dirItems.ScanAltStreams = options.AltStreamsMode;
|
||||
|
||||
HRESULT res = EnumerateItems(censor,
|
||||
@@ -258,31 +261,47 @@ HRESULT HashCalc(
|
||||
UString path;
|
||||
bool isDir = false;
|
||||
bool isAltStream = false;
|
||||
|
||||
if (options.StdInMode)
|
||||
{
|
||||
inStream = new CStdInFileStream;
|
||||
}
|
||||
else
|
||||
{
|
||||
CInFileStream *inStreamSpec = new CInFileStream;
|
||||
inStream = inStreamSpec;
|
||||
const CDirItem &dirItem = dirItems.Items[i];
|
||||
isDir = dirItem.IsDir();
|
||||
isAltStream = dirItem.IsAltStream;
|
||||
path = dirItems.GetLogPath(i);
|
||||
if (!isDir)
|
||||
const CDirItem &di = dirItems.Items[i];
|
||||
isAltStream = di.IsAltStream;
|
||||
|
||||
#ifndef UNDER_CE
|
||||
// if (di.AreReparseData())
|
||||
if (di.ReparseData.Size() != 0)
|
||||
{
|
||||
FString phyPath = dirItems.GetPhyPath(i);
|
||||
if (!inStreamSpec->OpenShared(phyPath, options.OpenShareForWrite))
|
||||
CBufInStream *inStreamSpec = new CBufInStream();
|
||||
inStream = inStreamSpec;
|
||||
inStreamSpec->Init(di.ReparseData, di.ReparseData.Size());
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
CInFileStream *inStreamSpec = new CInFileStream;
|
||||
inStreamSpec->File.PreserveATime = options.PreserveATime;
|
||||
inStream = inStreamSpec;
|
||||
isDir = di.IsDir();
|
||||
if (!isDir)
|
||||
{
|
||||
HRESULT res = callback->OpenFileError(phyPath, ::GetLastError());
|
||||
hb.NumErrors++;
|
||||
if (res != S_FALSE)
|
||||
return res;
|
||||
continue;
|
||||
const FString phyPath = dirItems.GetPhyPath(i);
|
||||
if (!inStreamSpec->OpenShared(phyPath, options.OpenShareForWrite))
|
||||
{
|
||||
HRESULT res = callback->OpenFileError(phyPath, ::GetLastError());
|
||||
hb.NumErrors++;
|
||||
if (res != S_FALSE)
|
||||
return res;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RINOK(callback->GetStream(path, isDir));
|
||||
UInt64 fileSize = 0;
|
||||
|
||||
|
||||
@@ -62,6 +62,8 @@ struct CHashBundle: public IHashCalc
|
||||
NumDirs = NumFiles = NumAltStreams = FilesSize = AltStreamsSize = NumErrors = 0;
|
||||
}
|
||||
|
||||
virtual ~CHashBundle() {};
|
||||
|
||||
void InitForNewFile();
|
||||
void Update(const void *data, UInt32 size);
|
||||
void SetSize(UInt64 size);
|
||||
@@ -90,12 +92,20 @@ struct IHashCallbackUI: public IDirItemsCallback
|
||||
struct CHashOptions
|
||||
{
|
||||
UStringVector Methods;
|
||||
bool PreserveATime;
|
||||
bool OpenShareForWrite;
|
||||
bool StdInMode;
|
||||
bool AltStreamsMode;
|
||||
CBoolPair SymLinks;
|
||||
|
||||
NWildcard::ECensorPathMode PathMode;
|
||||
|
||||
CHashOptions(): StdInMode(false), OpenShareForWrite(false), AltStreamsMode(false), PathMode(NWildcard::k_RelatPath) {};
|
||||
CHashOptions():
|
||||
PreserveATime(false),
|
||||
OpenShareForWrite(false),
|
||||
StdInMode(false),
|
||||
AltStreamsMode(false),
|
||||
PathMode(NWildcard::k_RelatPath) {};
|
||||
};
|
||||
|
||||
HRESULT HashCalc(
|
||||
|
||||
@@ -39,6 +39,8 @@ EXPORT_CODECS
|
||||
#include "../../../Common/StringToInt.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
|
||||
#include "../../../Windows/ErrorMsg.h"
|
||||
#include "../../../Windows/FileIO.h"
|
||||
#include "../../../Windows/PropVariant.h"
|
||||
|
||||
#include "LoadCodecs.h"
|
||||
@@ -82,11 +84,11 @@ using namespace NFile;
|
||||
|
||||
|
||||
static CFSTR const kMainDll =
|
||||
// #ifdef _WIN32
|
||||
#ifdef _WIN32
|
||||
FTEXT("7z.dll");
|
||||
// #else
|
||||
// FTEXT("7z.so");
|
||||
// #endif
|
||||
#else
|
||||
FTEXT("7z.so");
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef _WIN32
|
||||
@@ -110,7 +112,7 @@ static bool ReadPathFromRegistry(HKEY baseKey, LPCWSTR value, FString &path)
|
||||
{
|
||||
path = us2fs(pathU);
|
||||
NName::NormalizeDirPathPrefix(path);
|
||||
return NFind::DoesFileExist(path + kMainDll);
|
||||
return NFind::DoesFileExist_Raw(path + kMainDll);
|
||||
}
|
||||
}
|
||||
return false;
|
||||
@@ -163,7 +165,7 @@ int CArcInfoEx::FindExtension(const UString &ext) const
|
||||
{
|
||||
FOR_VECTOR (i, Exts)
|
||||
if (ext.IsEqualTo_NoCase(Exts[i].Ext))
|
||||
return i;
|
||||
return (int)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -206,15 +208,18 @@ static bool ParseSignatures(const Byte *data, unsigned size, CObjectVector<CByte
|
||||
|
||||
#endif // _SFX
|
||||
|
||||
// #include <stdio.h>
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
|
||||
static FString GetBaseFolderPrefixFromRegistry()
|
||||
{
|
||||
FString moduleFolderPrefix = NDLL::GetModuleDirPrefix();
|
||||
|
||||
#ifdef _WIN32
|
||||
if (!NFind::DoesFileExist(moduleFolderPrefix + kMainDll) &&
|
||||
!NFind::DoesDirExist(moduleFolderPrefix + kCodecsFolderName) &&
|
||||
!NFind::DoesDirExist(moduleFolderPrefix + kFormatsFolderName))
|
||||
if ( !NFind::DoesFileOrDirExist(moduleFolderPrefix + kMainDll)
|
||||
&& !NFind::DoesFileOrDirExist(moduleFolderPrefix + kCodecsFolderName)
|
||||
&& !NFind::DoesFileOrDirExist(moduleFolderPrefix + kFormatsFolderName))
|
||||
{
|
||||
FString path;
|
||||
if (ReadPathFromRegistry(HKEY_CURRENT_USER, kProgramPath2Value, path)) return path;
|
||||
@@ -223,6 +228,8 @@ static FString GetBaseFolderPrefixFromRegistry()
|
||||
if (ReadPathFromRegistry(HKEY_LOCAL_MACHINE, kProgramPathValue, path)) return path;
|
||||
}
|
||||
#endif
|
||||
|
||||
// printf("\nmoduleFolderPrefix = %s\n", (const char *)GetAnsiString(moduleFolderPrefix));
|
||||
return moduleFolderPrefix;
|
||||
}
|
||||
|
||||
@@ -238,25 +245,29 @@ static HRESULT GetCoderClass(Func_GetMethodProperty getMethodProperty, UInt32 in
|
||||
if (::SysStringByteLen(prop.bstrVal) != sizeof(GUID))
|
||||
return E_FAIL;
|
||||
isAssigned = true;
|
||||
clsId = *(const GUID *)prop.bstrVal;
|
||||
clsId = *(const GUID *)(const void *)prop.bstrVal;
|
||||
}
|
||||
else if (prop.vt != VT_EMPTY)
|
||||
return E_FAIL;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
#define MY_GET_FUNC(dest, type, func) *(void **)(&dest) = (func);
|
||||
// #define MY_GET_FUNC(dest, type, func) dest = (type)(func);
|
||||
|
||||
HRESULT CCodecs::LoadCodecs()
|
||||
{
|
||||
CCodecLib &lib = Libs.Back();
|
||||
|
||||
lib.CreateDecoder = (Func_CreateDecoder)lib.Lib.GetProc("CreateDecoder");
|
||||
lib.CreateEncoder = (Func_CreateEncoder)lib.Lib.GetProc("CreateEncoder");
|
||||
lib.GetMethodProperty = (Func_GetMethodProperty)lib.Lib.GetProc("GetMethodProperty");
|
||||
MY_GET_FUNC (lib.CreateDecoder, Func_CreateDecoder, lib.Lib.GetProc("CreateDecoder"));
|
||||
MY_GET_FUNC (lib.CreateEncoder, Func_CreateEncoder, lib.Lib.GetProc("CreateEncoder"));
|
||||
MY_GET_FUNC (lib.GetMethodProperty, Func_GetMethodProperty, lib.Lib.GetProc("GetMethodProperty"));
|
||||
|
||||
if (lib.GetMethodProperty)
|
||||
{
|
||||
UInt32 numMethods = 1;
|
||||
Func_GetNumberOfMethods getNumberOfMethods = (Func_GetNumberOfMethods)lib.Lib.GetProc("GetNumberOfMethods");
|
||||
Func_GetNumberOfMethods getNumberOfMethods;
|
||||
MY_GET_FUNC (getNumberOfMethods, Func_GetNumberOfMethods, lib.Lib.GetProc("GetNumberOfMethods"));
|
||||
if (getNumberOfMethods)
|
||||
{
|
||||
RINOK(getNumberOfMethods(&numMethods));
|
||||
@@ -272,7 +283,8 @@ HRESULT CCodecs::LoadCodecs()
|
||||
}
|
||||
}
|
||||
|
||||
Func_GetHashers getHashers = (Func_GetHashers)lib.Lib.GetProc("GetHashers");
|
||||
Func_GetHashers getHashers;
|
||||
MY_GET_FUNC (getHashers, Func_GetHashers, lib.Lib.GetProc("GetHashers"));
|
||||
if (getHashers)
|
||||
{
|
||||
RINOK(getHashers(&lib.ComHashers));
|
||||
@@ -381,14 +393,17 @@ HRESULT CCodecs::LoadFormats()
|
||||
const NDLL::CLibrary &lib = Libs.Back().Lib;
|
||||
|
||||
Func_GetHandlerProperty getProp = NULL;
|
||||
Func_GetHandlerProperty2 getProp2 = (Func_GetHandlerProperty2)lib.GetProc("GetHandlerProperty2");
|
||||
Func_GetIsArc getIsArc = (Func_GetIsArc)lib.GetProc("GetIsArc");
|
||||
Func_GetHandlerProperty2 getProp2;
|
||||
MY_GET_FUNC (getProp2, Func_GetHandlerProperty2, lib.GetProc("GetHandlerProperty2"));
|
||||
Func_GetIsArc getIsArc;
|
||||
MY_GET_FUNC (getIsArc, Func_GetIsArc, lib.GetProc("GetIsArc"));
|
||||
|
||||
UInt32 numFormats = 1;
|
||||
|
||||
if (getProp2)
|
||||
{
|
||||
Func_GetNumberOfFormats getNumberOfFormats = (Func_GetNumberOfFormats)lib.GetProc("GetNumberOfFormats");
|
||||
Func_GetNumberOfFormats getNumberOfFormats;
|
||||
MY_GET_FUNC (getNumberOfFormats, Func_GetNumberOfFormats, lib.GetProc("GetNumberOfFormats"));
|
||||
if (getNumberOfFormats)
|
||||
{
|
||||
RINOK(getNumberOfFormats(&numFormats));
|
||||
@@ -396,7 +411,7 @@ HRESULT CCodecs::LoadFormats()
|
||||
}
|
||||
else
|
||||
{
|
||||
getProp = (Func_GetHandlerProperty)lib.GetProc("GetHandlerProperty");
|
||||
MY_GET_FUNC (getProp, Func_GetHandlerProperty, lib.GetProc("GetHandlerProperty"));
|
||||
if (!getProp)
|
||||
return S_OK;
|
||||
}
|
||||
@@ -404,7 +419,7 @@ HRESULT CCodecs::LoadFormats()
|
||||
for (UInt32 i = 0; i < numFormats; i++)
|
||||
{
|
||||
CArcInfoEx item;
|
||||
item.LibIndex = Libs.Size() - 1;
|
||||
item.LibIndex = (int)(Libs.Size() - 1);
|
||||
item.FormatIndex = i;
|
||||
|
||||
RINOK(GetProp_String(getProp, getProp2, i, NArchive::NHandlerPropID::kName, item.Name));
|
||||
@@ -417,7 +432,7 @@ HRESULT CCodecs::LoadFormats()
|
||||
continue;
|
||||
if (::SysStringByteLen(prop.bstrVal) != sizeof(GUID))
|
||||
return E_FAIL;
|
||||
item.ClassID = *(const GUID *)prop.bstrVal;
|
||||
item.ClassID = *(const GUID *)(const void *)prop.bstrVal;
|
||||
prop.Clear();
|
||||
}
|
||||
|
||||
@@ -473,23 +488,53 @@ extern "C"
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void CCodecs::AddLastError(const FString &path)
|
||||
{
|
||||
HRESULT res = GetLastError_noZero_HRESULT();
|
||||
CCodecError &error = Errors.AddNew();
|
||||
error.Path = path;
|
||||
error.ErrorCode = res;
|
||||
}
|
||||
|
||||
HRESULT CCodecs::LoadDll(const FString &dllPath, bool needCheckDll, bool *loadedOK)
|
||||
{
|
||||
if (loadedOK)
|
||||
*loadedOK = false;
|
||||
|
||||
// needCheckDll = 1;
|
||||
|
||||
#ifdef _WIN32
|
||||
if (needCheckDll)
|
||||
{
|
||||
NDLL::CLibrary lib;
|
||||
if (!lib.LoadEx(dllPath, LOAD_LIBRARY_AS_DATAFILE))
|
||||
{
|
||||
/* if is not win32
|
||||
// %1 is not a valid Win32 application.
|
||||
// #define ERROR_BAD_EXE_FORMAT 193L
|
||||
*/
|
||||
// return GetLastError_noZero_HRESULT();
|
||||
DWORD lastError = GetLastError();
|
||||
if (lastError != ERROR_BAD_EXE_FORMAT)
|
||||
{
|
||||
CCodecError &error = Errors.AddNew();
|
||||
error.Path = dllPath;
|
||||
error.Message = "cannot load file as datafile library";
|
||||
error.ErrorCode = HRESULT_FROM_WIN32(lastError);
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
#else
|
||||
UNUSED_VAR(needCheckDll)
|
||||
#endif
|
||||
|
||||
Libs.AddNew();
|
||||
CCodecLib &lib = Libs.Back();
|
||||
lib.Path = dllPath;
|
||||
bool used = false;
|
||||
HRESULT res = S_OK;
|
||||
// HRESULT res = S_OK;
|
||||
|
||||
if (lib.Lib.Load(dllPath))
|
||||
{
|
||||
@@ -499,10 +544,28 @@ HRESULT CCodecs::LoadDll(const FString &dllPath, bool needCheckDll, bool *loaded
|
||||
lib.LoadIcons();
|
||||
#endif
|
||||
|
||||
/*
|
||||
{
|
||||
Func_LibStartup _LibStartup;
|
||||
MY_GET_FUNC (_LibStartup, Func_LibStartup, lib.Lib.GetProc("LibStartup"));
|
||||
if (_LibStartup)
|
||||
{
|
||||
HRESULT res = _LibStartup();
|
||||
if (res != 0)
|
||||
{
|
||||
CCodecError &error = Errors.AddNew();
|
||||
error.Path = dllPath;
|
||||
error.ErrorCode = res;
|
||||
}
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
#ifdef _7ZIP_LARGE_PAGES
|
||||
if (g_LargePageSize != 0)
|
||||
{
|
||||
Func_SetLargePageMode setLargePageMode = (Func_SetLargePageMode)lib.Lib.GetProc("SetLargePageMode");
|
||||
Func_SetLargePageMode setLargePageMode;
|
||||
MY_GET_FUNC (setLargePageMode, Func_SetLargePageMode, lib.Lib.GetProc("SetLargePageMode"));
|
||||
if (setLargePageMode)
|
||||
setLargePageMode();
|
||||
}
|
||||
@@ -510,16 +573,18 @@ HRESULT CCodecs::LoadDll(const FString &dllPath, bool needCheckDll, bool *loaded
|
||||
|
||||
if (CaseSensitiveChange)
|
||||
{
|
||||
Func_SetCaseSensitive setCaseSensitive = (Func_SetCaseSensitive)lib.Lib.GetProc("SetCaseSensitive");
|
||||
Func_SetCaseSensitive setCaseSensitive;
|
||||
MY_GET_FUNC (setCaseSensitive, Func_SetCaseSensitive, lib.Lib.GetProc("SetCaseSensitive"));
|
||||
if (setCaseSensitive)
|
||||
setCaseSensitive(CaseSensitive ? 1 : 0);
|
||||
}
|
||||
|
||||
lib.CreateObject = (Func_CreateObject)lib.Lib.GetProc("CreateObject");
|
||||
MY_GET_FUNC (lib.CreateObject, Func_CreateObject, lib.Lib.GetProc("CreateObject"));
|
||||
{
|
||||
unsigned startSize = Codecs.Size() + Hashers.Size();
|
||||
res = LoadCodecs();
|
||||
used = (startSize != Codecs.Size() + Hashers.Size());
|
||||
HRESULT res = LoadCodecs();
|
||||
if (startSize != Codecs.Size() + Hashers.Size())
|
||||
used = true;
|
||||
if (res == S_OK && lib.CreateObject)
|
||||
{
|
||||
startSize = Formats.Size();
|
||||
@@ -527,22 +592,61 @@ HRESULT CCodecs::LoadDll(const FString &dllPath, bool needCheckDll, bool *loaded
|
||||
if (startSize != Formats.Size())
|
||||
used = true;
|
||||
}
|
||||
if (res != S_OK)
|
||||
{
|
||||
CCodecError &error = Errors.AddNew();
|
||||
error.Path = dllPath;
|
||||
error.ErrorCode = res;
|
||||
}
|
||||
}
|
||||
// plugins can use non-7-zip dlls, so we silently ignore non7zip DLLs
|
||||
/*
|
||||
if (!used)
|
||||
{
|
||||
CCodecError &error = Errors.AddNew();
|
||||
error.Path = dllPath;
|
||||
error.Message = "no 7-Zip code";
|
||||
}
|
||||
*/
|
||||
}
|
||||
else
|
||||
{
|
||||
AddLastError(dllPath);
|
||||
}
|
||||
|
||||
if (!used)
|
||||
Libs.DeleteBack();
|
||||
|
||||
return res;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT CCodecs::LoadDllsFromFolder(const FString &folderPrefix)
|
||||
HRESULT CCodecs::LoadDllsFromFolder(const FString &folderPath)
|
||||
{
|
||||
if (!NFile::NFind::DoesDirExist_FollowLink(folderPath))
|
||||
// if (!NFile::NFind::DoesDirExist(folderPath))
|
||||
{
|
||||
// AddLastError(folderPath);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
FString folderPrefix = folderPath;
|
||||
folderPrefix.Add_PathSepar();
|
||||
|
||||
NFile::NFind::CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(folderPrefix);
|
||||
NFile::NFind::CFileInfo fi;
|
||||
while (enumerator.Next(fi))
|
||||
NFile::NFind::CDirEntry fi;
|
||||
for (;;)
|
||||
{
|
||||
bool found;
|
||||
if (!enumerator.Next(fi, found))
|
||||
{
|
||||
// it can be wrong Symbolic link to folder here
|
||||
AddLastError(folderPath);
|
||||
break;
|
||||
// return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
if (!found)
|
||||
break;
|
||||
if (fi.IsDir())
|
||||
continue;
|
||||
RINOK(LoadDll(folderPrefix + fi.Name, true));
|
||||
@@ -585,6 +689,7 @@ HRESULT CCodecs::Load()
|
||||
Formats.Clear();
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
Errors.Clear();
|
||||
MainDll_ErrorPath.Empty();
|
||||
Codecs.Clear();
|
||||
Hashers.Clear();
|
||||
@@ -627,6 +732,8 @@ HRESULT CCodecs::Load()
|
||||
Formats.Add(item);
|
||||
}
|
||||
|
||||
// printf("\nLoad codecs \n");
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
const FString baseFolder = GetBaseFolderPrefixFromRegistry();
|
||||
{
|
||||
@@ -635,8 +742,8 @@ HRESULT CCodecs::Load()
|
||||
if (!loadedOK)
|
||||
MainDll_ErrorPath = kMainDll;
|
||||
}
|
||||
RINOK(LoadDllsFromFolder(baseFolder + kCodecsFolderName FSTRING_PATH_SEPARATOR));
|
||||
RINOK(LoadDllsFromFolder(baseFolder + kFormatsFolderName FSTRING_PATH_SEPARATOR));
|
||||
RINOK(LoadDllsFromFolder(baseFolder + kCodecsFolderName));
|
||||
RINOK(LoadDllsFromFolder(baseFolder + kFormatsFolderName));
|
||||
|
||||
NeedSetLibCodecs = true;
|
||||
|
||||
@@ -659,7 +766,7 @@ HRESULT CCodecs::Load()
|
||||
FOR_VECTOR(i, Libs)
|
||||
{
|
||||
CCodecLib &lib = Libs[i];
|
||||
lib.SetCodecs = (Func_SetCodecs)lib.Lib.GetProc("SetCodecs");
|
||||
MY_GET_FUNC (lib.SetCodecs, Func_SetCodecs, lib.Lib.GetProc("SetCodecs"));
|
||||
if (lib.SetCodecs)
|
||||
{
|
||||
RINOK(lib.SetCodecs(this));
|
||||
@@ -679,7 +786,7 @@ int CCodecs::FindFormatForArchiveName(const UString &arcPath) const
|
||||
int dotPos = arcPath.ReverseFind_Dot();
|
||||
if (dotPos <= arcPath.ReverseFind_PathSepar())
|
||||
return -1;
|
||||
const UString ext = arcPath.Ptr(dotPos + 1);
|
||||
const UString ext = arcPath.Ptr((unsigned)(dotPos + 1));
|
||||
if (ext.IsEmpty())
|
||||
return -1;
|
||||
if (ext.IsEqualTo_Ascii_NoCase("exe"))
|
||||
@@ -692,7 +799,7 @@ int CCodecs::FindFormatForArchiveName(const UString &arcPath) const
|
||||
continue;
|
||||
*/
|
||||
if (arc.FindExtension(ext) >= 0)
|
||||
return i;
|
||||
return (int)i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
@@ -703,7 +810,7 @@ int CCodecs::FindFormatForExtension(const UString &ext) const
|
||||
return -1;
|
||||
FOR_VECTOR (i, Formats)
|
||||
if (Formats[i].FindExtension(ext) >= 0)
|
||||
return i;
|
||||
return (int)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -711,7 +818,7 @@ int CCodecs::FindFormatForArchiveType(const UString &arcType) const
|
||||
{
|
||||
FOR_VECTOR (i, Formats)
|
||||
if (Formats[i].Name.IsEqualTo_NoCase(arcType))
|
||||
return i;
|
||||
return (int)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -722,8 +829,8 @@ bool CCodecs::FindFormatForArchiveType(const UString &arcType, CIntVector &forma
|
||||
{
|
||||
int pos2 = arcType.Find(L'.', pos);
|
||||
if (pos2 < 0)
|
||||
pos2 = arcType.Len();
|
||||
const UString name = arcType.Mid(pos, pos2 - pos);
|
||||
pos2 = (int)arcType.Len();
|
||||
const UString name = arcType.Mid(pos, (unsigned)pos2 - pos);
|
||||
if (name.IsEmpty())
|
||||
return false;
|
||||
int index = FindFormatForArchiveType(name);
|
||||
@@ -733,7 +840,7 @@ bool CCodecs::FindFormatForArchiveType(const UString &arcType, CIntVector &forma
|
||||
return false;
|
||||
}
|
||||
formatIndices.Add(index);
|
||||
pos = pos2 + 1;
|
||||
pos = (unsigned)pos2 + 1;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -756,19 +863,19 @@ void CCodecIcons::LoadIcons(HMODULE m)
|
||||
CIconPair iconPair;
|
||||
iconPair.IconIndex = -1;
|
||||
if (pos < 0)
|
||||
pos = s.Len();
|
||||
pos = (int)s.Len();
|
||||
else
|
||||
{
|
||||
UString num = s.Ptr(pos + 1);
|
||||
const UString num = s.Ptr((unsigned)pos + 1);
|
||||
if (!num.IsEmpty())
|
||||
{
|
||||
const wchar_t *end;
|
||||
iconPair.IconIndex = ConvertStringToUInt32(num, &end);
|
||||
iconPair.IconIndex = (int)ConvertStringToUInt32(num, &end);
|
||||
if (*end != 0)
|
||||
continue;
|
||||
}
|
||||
}
|
||||
iconPair.Ext = s.Left(pos);
|
||||
iconPair.Ext = s.Left((unsigned)pos);
|
||||
IconPairs.Add(iconPair);
|
||||
}
|
||||
}
|
||||
@@ -946,7 +1053,7 @@ int CCodecs::GetCodec_LibIndex(UInt32 index) const
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
const CDllCodecInfo &ci = Codecs[index - NUM_EXPORT_CODECS];
|
||||
return ci.LibIndex;
|
||||
return (int)ci.LibIndex;
|
||||
#else
|
||||
return -1;
|
||||
#endif
|
||||
@@ -961,7 +1068,7 @@ int CCodecs::GetHasherLibIndex(UInt32 index)
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
const CDllHasherInfo &ci = Hashers[index - NUM_EXPORT_HASHERS];
|
||||
return ci.LibIndex;
|
||||
return (int)ci.LibIndex;
|
||||
#else
|
||||
return -1;
|
||||
#endif
|
||||
@@ -1014,7 +1121,8 @@ bool CCodecs::GetCodec_EncoderIsAssigned(UInt32 index) const
|
||||
UInt32 CCodecs::GetCodec_NumStreams(UInt32 index)
|
||||
{
|
||||
NCOM::CPropVariant prop;
|
||||
RINOK(GetProperty(index, NMethodPropID::kPackStreams, &prop));
|
||||
if (GetProperty(index, NMethodPropID::kPackStreams, &prop) != S_OK)
|
||||
return 0;
|
||||
if (prop.vt == VT_UI4)
|
||||
return (UInt32)prop.ulVal;
|
||||
if (prop.vt == VT_EMPTY)
|
||||
@@ -1065,10 +1173,33 @@ AString CCodecs::GetHasherName(UInt32 index)
|
||||
UInt32 CCodecs::GetHasherDigestSize(UInt32 index)
|
||||
{
|
||||
NCOM::CPropVariant prop;
|
||||
RINOK(GetHasherProp(index, NMethodPropID::kDigestSize, &prop));
|
||||
if (GetHasherProp(index, NMethodPropID::kDigestSize, &prop) != S_OK)
|
||||
return 0;
|
||||
if (prop.vt != VT_UI4)
|
||||
return 0;
|
||||
return prop.ulVal;
|
||||
}
|
||||
|
||||
void CCodecs::GetCodecsErrorMessage(UString &s)
|
||||
{
|
||||
s.Empty();
|
||||
FOR_VECTOR (i, Errors)
|
||||
{
|
||||
const CCodecError &ce = Errors[i];
|
||||
s += "Codec Load Error: ";
|
||||
s += fs2us(ce.Path);
|
||||
if (ce.ErrorCode != 0)
|
||||
{
|
||||
s += " : ";
|
||||
s += NWindows::NError::MyFormatMessage(ce.ErrorCode);
|
||||
}
|
||||
if (!ce.Message.IsEmpty())
|
||||
{
|
||||
s += " : ";
|
||||
s += ce.Message;
|
||||
}
|
||||
s.Add_LF();
|
||||
}
|
||||
}
|
||||
|
||||
#endif // EXTERNAL_CODECS
|
||||
|
||||
@@ -132,7 +132,8 @@ struct CArcInfoEx
|
||||
bool Flags_BackwardOpen() const { return (Flags & NArcInfoFlags::kBackwardOpen) != 0; }
|
||||
bool Flags_PreArc() const { return (Flags & NArcInfoFlags::kPreArc) != 0; }
|
||||
bool Flags_PureStartOpen() const { return (Flags & NArcInfoFlags::kPureStartOpen) != 0; }
|
||||
|
||||
bool Flags_ByExtOnlyOpen() const { return (Flags & NArcInfoFlags::kByExtOnlyOpen) != 0; }
|
||||
|
||||
UString GetMainExt() const
|
||||
{
|
||||
if (Exts.IsEmpty())
|
||||
@@ -227,6 +228,13 @@ struct CCodecLib
|
||||
|
||||
#endif
|
||||
|
||||
struct CCodecError
|
||||
{
|
||||
FString Path;
|
||||
HRESULT ErrorCode;
|
||||
AString Message;
|
||||
CCodecError(): ErrorCode(0) {}
|
||||
};
|
||||
|
||||
class CCodecs:
|
||||
#ifdef EXTERNAL_CODECS
|
||||
@@ -243,7 +251,9 @@ public:
|
||||
|
||||
CObjectVector<CCodecLib> Libs;
|
||||
FString MainDll_ErrorPath;
|
||||
|
||||
CObjectVector<CCodecError> Errors;
|
||||
|
||||
void AddLastError(const FString &path);
|
||||
void CloseLibs();
|
||||
|
||||
class CReleaser
|
||||
@@ -272,7 +282,7 @@ public:
|
||||
|
||||
HRESULT CreateArchiveHandler(const CArcInfoEx &ai, bool outHandler, void **archive) const
|
||||
{
|
||||
return Libs[ai.LibIndex].CreateObject(&ai.ClassID, outHandler ? &IID_IOutArchive : &IID_IInArchive, (void **)archive);
|
||||
return Libs[(unsigned)ai.LibIndex].CreateObject(&ai.ClassID, outHandler ? &IID_IOutArchive : &IID_IInArchive, (void **)archive);
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -306,11 +316,11 @@ public:
|
||||
|
||||
const wchar_t *GetFormatNamePtr(int formatIndex) const
|
||||
{
|
||||
return formatIndex < 0 ? L"#" : (const wchar_t *)Formats[formatIndex].Name;
|
||||
return formatIndex < 0 ? L"#" : (const wchar_t *)Formats[(unsigned)formatIndex].Name;
|
||||
}
|
||||
|
||||
HRESULT Load();
|
||||
|
||||
|
||||
#ifndef _SFX
|
||||
int FindFormatForArchiveName(const UString &arcPath) const;
|
||||
int FindFormatForExtension(const UString &ext) const;
|
||||
@@ -352,6 +362,8 @@ public:
|
||||
AString GetHasherName(UInt32 index);
|
||||
UInt32 GetHasherDigestSize(UInt32 index);
|
||||
|
||||
void GetCodecsErrorMessage(UString &s);
|
||||
|
||||
#endif
|
||||
|
||||
HRESULT CreateInArchive(unsigned formatIndex, CMyComPtr<IInArchive> &archive) const
|
||||
@@ -399,7 +411,7 @@ public:
|
||||
if (!arc.UpdateEnabled)
|
||||
continue;
|
||||
if (arc.Name.IsEqualTo_NoCase(name))
|
||||
return i;
|
||||
return (int)i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
#include "../../../Common/IntToString.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "../../../Common/StringToInt.h"
|
||||
#include "../../../Common/UTFConvert.h"
|
||||
#include "../../../Common/Wildcard.h"
|
||||
|
||||
#include "../../../Windows/FileDir.h"
|
||||
@@ -32,11 +33,13 @@
|
||||
#include "SetProperties.h"
|
||||
#endif
|
||||
|
||||
#ifndef _SFX
|
||||
#ifdef SHOW_DEBUG_INFO
|
||||
#define PRF(x) x
|
||||
#else
|
||||
#define PRF(x)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
// increase it, if you need to support larger SFX stubs
|
||||
static const UInt64 kMaxCheckStartPosition = 1 << 23;
|
||||
@@ -64,7 +67,7 @@ Open:
|
||||
- open FAIL:
|
||||
Try to open with all other types from offset 0 only.
|
||||
If some open type is OK and physical archive size is uequal or larger
|
||||
than file size, then return that archive with warning that can not be open as [extension type].
|
||||
than file size, then return that archive with warning that cannot be open as [extension type].
|
||||
If extension was EXE, it will try to open as unknown_extension case
|
||||
- file has unknown extension (like a.hhh)
|
||||
It tries to open via parser code.
|
||||
@@ -141,14 +144,14 @@ struct CParseItem
|
||||
bool LenIsUnknown;
|
||||
|
||||
CParseItem():
|
||||
LenIsUnknown(false),
|
||||
// OkSize(0),
|
||||
FileTime_Defined(false),
|
||||
UnpackSize_Defined(false),
|
||||
NumSubFiles_Defined(false),
|
||||
NumSubDirs_Defined(false),
|
||||
NumSubFiles_Defined(false),
|
||||
IsSelfExe(false),
|
||||
IsNotArcType(false)
|
||||
// OkSize(0)
|
||||
IsNotArcType(false),
|
||||
LenIsUnknown(false)
|
||||
{}
|
||||
|
||||
/*
|
||||
@@ -214,15 +217,17 @@ int CHandler::FindInsertPos(const CParseItem &item) const
|
||||
left = mid + 1;
|
||||
else if (item.Size < midItem.Size)
|
||||
right = mid;
|
||||
/*
|
||||
else if (item.Size > midItem.Size)
|
||||
left = mid + 1;
|
||||
*/
|
||||
else
|
||||
{
|
||||
left = mid + 1;
|
||||
// return -1;
|
||||
}
|
||||
}
|
||||
return left;
|
||||
return (int)left;
|
||||
}
|
||||
|
||||
void CHandler::AddUnknownItem(UInt64 next)
|
||||
@@ -260,7 +265,7 @@ void CHandler::AddItem(const CParseItem &item)
|
||||
int pos = FindInsertPos(item);
|
||||
if (pos >= 0)
|
||||
{
|
||||
_items.Insert(pos, item);
|
||||
_items.Insert((unsigned)pos, item);
|
||||
UInt64 next = item.Offset + item.Size;
|
||||
if (_maxEndOffset < next)
|
||||
_maxEndOffset = next;
|
||||
@@ -401,7 +406,7 @@ HRESULT CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
Int32 askMode = testMode ?
|
||||
NExtract::NAskMode::kTest :
|
||||
NExtract::NAskMode::kExtract;
|
||||
Int32 index = allFilesMode ? i : indices[i];
|
||||
UInt32 index = allFilesMode ? i : indices[i];
|
||||
const CParseItem &item = _items[index];
|
||||
|
||||
RINOK(extractCallback->GetStream(index, &realOutStream, askMode));
|
||||
@@ -417,7 +422,7 @@ HRESULT CHandler::Extract(const UInt32 *indices, UInt32 numItems,
|
||||
outStreamSpec->Init(skipMode ? 0 : unpackSize, true);
|
||||
|
||||
Int32 opRes = NExtract::NOperationResult::kOK;
|
||||
RINOK(_stream->Seek(item.Offset, STREAM_SEEK_SET, NULL));
|
||||
RINOK(_stream->Seek((Int64)item.Offset, STREAM_SEEK_SET, NULL));
|
||||
streamSpec->Init(unpackSize);
|
||||
RINOK(copyCoder->Code(inStream, outStream, NULL, NULL, progress));
|
||||
|
||||
@@ -496,13 +501,14 @@ static HRESULT Archive_GetArcProp_UInt(IInArchive *arc, PROPID propid, UInt64 &r
|
||||
RINOK(arc->GetArchiveProperty(propid, &prop));
|
||||
switch (prop.vt)
|
||||
{
|
||||
case VT_UI4: result = prop.ulVal; defined = true; break;
|
||||
case VT_I4: result = (Int64)prop.lVal; defined = true; break;
|
||||
case VT_UI8: result = (UInt64)prop.uhVal.QuadPart; defined = true; break;
|
||||
case VT_I8: result = (UInt64)prop.hVal.QuadPart; defined = true; break;
|
||||
case VT_EMPTY: break;
|
||||
case VT_UI4: result = prop.ulVal; break;
|
||||
case VT_I4: result = (UInt64)(Int64)prop.lVal; break;
|
||||
case VT_UI8: result = (UInt64)prop.uhVal.QuadPart; break;
|
||||
case VT_I8: result = (UInt64)prop.hVal.QuadPart; break;
|
||||
case VT_EMPTY: return S_OK;
|
||||
default: return E_FAIL;
|
||||
}
|
||||
defined = true;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -513,13 +519,14 @@ static HRESULT Archive_GetArcProp_Int(IInArchive *arc, PROPID propid, Int64 &res
|
||||
RINOK(arc->GetArchiveProperty(propid, &prop));
|
||||
switch (prop.vt)
|
||||
{
|
||||
case VT_UI4: result = prop.ulVal; defined = true; break;
|
||||
case VT_I4: result = prop.lVal; defined = true; break;
|
||||
case VT_UI8: result = (Int64)prop.uhVal.QuadPart; defined = true; break;
|
||||
case VT_I8: result = (Int64)prop.hVal.QuadPart; defined = true; break;
|
||||
case VT_EMPTY: break;
|
||||
case VT_UI4: result = prop.ulVal; break;
|
||||
case VT_I4: result = prop.lVal; break;
|
||||
case VT_UI8: result = (Int64)prop.uhVal.QuadPart; break;
|
||||
case VT_I8: result = (Int64)prop.hVal.QuadPart; break;
|
||||
case VT_EMPTY: return S_OK;
|
||||
default: return E_FAIL;
|
||||
}
|
||||
defined = true;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -607,6 +614,8 @@ HRESULT CArc::GetItemPathToParent(UInt32 index, UInt32 parent, UStringVector &pa
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
HRESULT CArc::GetItemPath(UInt32 index, UString &result) const
|
||||
{
|
||||
#ifdef MY_CPU_LE
|
||||
@@ -621,19 +630,42 @@ HRESULT CArc::GetItemPath(UInt32 index, UString &result) const
|
||||
propType == NPropDataType::kUtf16z)
|
||||
{
|
||||
unsigned len = size / 2 - 1;
|
||||
// (len) doesn't include null terminator
|
||||
|
||||
/*
|
||||
#if WCHAR_MAX > 0xffff
|
||||
len = (unsigned)Utf16LE__Get_Num_WCHARs(p, len);
|
||||
|
||||
wchar_t *s = result.GetBuf(len);
|
||||
wchar_t *sEnd = Utf16LE__To_WCHARs_Sep(p, len, s);
|
||||
if (s + len != sEnd) return E_FAIL;
|
||||
*sEnd = 0;
|
||||
|
||||
#else
|
||||
*/
|
||||
|
||||
wchar_t *s = result.GetBuf(len);
|
||||
for (unsigned i = 0; i < len; i++)
|
||||
{
|
||||
wchar_t c = GetUi16(p);
|
||||
p = (const void *)((const Byte *)p + 2);
|
||||
|
||||
#if WCHAR_PATH_SEPARATOR != L'/'
|
||||
if (c == L'/')
|
||||
c = WCHAR_PATH_SEPARATOR;
|
||||
else if (c == L'\\')
|
||||
c = WCHAR_IN_FILE_NAME_BACKSLASH_REPLACEMENT; // WSL scheme
|
||||
#endif
|
||||
|
||||
*s++ = c;
|
||||
}
|
||||
*s = 0;
|
||||
|
||||
// #endif
|
||||
|
||||
result.ReleaseBuf_SetLen(len);
|
||||
|
||||
Convert_UnicodeEsc16_To_UnicodeEscHigh(result);
|
||||
if (len != 0)
|
||||
return S_OK;
|
||||
}
|
||||
@@ -721,6 +753,8 @@ HRESULT CArc::GetItemPath(UInt32 index, UString &result) const
|
||||
|
||||
if (result.IsEmpty())
|
||||
return GetDefaultItemPath(index, result);
|
||||
|
||||
Convert_UnicodeEsc16_To_UnicodeEscHigh(result);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -772,7 +806,7 @@ int FindAltStreamColon_in_Path(const wchar_t *path)
|
||||
if (c == ':')
|
||||
{
|
||||
if (colonPos < 0)
|
||||
colonPos = i;
|
||||
colonPos = (int)i;
|
||||
continue;
|
||||
}
|
||||
if (c == WCHAR_PATH_SEPARATOR)
|
||||
@@ -865,8 +899,8 @@ HRESULT CArc::GetItem(UInt32 index, CReadArcItem &item) const
|
||||
int colon = FindAltStreamColon_in_Path(item.Path);
|
||||
if (colon >= 0)
|
||||
{
|
||||
item.MainPath.DeleteFrom(colon);
|
||||
item.AltStreamName = item.Path.Ptr(colon + 1);
|
||||
item.MainPath.DeleteFrom((unsigned)colon);
|
||||
item.AltStreamName = item.Path.Ptr((unsigned)(colon + 1));
|
||||
item.MainIsDir = (colon == 0 || IsPathSepar(item.Path[(unsigned)colon - 1]));
|
||||
item.IsAltStream = true;
|
||||
}
|
||||
@@ -877,7 +911,7 @@ HRESULT CArc::GetItem(UInt32 index, CReadArcItem &item) const
|
||||
#ifndef _SFX
|
||||
if (item._use_baseParentFolder_mode)
|
||||
{
|
||||
RINOK(GetItemPathToParent(mainIndex, item._baseParentFolder, item.PathParts));
|
||||
RINOK(GetItemPathToParent(mainIndex, (unsigned)item._baseParentFolder, item.PathParts));
|
||||
|
||||
#ifdef SUPPORT_ALT_STREAMS
|
||||
if ((item.WriteToAltStreamIfColon || needFindAltStream) && !item.PathParts.IsEmpty())
|
||||
@@ -888,10 +922,10 @@ HRESULT CArc::GetItem(UInt32 index, CReadArcItem &item) const
|
||||
colon = FindAltStreamColon_in_Path(s);
|
||||
if (colon >= 0)
|
||||
{
|
||||
item.AltStreamName = s.Ptr(colon + 1);
|
||||
item.AltStreamName = s.Ptr((unsigned)(colon + 1));
|
||||
item.MainIsDir = (colon == 0 || IsPathSepar(s[(unsigned)colon - 1]));
|
||||
item.IsAltStream = true;
|
||||
s.DeleteFrom(colon);
|
||||
s.DeleteFrom((unsigned)colon);
|
||||
}
|
||||
}
|
||||
if (colon == 0)
|
||||
@@ -1007,9 +1041,9 @@ static void MakeCheckOrder(CCodecs *codecs,
|
||||
FOR_VECTOR (k, sigs)
|
||||
{
|
||||
const CByteBuffer &sig = sigs[k];
|
||||
if (sig.Size() == 0 && dataSize == 0 ||
|
||||
sig.Size() != 0 && sig.Size() <= dataSize &&
|
||||
TestSignature(data, sig, sig.Size()))
|
||||
if ((sig.Size() == 0 && dataSize == 0)
|
||||
|| (sig.Size() != 0 && sig.Size() <= dataSize
|
||||
&& TestSignature(data, sig, sig.Size())))
|
||||
{
|
||||
orderIndices2.Add(index);
|
||||
orderIndices[i] = -1;
|
||||
@@ -1019,8 +1053,6 @@ static void MakeCheckOrder(CCodecs *codecs,
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef UNDER_CE
|
||||
static const unsigned kNumHashBytes = 1;
|
||||
#define HASH_VAL(buf) ((buf)[0])
|
||||
@@ -1030,9 +1062,6 @@ static void MakeCheckOrder(CCodecs *codecs,
|
||||
#define HASH_VAL(buf) GetUi16(buf)
|
||||
#endif
|
||||
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
static bool IsExeExt(const UString &ext)
|
||||
{
|
||||
return ext.IsEqualTo_Ascii_NoCase("exe");
|
||||
@@ -1243,11 +1272,11 @@ HRESULT CArc::ReadBasicProps(IInArchive *archive, UInt64 startPos, HRESULT openR
|
||||
bool offsetDefined;
|
||||
RINOK(Archive_GetArcProp_Int(archive, kpidOffset, Offset, offsetDefined));
|
||||
|
||||
Int64 globalOffset = startPos + Offset;
|
||||
AvailPhySize = FileSize - globalOffset;
|
||||
Int64 globalOffset = (Int64)startPos + Offset;
|
||||
AvailPhySize = (UInt64)((Int64)FileSize - globalOffset);
|
||||
if (PhySizeDefined)
|
||||
{
|
||||
UInt64 endPos = globalOffset + PhySize;
|
||||
UInt64 endPos = (UInt64)(globalOffset + (Int64)PhySize);
|
||||
if (endPos < FileSize)
|
||||
{
|
||||
AvailPhySize = PhySize;
|
||||
@@ -1263,11 +1292,12 @@ HRESULT CArc::ReadBasicProps(IInArchive *archive, UInt64 startPos, HRESULT openR
|
||||
}
|
||||
|
||||
/*
|
||||
static PrintNumber(const char *s, int n)
|
||||
static void PrintNumber(const char *s, int n)
|
||||
{
|
||||
char temp[100];
|
||||
sprintf(temp, "%s %d", s, n);
|
||||
OutputDebugStringA(temp);
|
||||
// OutputDebugStringA(temp);
|
||||
printf(temp);
|
||||
}
|
||||
*/
|
||||
|
||||
@@ -1286,7 +1316,7 @@ HRESULT CArc::PrepareToOpen(const COpenOptions &op, unsigned formatIndex, CMyCom
|
||||
{
|
||||
const CArcInfoEx &ai = op.codecs->Formats[formatIndex];
|
||||
if (ai.LibIndex >= 0 ?
|
||||
!op.codecs->Libs[ai.LibIndex].SetCodecs :
|
||||
!op.codecs->Libs[(unsigned)ai.LibIndex].SetCodecs :
|
||||
!op.codecs->Libs.IsEmpty())
|
||||
{
|
||||
CMyComPtr<ISetCompressCodecsInfo> setCompressCodecsInfo;
|
||||
@@ -1437,7 +1467,7 @@ HRESULT CArc::CheckZerosTail(const COpenOptions &op, UInt64 offset)
|
||||
{
|
||||
if (!op.stream)
|
||||
return S_OK;
|
||||
RINOK(op.stream->Seek(offset, STREAM_SEEK_SET, NULL));
|
||||
RINOK(op.stream->Seek((Int64)offset, STREAM_SEEK_SET, NULL));
|
||||
const UInt32 kBufSize = 1 << 11;
|
||||
Byte buf[kBufSize];
|
||||
|
||||
@@ -1463,6 +1493,8 @@ HRESULT CArc::CheckZerosTail(const COpenOptions &op, UInt64 offset)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
class CExtractCallback_To_OpenCallback:
|
||||
@@ -1510,7 +1542,7 @@ STDMETHODIMP CExtractCallback_To_OpenCallback::SetRatioInfo(const UInt64 *inSize
|
||||
|
||||
STDMETHODIMP CExtractCallback_To_OpenCallback::GetStream(UInt32 /* index */, ISequentialOutStream **outStream, Int32 /* askExtractMode */)
|
||||
{
|
||||
*outStream = 0;
|
||||
*outStream = NULL;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -1524,6 +1556,7 @@ STDMETHODIMP CExtractCallback_To_OpenCallback::SetOperationResult(Int32 /* opera
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
static HRESULT OpenArchiveSpec(IInArchive *archive, bool needPhySize,
|
||||
IInStream *stream, const UInt64 *maxCheckStartPosition,
|
||||
IArchiveOpenCallback *openCallback,
|
||||
@@ -1547,22 +1580,32 @@ static HRESULT OpenArchiveSpec(IInArchive *archive, bool needPhySize,
|
||||
if (phySize_Defined)
|
||||
return S_OK;
|
||||
|
||||
bool phySizeCantBeDetected = false;;
|
||||
bool phySizeCantBeDetected = false;
|
||||
RINOK(Archive_GetArcBoolProp(archive, kpidPhySizeCantBeDetected, phySizeCantBeDetected));
|
||||
|
||||
if (!phySizeCantBeDetected)
|
||||
{
|
||||
RINOK(archive->Extract(0, (UInt32)(Int32)-1, BoolToInt(true), extractCallback));
|
||||
PRF(printf("\n-- !phySize_Defined after Open, call archive->Extract()"));
|
||||
// It's for bzip2/gz and some xz archives, where Open operation doesn't know phySize.
|
||||
// But the Handler will know phySize after full archive testing.
|
||||
RINOK(archive->Extract(NULL, (UInt32)(Int32)-1, BoolToInt(true), extractCallback));
|
||||
PRF(printf("\n-- OK"));
|
||||
}
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
static int FindFormatForArchiveType(CCodecs *codecs, CIntVector orderIndices, const char *name)
|
||||
{
|
||||
FOR_VECTOR (i, orderIndices)
|
||||
if (StringsAreEqualNoCase_Ascii(codecs->Formats[orderIndices[i]].Name, name))
|
||||
return i;
|
||||
{
|
||||
int oi = orderIndices[i];
|
||||
if (oi >= 0)
|
||||
if (StringsAreEqualNoCase_Ascii(codecs->Formats[(unsigned)oi].Name, name))
|
||||
return (int)i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -1590,7 +1633,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
{
|
||||
int dotPos = fileName.ReverseFind_Dot();
|
||||
if (dotPos >= 0)
|
||||
extension = fileName.Ptr(dotPos + 1);
|
||||
extension = fileName.Ptr((unsigned)(dotPos + 1));
|
||||
}
|
||||
|
||||
CIntVector orderIndices;
|
||||
@@ -1615,13 +1658,18 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
bool isUnknownExt = false;
|
||||
#endif
|
||||
|
||||
#ifndef _SFX
|
||||
bool isForced = false;
|
||||
#endif
|
||||
|
||||
unsigned numMainTypes = 0;
|
||||
int formatIndex = op.openType.FormatIndex;
|
||||
|
||||
if (formatIndex >= 0)
|
||||
{
|
||||
#ifndef _SFX
|
||||
isForced = true;
|
||||
#endif
|
||||
orderIndices.Add(formatIndex);
|
||||
numMainTypes = 1;
|
||||
isMainFormatArr[(unsigned)formatIndex] = true;
|
||||
@@ -1658,10 +1706,12 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
isNumber = true;
|
||||
}
|
||||
if (isNumber)
|
||||
{
|
||||
if (c == 'z' || c == 'Z')
|
||||
isZip = true;
|
||||
else
|
||||
isRar = true;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -1673,7 +1723,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
if (IgnoreSplit || !op.openType.CanReturnArc)
|
||||
if (ai.IsSplit())
|
||||
continue;
|
||||
if (op.excludedFormats->FindInSorted(i) >= 0)
|
||||
if (op.excludedFormats->FindInSorted((int)i) >= 0)
|
||||
continue;
|
||||
|
||||
#ifndef _SFX
|
||||
@@ -1683,17 +1733,17 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
|
||||
if (ai.FindExtension(extension) >= 0
|
||||
#ifndef _SFX
|
||||
|| isZip && StringsAreEqualNoCase_Ascii(ai.Name, "zip")
|
||||
|| isRar && StringsAreEqualNoCase_Ascii(ai.Name, "rar")
|
||||
|| (isZip && StringsAreEqualNoCase_Ascii(ai.Name, "zip"))
|
||||
|| (isRar && StringsAreEqualNoCase_Ascii(ai.Name, "rar"))
|
||||
#endif
|
||||
)
|
||||
{
|
||||
// PrintNumber("orderIndices.Insert", i);
|
||||
orderIndices.Insert(numFinded++, i);
|
||||
orderIndices.Insert(numFinded++, (int)i);
|
||||
isMainFormatArr[i] = true;
|
||||
}
|
||||
else
|
||||
orderIndices.Add(i);
|
||||
orderIndices.Add((int)i);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1739,8 +1789,8 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
const Byte kRarHeader[] = { 0x52 , 0x61, 0x72, 0x21, 0x1a, 0x07, 0x00 };
|
||||
if (TestSignature(buf, kRarHeader, 7) && buf[9] == 0x73 && (buf[10] & 1) != 0)
|
||||
{
|
||||
orderIndices2.Add(orderIndices[i]);
|
||||
orderIndices[i] = -1;
|
||||
orderIndices2.Add(orderIndices[(unsigned)i]);
|
||||
orderIndices[(unsigned)i] = -1;
|
||||
if (i >= (int)numFinded)
|
||||
numFinded++;
|
||||
}
|
||||
@@ -1785,10 +1835,10 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
int iUdf = FindFormatForArchiveType(op.codecs, orderIndices, "udf");
|
||||
if (iUdf > iIso && iIso >= 0)
|
||||
{
|
||||
int isoIndex = orderIndices[iIso];
|
||||
int udfIndex = orderIndices[iUdf];
|
||||
orderIndices[iUdf] = isoIndex;
|
||||
orderIndices[iIso] = udfIndex;
|
||||
int isoIndex = orderIndices[(unsigned)iIso];
|
||||
int udfIndex = orderIndices[(unsigned)iUdf];
|
||||
orderIndices[(unsigned)iUdf] = isoIndex;
|
||||
orderIndices[(unsigned)iIso] = udfIndex;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1842,12 +1892,14 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
for (unsigned i = 0; i < numCheckTypes; i++)
|
||||
{
|
||||
FormatIndex = orderIndices[i];
|
||||
|
||||
// orderIndices[] item cannot be negative here
|
||||
|
||||
bool exactOnly = false;
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
const CArcInfoEx &ai = op.codecs->Formats[FormatIndex];
|
||||
const CArcInfoEx &ai = op.codecs->Formats[(unsigned)FormatIndex];
|
||||
// OutputDebugStringW(ai.Name);
|
||||
if (i >= numMainTypes)
|
||||
{
|
||||
@@ -1871,7 +1923,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
|
||||
CMyComPtr<IInArchive> archive;
|
||||
|
||||
RINOK(PrepareToOpen(op, FormatIndex, archive));
|
||||
RINOK(PrepareToOpen(op, (unsigned)FormatIndex, archive));
|
||||
if (!archive)
|
||||
continue;
|
||||
|
||||
@@ -1948,7 +2000,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
bool thereIsTail = ErrorInfo.ThereIsTail;
|
||||
if (thereIsTail && mode.ZerosTailIsAllowed)
|
||||
{
|
||||
RINOK(CheckZerosTail(op, Offset + PhySize));
|
||||
RINOK(CheckZerosTail(op, (UInt64)(Offset + (Int64)PhySize)));
|
||||
if (ErrorInfo.IgnoreTail)
|
||||
thereIsTail = false;
|
||||
}
|
||||
@@ -2063,16 +2115,22 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
|
||||
for (i = 0; i < orderIndices.Size(); i++)
|
||||
{
|
||||
unsigned form = orderIndices[i];
|
||||
// orderIndices[] item cannot be negative here
|
||||
unsigned form = (unsigned)orderIndices[i];
|
||||
if (skipFrontalFormat[form])
|
||||
continue;
|
||||
|
||||
const CArcInfoEx &ai = op.codecs->Formats[form];
|
||||
|
||||
if (ai.IsSplit())
|
||||
{
|
||||
splitIndex = form;
|
||||
splitIndex = (int)form;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (ai.Flags_ByExtOnlyOpen())
|
||||
continue;
|
||||
|
||||
if (ai.IsArcFunc)
|
||||
{
|
||||
UInt32 isArcRes = ai.IsArcFunc(byteBuffer, processedSize);
|
||||
@@ -2118,12 +2176,12 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
|
||||
if (splitIndex >= 0)
|
||||
sortedFormats.Insert(0, splitIndex);
|
||||
sortedFormats.Insert(0, (unsigned)splitIndex);
|
||||
|
||||
for (i = 0; i < sortedFormats.Size(); i++)
|
||||
{
|
||||
FormatIndex = sortedFormats[i];
|
||||
const CArcInfoEx &ai = op.codecs->Formats[FormatIndex];
|
||||
FormatIndex = (int)sortedFormats[i];
|
||||
const CArcInfoEx &ai = op.codecs->Formats[(unsigned)FormatIndex];
|
||||
|
||||
if (op.callback)
|
||||
RINOK(op.callback->SetTotal(NULL, &fileSize));
|
||||
@@ -2131,7 +2189,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
RINOK(op.stream->Seek(0, STREAM_SEEK_SET, NULL));
|
||||
|
||||
CMyComPtr<IInArchive> archive;
|
||||
RINOK(PrepareToOpen(op, FormatIndex, archive));
|
||||
RINOK(PrepareToOpen(op, (unsigned)FormatIndex, archive));
|
||||
if (!archive)
|
||||
continue;
|
||||
|
||||
@@ -2144,7 +2202,10 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
result = archive->Open(op.stream, &searchLimit, op.callback);
|
||||
else
|
||||
*/
|
||||
result = OpenArchiveSpec(archive, !mode.CanReturnArc, op.stream, &searchLimit, op.callback, extractCallback_To_OpenCallback);
|
||||
// if (!CanReturnArc), it's ParserMode, and we need phy size
|
||||
result = OpenArchiveSpec(archive,
|
||||
!mode.CanReturnArc, // needPhySize
|
||||
op.stream, &searchLimit, op.callback, extractCallback_To_OpenCallback);
|
||||
}
|
||||
|
||||
if (result == S_FALSE)
|
||||
@@ -2166,7 +2227,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
|
||||
NArchive::NParser::CParseItem pi;
|
||||
pi.Offset = Offset;
|
||||
pi.Offset = (UInt64)Offset;
|
||||
pi.Size = AvailPhySize;
|
||||
|
||||
// bool needScan = false;
|
||||
@@ -2203,7 +2264,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
{
|
||||
if (mode.ZerosTailIsAllowed)
|
||||
{
|
||||
RINOK(CheckZerosTail(op, Offset + PhySize));
|
||||
RINOK(CheckZerosTail(op, (UInt64)(Offset + (Int64)PhySize)));
|
||||
if (ErrorInfo.IgnoreTail)
|
||||
openCur = true;
|
||||
}
|
||||
@@ -2299,6 +2360,8 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
if (index < 0)
|
||||
continue;
|
||||
const CArcInfoEx &ai = op.codecs->Formats[(unsigned)index];
|
||||
if (ai.Flags_ByExtOnlyOpen())
|
||||
continue;
|
||||
bool isDifficult = false;
|
||||
// if (ai.Version < 0x91F) // we don't use parser with old DLL (before 9.31)
|
||||
if (!ai.NewInterface)
|
||||
@@ -2329,7 +2392,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
if (isDifficult)
|
||||
{
|
||||
difficultFormats.Add(index);
|
||||
difficultFormats.Add((unsigned)index);
|
||||
difficultBools[(unsigned)index] = true;
|
||||
}
|
||||
}
|
||||
@@ -2398,7 +2461,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
size_t processedSize = kBufSize - bytesInBuf;
|
||||
// printf("\nRead ask = %d", (unsigned)processedSize);
|
||||
UInt64 seekPos = bufPhyPos + bytesInBuf;
|
||||
RINOK(op.stream->Seek(bufPhyPos + bytesInBuf, STREAM_SEEK_SET, NULL));
|
||||
RINOK(op.stream->Seek((Int64)(bufPhyPos + bytesInBuf), STREAM_SEEK_SET, NULL));
|
||||
RINOK(ReadStream(op.stream, byteBuffer + bytesInBuf, &processedSize));
|
||||
// printf(" processed = %d", (unsigned)processedSize);
|
||||
if (processedSize == 0)
|
||||
@@ -2471,7 +2534,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
}
|
||||
|
||||
size_t availSize = bytesInBuf - (size_t)posInBuf;
|
||||
const size_t availSize = bytesInBuf - (size_t)posInBuf;
|
||||
if (availSize < kNumHashBytes)
|
||||
break;
|
||||
size_t scanSize = availSize -
|
||||
@@ -2502,7 +2565,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
if (!needCheckStartOpen)
|
||||
{
|
||||
for (; buf < bufLimit && hash[HASH_VAL(buf)] == 0xFF; buf++);
|
||||
ppp = buf - (byteBuffer + (size_t)posInBuf);
|
||||
ppp = (size_t)(buf - (byteBuffer + (size_t)posInBuf));
|
||||
pos += ppp;
|
||||
if (buf == bufLimit)
|
||||
continue;
|
||||
@@ -2599,13 +2662,9 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
// printf("\nIsArc OK: %S", (const wchar_t *)ai.Name);
|
||||
}
|
||||
|
||||
/*
|
||||
if (pos == 67109888)
|
||||
pos = pos;
|
||||
*/
|
||||
PRF(printf("\npos = %9I64d : %S", pos, (const wchar_t *)ai.Name));
|
||||
|
||||
bool isMainFormat = isMainFormatArr[index];
|
||||
const bool isMainFormat = isMainFormatArr[index];
|
||||
const COpenSpecFlags &specFlags = mode.GetSpec(isForced, isMainFormat, isUnknownExt);
|
||||
|
||||
CMyComPtr<IInArchive> archive;
|
||||
@@ -2615,14 +2674,14 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
|
||||
// OutputDebugStringW(ai.Name);
|
||||
|
||||
UInt64 rem = fileSize - startArcPos;
|
||||
const UInt64 rem = fileSize - startArcPos;
|
||||
|
||||
UInt64 arcStreamOffset = 0;
|
||||
|
||||
if (ai.Flags_UseGlobalOffset())
|
||||
{
|
||||
limitedStreamSpec->InitAndSeek(0, fileSize);
|
||||
limitedStream->Seek(startArcPos, STREAM_SEEK_SET, NULL);
|
||||
limitedStream->Seek((Int64)startArcPos, STREAM_SEEK_SET, NULL);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -2642,20 +2701,23 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
extractCallback_To_OpenCallback_Spec->Files = 0;
|
||||
extractCallback_To_OpenCallback_Spec->Offset = startArcPos;
|
||||
|
||||
HRESULT result = OpenArchiveSpec(archive, true, limitedStream, &maxCheckStartPosition,
|
||||
HRESULT result = OpenArchiveSpec(archive,
|
||||
true, // needPhySize
|
||||
limitedStream, &maxCheckStartPosition,
|
||||
useOffsetCallback ? (IArchiveOpenCallback *)openCallback_Offset : (IArchiveOpenCallback *)op.callback,
|
||||
extractCallback_To_OpenCallback);
|
||||
|
||||
RINOK(ReadBasicProps(archive, ai.Flags_UseGlobalOffset() ? 0 : startArcPos, result));
|
||||
|
||||
bool isOpen = false;
|
||||
|
||||
if (result == S_FALSE)
|
||||
{
|
||||
if (!mode.CanReturnParser)
|
||||
{
|
||||
if (formatIndex < 0 && ErrorInfo.IsArc_After_NonOpen())
|
||||
{
|
||||
ErrorInfo.ErrorFormatIndex = index;
|
||||
ErrorInfo.ErrorFormatIndex = (int)index;
|
||||
NonOpen_ErrorInfo = ErrorInfo;
|
||||
// if archive was detected, we don't need additional open attempts
|
||||
return S_FALSE;
|
||||
@@ -2667,6 +2729,12 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
else
|
||||
{
|
||||
if (PhySizeDefined && PhySize == 0)
|
||||
{
|
||||
PRF(printf(" phySizeDefined && PhySize == 0 "));
|
||||
// we skip that epmty archive case with unusual unexpected (PhySize == 0) from Code function.
|
||||
continue;
|
||||
}
|
||||
isOpen = true;
|
||||
RINOK(result);
|
||||
PRF(printf(" OK "));
|
||||
@@ -2680,9 +2748,10 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
pi.Offset = startArcPos;
|
||||
|
||||
if (ai.Flags_UseGlobalOffset())
|
||||
pi.Offset = Offset;
|
||||
pi.Offset = (UInt64)Offset;
|
||||
else if (Offset != 0)
|
||||
return E_FAIL;
|
||||
|
||||
UInt64 arcRem = FileSize - pi.Offset;
|
||||
UInt64 phySize = arcRem;
|
||||
bool phySizeDefined = PhySizeDefined;
|
||||
@@ -2714,7 +2783,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
|
||||
if (isOpen && !phySizeDefined)
|
||||
{
|
||||
// it's for Z format
|
||||
// it's for Z format, or bzip2,gz,xz with phySize that was not detected
|
||||
pi.LenIsUnknown = true;
|
||||
needScan = true;
|
||||
phySize = arcRem;
|
||||
@@ -2786,7 +2855,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
bool thereIsTail = ErrorInfo.ThereIsTail;
|
||||
if (thereIsTail && mode.ZerosTailIsAllowed)
|
||||
{
|
||||
RINOK(CheckZerosTail(op, arcStreamOffset + Offset + PhySize));
|
||||
RINOK(CheckZerosTail(op, (UInt64)((Int64)arcStreamOffset + Offset + (Int64)PhySize)));
|
||||
if (ErrorInfo.IgnoreTail)
|
||||
thereIsTail = false;
|
||||
}
|
||||
@@ -2794,10 +2863,12 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
if (pi.Offset != 0)
|
||||
{
|
||||
if (!pi.IsNotArcType)
|
||||
{
|
||||
if (thereIsTail)
|
||||
openCur = specFlags.CanReturnMid;
|
||||
else
|
||||
openCur = specFlags.CanReturnTail;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -2805,11 +2876,11 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
openCur = true;
|
||||
else
|
||||
openCur = specFlags.CanReturnFrontal;
|
||||
|
||||
|
||||
if (formatIndex >= -2)
|
||||
openCur = true;
|
||||
}
|
||||
|
||||
if (formatIndex < 0 && pi.IsSelfExe /* && mode.SkipSfxStub */)
|
||||
openCur = false;
|
||||
|
||||
@@ -2836,7 +2907,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
{
|
||||
InStream = op.stream;
|
||||
Archive = archive;
|
||||
FormatIndex = index;
|
||||
FormatIndex = (int)index;
|
||||
ArcStreamOffset = arcStreamOffset;
|
||||
return S_OK;
|
||||
}
|
||||
@@ -2850,7 +2921,7 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
}
|
||||
*/
|
||||
|
||||
pi.FormatIndex = index;
|
||||
pi.FormatIndex = (int)index;
|
||||
|
||||
// printf("\nAdd offset = %d", (int)pi.Offset);
|
||||
handlerSpec->AddItem(pi);
|
||||
@@ -2905,6 +2976,9 @@ HRESULT CArc::OpenStream2(const COpenOptions &op)
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
HRESULT CArc::OpenStream(const COpenOptions &op)
|
||||
{
|
||||
RINOK(OpenStream2(op));
|
||||
@@ -2929,13 +3003,13 @@ HRESULT CArc::OpenStream(const COpenOptions &op)
|
||||
{
|
||||
int dotPos = fileName.ReverseFind_Dot();
|
||||
if (dotPos >= 0)
|
||||
extension = fileName.Ptr(dotPos + 1);
|
||||
extension = fileName.Ptr((unsigned)(dotPos + 1));
|
||||
}
|
||||
|
||||
DefaultName.Empty();
|
||||
if (FormatIndex >= 0)
|
||||
{
|
||||
const CArcInfoEx &ai = op.codecs->Formats[FormatIndex];
|
||||
const CArcInfoEx &ai = op.codecs->Formats[(unsigned)FormatIndex];
|
||||
if (ai.Exts.Size() == 0)
|
||||
DefaultName = GetDefaultName2(fileName, UString(), UString());
|
||||
else
|
||||
@@ -2943,7 +3017,7 @@ HRESULT CArc::OpenStream(const COpenOptions &op)
|
||||
int subExtIndex = ai.FindExtension(extension);
|
||||
if (subExtIndex < 0)
|
||||
subExtIndex = 0;
|
||||
const CArcExtInfo &extInfo = ai.Exts[subExtIndex];
|
||||
const CArcExtInfo &extInfo = ai.Exts[(unsigned)subExtIndex];
|
||||
DefaultName = GetDefaultName2(fileName, extInfo.Ext, extInfo.AddExt);
|
||||
}
|
||||
}
|
||||
@@ -2981,9 +3055,7 @@ HRESULT CArc::OpenStreamOrFile(COpenOptions &op)
|
||||
fileStream = fileStreamSpec;
|
||||
Path = filePath;
|
||||
if (!fileStreamSpec->Open(us2fs(Path)))
|
||||
{
|
||||
return GetLastError();
|
||||
}
|
||||
return GetLastError_noZero_HRESULT();
|
||||
op.stream = fileStream;
|
||||
#ifdef _SFX
|
||||
IgnoreSplit = true;
|
||||
@@ -3288,7 +3360,7 @@ HRESULT CArchiveLink::Open2(COpenOptions &op, IOpenCallbackUI *callbackUI)
|
||||
if (!op.stream && !op.stdInMode)
|
||||
{
|
||||
NFile::NDir::GetFullPathAndSplit(us2fs(op.filePath), prefix, name);
|
||||
openCallbackSpec->Init(prefix, name);
|
||||
RINOK(openCallbackSpec->Init2(prefix, name));
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -3340,7 +3412,7 @@ HRESULT CArc::ReOpen(const COpenOptions &op)
|
||||
CTailInStream *tailStreamSpec = new CTailInStream;
|
||||
stream2 = tailStreamSpec;
|
||||
tailStreamSpec->Stream = op.stream;
|
||||
tailStreamSpec->Offset = globalOffset;
|
||||
tailStreamSpec->Offset = (UInt64)globalOffset;
|
||||
tailStreamSpec->Init();
|
||||
RINOK(tailStreamSpec->SeekToStart());
|
||||
}
|
||||
@@ -3352,8 +3424,8 @@ HRESULT CArc::ReOpen(const COpenOptions &op)
|
||||
|
||||
if (res == S_OK)
|
||||
{
|
||||
RINOK(ReadBasicProps(Archive, globalOffset, res));
|
||||
ArcStreamOffset = globalOffset;
|
||||
RINOK(ReadBasicProps(Archive, (UInt64)globalOffset, res));
|
||||
ArcStreamOffset = (UInt64)globalOffset;
|
||||
if (ArcStreamOffset != 0)
|
||||
InStream = op.stream;
|
||||
}
|
||||
@@ -3393,14 +3465,14 @@ HRESULT CArchiveLink::ReOpen(COpenOptions &op)
|
||||
{
|
||||
FString dirPrefix, fileName;
|
||||
NFile::NDir::GetFullPathAndSplit(us2fs(op.filePath), dirPrefix, fileName);
|
||||
openCallbackSpec->Init(dirPrefix, fileName);
|
||||
RINOK(openCallbackSpec->Init2(dirPrefix, fileName));
|
||||
}
|
||||
|
||||
|
||||
CInFileStream *fileStreamSpec = new CInFileStream;
|
||||
CMyComPtr<IInStream> stream(fileStreamSpec);
|
||||
if (!fileStreamSpec->Open(us2fs(op.filePath)))
|
||||
return GetLastError();
|
||||
return GetLastError_noZero_HRESULT();
|
||||
op.stream = stream;
|
||||
|
||||
CArc &arc = Arcs[0];
|
||||
@@ -3415,6 +3487,7 @@ HRESULT CArchiveLink::ReOpen(COpenOptions &op)
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
bool ParseComplexSize(const wchar_t *s, UInt64 &result);
|
||||
bool ParseComplexSize(const wchar_t *s, UInt64 &result)
|
||||
{
|
||||
result = 0;
|
||||
@@ -3472,7 +3545,7 @@ static bool ParseTypeParams(const UString &s, COpenType &type)
|
||||
return false;
|
||||
}
|
||||
|
||||
bool ParseType(CCodecs &codecs, const UString &s, COpenType &type)
|
||||
static bool ParseType(CCodecs &codecs, const UString &s, COpenType &type)
|
||||
{
|
||||
int pos2 = s.Find(L':');
|
||||
|
||||
@@ -3481,11 +3554,11 @@ bool ParseType(CCodecs &codecs, const UString &s, COpenType &type)
|
||||
if (pos2 < 0)
|
||||
{
|
||||
name = s;
|
||||
pos2 = s.Len();
|
||||
pos2 = (int)s.Len();
|
||||
}
|
||||
else
|
||||
{
|
||||
name = s.Left(pos2);
|
||||
name = s.Left((unsigned)pos2);
|
||||
pos2++;
|
||||
}
|
||||
|
||||
@@ -3514,17 +3587,17 @@ bool ParseType(CCodecs &codecs, const UString &s, COpenType &type)
|
||||
|
||||
}
|
||||
|
||||
for (unsigned i = pos2; i < s.Len();)
|
||||
for (unsigned i = (unsigned)pos2; i < s.Len();)
|
||||
{
|
||||
int next = s.Find(L':', i);
|
||||
if (next < 0)
|
||||
next = s.Len();
|
||||
const UString name = s.Mid(i, next - i);
|
||||
next = (int)s.Len();
|
||||
const UString name = s.Mid(i, (unsigned)next - i);
|
||||
if (name.IsEmpty())
|
||||
return false;
|
||||
if (!ParseTypeParams(name, type))
|
||||
return false;
|
||||
i = next + 1;
|
||||
i = (unsigned)next + 1;
|
||||
}
|
||||
|
||||
return true;
|
||||
@@ -3537,15 +3610,15 @@ bool ParseOpenTypes(CCodecs &codecs, const UString &s, CObjectVector<COpenType>
|
||||
{
|
||||
int pos2 = s.Find(L'.', pos);
|
||||
if (pos2 < 0)
|
||||
pos2 = s.Len();
|
||||
UString name = s.Mid(pos, pos2 - pos);
|
||||
pos2 = (int)s.Len();
|
||||
UString name = s.Mid(pos, (unsigned)pos2 - pos);
|
||||
if (name.IsEmpty())
|
||||
return false;
|
||||
COpenType type;
|
||||
if (!ParseType(codecs, name, type))
|
||||
return false;
|
||||
types.Add(type);
|
||||
pos = pos2 + 1;
|
||||
pos = (unsigned)pos2 + 1;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -88,9 +88,9 @@ struct COpenType
|
||||
COpenType():
|
||||
FormatIndex(-1),
|
||||
Recursive(true),
|
||||
EachPos(false),
|
||||
CanReturnArc(true),
|
||||
CanReturnParser(false),
|
||||
EachPos(false),
|
||||
// SkipSfxStub(true),
|
||||
// ExeAsUnknown(true),
|
||||
ZerosTailIsAllowed(false),
|
||||
@@ -121,7 +121,7 @@ struct COpenOptions
|
||||
IInStream *stream;
|
||||
ISequentialInStream *seqStream;
|
||||
IArchiveOpenCallback *callback;
|
||||
COpenCallbackImp *callbackSpec;
|
||||
COpenCallbackImp *callbackSpec; // it's used for SFX only
|
||||
OPEN_PROPS_DECL
|
||||
// bool openOnlySpecifiedByExtension,
|
||||
|
||||
@@ -286,7 +286,7 @@ public:
|
||||
UString filePath;
|
||||
UString DefaultName;
|
||||
int FormatIndex; // - 1 means Parser.
|
||||
int SubfileIndex;
|
||||
UInt32 SubfileIndex; // (UInt32)(Int32)-1; means no subfile
|
||||
FILETIME MTime;
|
||||
bool MTimeDefined;
|
||||
|
||||
@@ -302,7 +302,7 @@ public:
|
||||
UInt64 GetEstmatedPhySize() const { return PhySizeDefined ? PhySize : FileSize; }
|
||||
|
||||
UInt64 ArcStreamOffset; // offset of stream that is open by Archive Handler
|
||||
Int64 GetGlobalOffset() const { return ArcStreamOffset + Offset; } // it's global offset of archive
|
||||
Int64 GetGlobalOffset() const { return (Int64)ArcStreamOffset + Offset; } // it's global offset of archive
|
||||
|
||||
// AString ErrorFlagsText;
|
||||
|
||||
@@ -397,6 +397,13 @@ struct CArchiveLink
|
||||
IArchiveGetRawProps *GetArchiveGetRawProps() const { return Arcs.Back().GetRawProps; }
|
||||
IArchiveGetRootProps *GetArchiveGetRootProps() const { return Arcs.Back().GetRootProps; }
|
||||
|
||||
/*
|
||||
Open() opens archive and COpenOptions::callback
|
||||
Open2() uses COpenCallbackImp that implements Volumes and password callback
|
||||
Open3() calls Open2() and callbackUI->Open_Finished();
|
||||
Open_Strict() returns S_FALSE also in case, if there is non-open expected nested archive.
|
||||
*/
|
||||
|
||||
HRESULT Open(COpenOptions &options);
|
||||
HRESULT Open2(COpenOptions &options, IOpenCallbackUI *callbackUI);
|
||||
HRESULT Open3(COpenOptions &options, IOpenCallbackUI *callbackUI);
|
||||
|
||||
@@ -14,8 +14,10 @@
|
||||
|
||||
#include "PropIDUtils.h"
|
||||
|
||||
#ifndef _SFX
|
||||
#define Get16(x) GetUi16(x)
|
||||
#define Get32(x) GetUi32(x)
|
||||
#endif
|
||||
|
||||
using namespace NWindows;
|
||||
|
||||
@@ -63,9 +65,9 @@ static void ConvertPosixAttribToString(char *s, UInt32 a) throw()
|
||||
s[8 - i] = MY_ATTR_CHAR(a, i + 1, 'w');
|
||||
s[9 - i] = MY_ATTR_CHAR(a, i + 0, 'x');
|
||||
}
|
||||
if ((a & 0x800) != 0) s[3] = ((a & (1 << 6)) ? 's' : 'S');
|
||||
if ((a & 0x400) != 0) s[6] = ((a & (1 << 3)) ? 's' : 'S');
|
||||
if ((a & 0x200) != 0) s[9] = ((a & (1 << 0)) ? 't' : 'T');
|
||||
if ((a & 0x800) != 0) s[3] = ((a & (1 << 6)) ? 's' : 'S'); // S_ISUID
|
||||
if ((a & 0x400) != 0) s[6] = ((a & (1 << 3)) ? 's' : 'S'); // S_ISGID
|
||||
if ((a & 0x200) != 0) s[9] = ((a & (1 << 0)) ? 't' : 'T'); // S_ISVTX
|
||||
s[10] = 0;
|
||||
|
||||
a &= ~(UInt32)0xFFFF;
|
||||
@@ -213,13 +215,13 @@ void ConvertPropertyToString2(UString &dest, const PROPVARIANT &prop, PROPID pro
|
||||
dest = temp;
|
||||
}
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
static inline unsigned GetHex(unsigned v)
|
||||
{
|
||||
return (v < 10) ? ('0' + v) : ('A' + (v - 10));
|
||||
}
|
||||
|
||||
#ifndef _SFX
|
||||
|
||||
static inline void AddHexToString(AString &res, unsigned v)
|
||||
{
|
||||
res += (char)GetHex(v >> 4);
|
||||
@@ -272,7 +274,7 @@ static int FindPairIndex(const CSecID2Name * pairs, unsigned num, UInt32 id)
|
||||
{
|
||||
for (unsigned i = 0; i < num; i++)
|
||||
if (pairs[i].n == id)
|
||||
return i;
|
||||
return (int)i;
|
||||
return -1;
|
||||
}
|
||||
|
||||
@@ -479,11 +481,16 @@ static void ParseAcl(AString &s, const Byte *p, UInt32 size, const char *strName
|
||||
*/
|
||||
}
|
||||
|
||||
/*
|
||||
#define MY_SE_OWNER_DEFAULTED (0x0001)
|
||||
#define MY_SE_GROUP_DEFAULTED (0x0002)
|
||||
*/
|
||||
#define MY_SE_DACL_PRESENT (0x0004)
|
||||
/*
|
||||
#define MY_SE_DACL_DEFAULTED (0x0008)
|
||||
*/
|
||||
#define MY_SE_SACL_PRESENT (0x0010)
|
||||
/*
|
||||
#define MY_SE_SACL_DEFAULTED (0x0020)
|
||||
#define MY_SE_DACL_AUTO_INHERIT_REQ (0x0100)
|
||||
#define MY_SE_SACL_AUTO_INHERIT_REQ (0x0200)
|
||||
@@ -493,6 +500,7 @@ static void ParseAcl(AString &s, const Byte *p, UInt32 size, const char *strName
|
||||
#define MY_SE_SACL_PROTECTED (0x2000)
|
||||
#define MY_SE_RM_CONTROL_VALID (0x4000)
|
||||
#define MY_SE_SELF_RELATIVE (0x8000)
|
||||
*/
|
||||
|
||||
void ConvertNtSecureToString(const Byte *data, UInt32 size, AString &s)
|
||||
{
|
||||
@@ -590,25 +598,45 @@ static const CSecID2Name k_ReparseTags[] =
|
||||
{ 0x80000014, "NFS" },
|
||||
{ 0x80000015, "FILE_PLACEHOLDER" },
|
||||
{ 0x80000016, "DFM" },
|
||||
{ 0x80000017, "WOF" }
|
||||
{ 0x80000017, "WOF" },
|
||||
{ 0x80000018, "WCI" },
|
||||
{ 0x8000001B, "APPEXECLINK" },
|
||||
{ 0xA000001D, "LX_SYMLINK" },
|
||||
{ 0x80000023, "AF_UNIX" },
|
||||
{ 0x80000024, "LX_FIFO" },
|
||||
{ 0x80000025, "LX_CHR" },
|
||||
{ 0x80000026, "LX_BLK" }
|
||||
};
|
||||
|
||||
bool ConvertNtReparseToString(const Byte *data, UInt32 size, UString &s)
|
||||
{
|
||||
s.Empty();
|
||||
NFile::CReparseAttr attr;
|
||||
DWORD errorCode = 0;
|
||||
if (attr.Parse(data, size, errorCode))
|
||||
|
||||
if (attr.Parse(data, size))
|
||||
{
|
||||
if (!attr.IsSymLink())
|
||||
s += "Junction: ";
|
||||
s += attr.GetPath();
|
||||
if (!attr.IsOkNamePair())
|
||||
if (attr.IsSymLink_WSL())
|
||||
{
|
||||
s += " : ";
|
||||
s += attr.PrintName;
|
||||
s += "WSL: ";
|
||||
s += attr.GetPath();
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!attr.IsSymLink_Win())
|
||||
s += "Junction: ";
|
||||
s += attr.GetPath();
|
||||
if (s.IsEmpty())
|
||||
s += "Link: ";
|
||||
if (!attr.IsOkNamePair())
|
||||
{
|
||||
s += " : ";
|
||||
s += attr.PrintName;
|
||||
}
|
||||
}
|
||||
if (attr.MinorError)
|
||||
s += " : MINOR_ERROR";
|
||||
return true;
|
||||
// s += " "; // for debug
|
||||
}
|
||||
|
||||
if (size < 8)
|
||||
@@ -651,7 +679,7 @@ bool ConvertNtReparseToString(const Byte *data, UInt32 size, UString &s)
|
||||
|
||||
for (UInt32 i = 0; i < len; i++)
|
||||
{
|
||||
if (i >= 8)
|
||||
if (i >= 16)
|
||||
{
|
||||
s += "...";
|
||||
break;
|
||||
|
||||
@@ -27,6 +27,21 @@ static void ParseNumberString(const UString &s, NCOM::CPropVariant &prop)
|
||||
prop = result;
|
||||
}
|
||||
|
||||
|
||||
struct CPropPropetiesVector
|
||||
{
|
||||
CPropVariant *values;
|
||||
CPropPropetiesVector(unsigned num)
|
||||
{
|
||||
values = new CPropVariant[num];
|
||||
}
|
||||
~CPropPropetiesVector()
|
||||
{
|
||||
delete []values;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
HRESULT SetProperties(IUnknown *unknown, const CObjectVector<CProperty> &properties)
|
||||
{
|
||||
if (properties.IsEmpty())
|
||||
@@ -37,8 +52,7 @@ HRESULT SetProperties(IUnknown *unknown, const CObjectVector<CProperty> &propert
|
||||
return S_OK;
|
||||
|
||||
UStringVector realNames;
|
||||
CPropVariant *values = new CPropVariant[properties.Size()];
|
||||
try
|
||||
CPropPropetiesVector values(properties.Size());
|
||||
{
|
||||
unsigned i;
|
||||
for (i = 0; i < properties.Size(); i++)
|
||||
@@ -62,19 +76,12 @@ HRESULT SetProperties(IUnknown *unknown, const CObjectVector<CProperty> &propert
|
||||
else
|
||||
ParseNumberString(property.Value, propVariant);
|
||||
realNames.Add(name);
|
||||
values[i] = propVariant;
|
||||
values.values[i] = propVariant;
|
||||
}
|
||||
CRecordVector<const wchar_t *> names;
|
||||
for (i = 0; i < realNames.Size(); i++)
|
||||
names.Add((const wchar_t *)realNames[i]);
|
||||
|
||||
RINOK(setProperties->SetProperties(&names.Front(), values, names.Size()));
|
||||
return setProperties->SetProperties(&names.Front(), values.values, names.Size());
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
delete []values;
|
||||
throw;
|
||||
}
|
||||
delete []values;
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -32,7 +32,7 @@
|
||||
static const char * const kUpdateIsNotSupoorted =
|
||||
"update operations are not supported for this archive";
|
||||
|
||||
static const char * const kUpdateIsNotSupoorted_MultiVol =
|
||||
static const char * const kUpdateIsNotSupported_MultiVol =
|
||||
"Updating for multivolume archives is not implemented";
|
||||
|
||||
using namespace NWindows;
|
||||
@@ -41,8 +41,9 @@ using namespace NFile;
|
||||
using namespace NDir;
|
||||
using namespace NName;
|
||||
|
||||
#ifdef _WIN32
|
||||
static CFSTR const kTempFolderPrefix = FTEXT("7zE");
|
||||
|
||||
#endif
|
||||
|
||||
void CUpdateErrorInfo::SetFromLastError(const char *message)
|
||||
{
|
||||
@@ -57,26 +58,12 @@ HRESULT CUpdateErrorInfo::SetFromLastError(const char *message, const FString &f
|
||||
return Get_HRESULT_Error();
|
||||
}
|
||||
|
||||
static bool DeleteEmptyFolderAndEmptySubFolders(const FString &path)
|
||||
HRESULT CUpdateErrorInfo::SetFromError_DWORD(const char *message, const FString &fileName, DWORD error)
|
||||
{
|
||||
NFind::CFileInfo fileInfo;
|
||||
FString pathPrefix = path + FCHAR_PATH_SEPARATOR;
|
||||
{
|
||||
NFind::CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(pathPrefix);
|
||||
while (enumerator.Next(fileInfo))
|
||||
{
|
||||
if (fileInfo.IsDir())
|
||||
if (!DeleteEmptyFolderAndEmptySubFolders(pathPrefix + fileInfo.Name))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
/*
|
||||
// we don't need clear read-only for folders
|
||||
if (!MySetFileAttributes(path, 0))
|
||||
return false;
|
||||
*/
|
||||
return RemoveDir(path);
|
||||
Message = message;
|
||||
FileNames.Add(fileName);
|
||||
SystemError = error;
|
||||
return Get_HRESULT_Error();
|
||||
}
|
||||
|
||||
|
||||
@@ -175,7 +162,7 @@ STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *pr
|
||||
altStream.StreamSpec = new COutFileStream;
|
||||
altStream.Stream = altStream.StreamSpec;
|
||||
if (!altStream.StreamSpec->Create(name, false))
|
||||
return ::GetLastError();
|
||||
return GetLastError_noZero_HRESULT();
|
||||
{
|
||||
// NSynchronization::CCriticalSectionLock lock(g_TempPathsCS);
|
||||
TempFiles->Paths.Add(name);
|
||||
@@ -204,14 +191,14 @@ STDMETHODIMP COutMultiVolStream::Write(const void *data, UInt32 size, UInt32 *pr
|
||||
{
|
||||
// CMyComPtr<IOutStream> outStream;
|
||||
// RINOK(altStream.Stream.QueryInterface(IID_IOutStream, &outStream));
|
||||
RINOK(altStream.Stream->Seek(_offsetPos, STREAM_SEEK_SET, NULL));
|
||||
RINOK(altStream.Stream->Seek((Int64)_offsetPos, STREAM_SEEK_SET, NULL));
|
||||
altStream.Pos = _offsetPos;
|
||||
}
|
||||
|
||||
UInt32 curSize = (UInt32)MyMin((UInt64)size, volSize - altStream.Pos);
|
||||
UInt32 realProcessed;
|
||||
RINOK(altStream.Stream->Write(data, curSize, &realProcessed));
|
||||
data = (void *)((Byte *)data + realProcessed);
|
||||
data = (const void *)((const Byte *)data + realProcessed);
|
||||
size -= realProcessed;
|
||||
altStream.Pos += realProcessed;
|
||||
_offsetPos += realProcessed;
|
||||
@@ -240,9 +227,9 @@ STDMETHODIMP COutMultiVolStream::Seek(Int64 offset, UInt32 seekOrigin, UInt64 *n
|
||||
return STG_E_INVALIDFUNCTION;
|
||||
switch (seekOrigin)
|
||||
{
|
||||
case STREAM_SEEK_SET: _absPos = offset; break;
|
||||
case STREAM_SEEK_CUR: _absPos += offset; break;
|
||||
case STREAM_SEEK_END: _absPos = _length + offset; break;
|
||||
case STREAM_SEEK_SET: _absPos = (UInt64)offset; break;
|
||||
case STREAM_SEEK_CUR: _absPos = (UInt64)((Int64)_absPos + offset); break;
|
||||
case STREAM_SEEK_END: _absPos = (UInt64)((Int64)_length + offset); break;
|
||||
}
|
||||
_offsetPos = _absPos;
|
||||
if (newPosition)
|
||||
@@ -298,11 +285,11 @@ void CArchivePath::ParseFromPath(const UString &path, EArcNameMode mode)
|
||||
Name.DeleteBack();
|
||||
else
|
||||
{
|
||||
const UString ext = Name.Ptr(dotPos + 1);
|
||||
const UString ext = Name.Ptr((unsigned)(dotPos + 1));
|
||||
if (BaseExtension.IsEqualTo_NoCase(ext))
|
||||
{
|
||||
BaseExtension = ext;
|
||||
Name.DeleteFrom(dotPos);
|
||||
Name.DeleteFrom((unsigned)dotPos);
|
||||
return;
|
||||
}
|
||||
}
|
||||
@@ -392,7 +379,7 @@ bool CUpdateOptions::SetArcPath(const CCodecs *codecs, const UString &arcPath)
|
||||
}
|
||||
else
|
||||
{
|
||||
const CArcInfoEx &arcInfo = codecs->Formats[formatIndex];
|
||||
const CArcInfoEx &arcInfo = codecs->Formats[(unsigned)formatIndex];
|
||||
if (!arcInfo.UpdateEnabled)
|
||||
return false;
|
||||
typeExt = arcInfo.GetMainExt();
|
||||
@@ -417,8 +404,8 @@ bool CUpdateOptions::SetArcPath(const CCodecs *codecs, const UString &arcPath)
|
||||
struct CUpdateProduceCallbackImp: public IUpdateProduceCallback
|
||||
{
|
||||
const CObjectVector<CArcItem> *_arcItems;
|
||||
IUpdateCallbackUI *_callback;
|
||||
CDirItemsStat *_stat;
|
||||
IUpdateCallbackUI *_callback;
|
||||
|
||||
CUpdateProduceCallbackImp(
|
||||
const CObjectVector<CArcItem> *a,
|
||||
@@ -541,7 +528,7 @@ static HRESULT Compress(
|
||||
}
|
||||
else
|
||||
{
|
||||
RINOK(codecs->CreateOutArchive(formatIndex, outArchive));
|
||||
RINOK(codecs->CreateOutArchive((unsigned)formatIndex, outArchive));
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
{
|
||||
@@ -576,7 +563,7 @@ static HRESULT Compress(
|
||||
}
|
||||
|
||||
{
|
||||
const CArcInfoEx &arcInfo = codecs->Formats[formatIndex];
|
||||
const CArcInfoEx &arcInfo = codecs->Formats[(unsigned)formatIndex];
|
||||
if (options.AltStreams.Val && !arcInfo.Flags_AltStreams())
|
||||
return E_NOTIMPL;
|
||||
if (options.NtSecurity.Val && !arcInfo.Flags_NtSecure())
|
||||
@@ -614,7 +601,7 @@ static HRESULT Compress(
|
||||
int colonPos = FindAltStreamColon_in_Path(ai.Name);
|
||||
if (colonPos >= 0)
|
||||
{
|
||||
UString mainName = ai.Name.Left(colonPos);
|
||||
UString mainName = ai.Name.Left((unsigned)colonPos);
|
||||
/*
|
||||
actually we must improve that code to support cases
|
||||
with folder renaming like: rn arc dir1\ dir2\
|
||||
@@ -623,7 +610,7 @@ static HRESULT Compress(
|
||||
{
|
||||
needRename = true;
|
||||
dest += ':';
|
||||
dest += ai.Name.Ptr(colonPos + 1);
|
||||
dest += ai.Name.Ptr((unsigned)(colonPos + 1));
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -638,7 +625,7 @@ static HRESULT Compress(
|
||||
{
|
||||
up2.NewProps = true;
|
||||
RINOK(arc->IsItemAnti(i, up2.IsAnti));
|
||||
up2.NewNameIndex = newNames.Add(dest);
|
||||
up2.NewNameIndex = (int)newNames.Add(dest);
|
||||
}
|
||||
updatePairs2.Add(up2);
|
||||
}
|
||||
@@ -664,7 +651,7 @@ static HRESULT Compress(
|
||||
if (up.ExistOnDisk())
|
||||
{
|
||||
CDirItemsStat2 &stat = stat2.NewData;
|
||||
const CDirItem &di = dirItems.Items[up.DirIndex];
|
||||
const CDirItem &di = dirItems.Items[(unsigned)up.DirIndex];
|
||||
if (di.IsDir())
|
||||
{
|
||||
if (up.IsAnti)
|
||||
@@ -697,7 +684,7 @@ static HRESULT Compress(
|
||||
else if (up.ArcIndex >= 0)
|
||||
{
|
||||
CDirItemsStat2 &stat = *(up.NewData ? &stat2.NewData : &stat2.OldData);
|
||||
const CArcItem &ai = arcItems[up.ArcIndex];
|
||||
const CArcItem &ai = arcItems[(unsigned)up.ArcIndex];
|
||||
if (ai.IsDir)
|
||||
{
|
||||
if (up.IsAnti)
|
||||
@@ -733,6 +720,7 @@ static HRESULT Compress(
|
||||
CArchiveUpdateCallback *updateCallbackSpec = new CArchiveUpdateCallback;
|
||||
CMyComPtr<IArchiveUpdateCallback> updateCallback(updateCallbackSpec);
|
||||
|
||||
updateCallbackSpec->PreserveATime = options.PreserveATime;
|
||||
updateCallbackSpec->ShareForWrite = options.OpenShareForWrite;
|
||||
updateCallbackSpec->StopAfterOpenError = options.StopAfterOpenError;
|
||||
updateCallbackSpec->StdInMode = options.StdInMode;
|
||||
@@ -922,9 +910,9 @@ static HRESULT Compress(
|
||||
CUpdatePair2 &pair2 = updatePairs2[i];
|
||||
const FILETIME *ft2 = NULL;
|
||||
if (pair2.NewProps && pair2.DirIndex >= 0)
|
||||
ft2 = &dirItems.Items[pair2.DirIndex].MTime;
|
||||
ft2 = &dirItems.Items[(unsigned)pair2.DirIndex].MTime;
|
||||
else if (pair2.UseArcProps && pair2.ArcIndex >= 0)
|
||||
ft2 = &arcItems[pair2.ArcIndex].MTime;
|
||||
ft2 = &arcItems[(unsigned)pair2.ArcIndex].MTime;
|
||||
if (ft2)
|
||||
{
|
||||
if (::CompareFileTime(&ft, ft2) < 0)
|
||||
@@ -936,7 +924,7 @@ static HRESULT Compress(
|
||||
if (outStreamSpec)
|
||||
outStreamSpec->SetMTime(&ft);
|
||||
else if (volStreamSpec)
|
||||
volStreamSpec->SetMTime(&ft);;
|
||||
volStreamSpec->SetMTime(&ft);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1041,7 +1029,7 @@ static HRESULT EnumerateInArchiveItems(
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
|
||||
#include <mapi.h>
|
||||
#include <MAPI.h>
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1074,7 +1062,7 @@ HRESULT UpdateArchive(
|
||||
if (options.Commands.Size() != 1)
|
||||
return E_NOTIMPL;
|
||||
const CActionSet &as = options.Commands[0].ActionSet;
|
||||
for (int i = 2; i < NPairState::kNumValues; i++)
|
||||
for (unsigned i = 2; i < NPairState::kNumValues; i++)
|
||||
if (as.StateActions[i] != NPairAction::kCompress)
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
@@ -1103,7 +1091,7 @@ HRESULT UpdateArchive(
|
||||
if (options.SfxModule.Find(FCHAR_PATH_SEPARATOR) < 0)
|
||||
{
|
||||
const FString fullName = NDLL::GetModuleDirPrefix() + options.SfxModule;
|
||||
if (NFind::DoesFileExist(fullName))
|
||||
if (NFind::DoesFileExist_FollowLink(fullName))
|
||||
{
|
||||
options.SfxModule = fullName;
|
||||
found = true;
|
||||
@@ -1111,7 +1099,7 @@ HRESULT UpdateArchive(
|
||||
}
|
||||
if (!found)
|
||||
{
|
||||
if (!NFind::DoesFileExist(options.SfxModule))
|
||||
if (!NFind::DoesFileExist_FollowLink(options.SfxModule))
|
||||
return errorInfo.SetFromLastError("cannot find specified SFX module", options.SfxModule);
|
||||
}
|
||||
}
|
||||
@@ -1143,7 +1131,7 @@ HRESULT UpdateArchive(
|
||||
else
|
||||
{
|
||||
NFind::CFileInfo fi;
|
||||
if (!fi.Find(us2fs(arcPath)))
|
||||
if (!fi.Find_FollowLink(us2fs(arcPath)))
|
||||
{
|
||||
if (renameMode)
|
||||
throw "can't find archive";;
|
||||
@@ -1156,24 +1144,35 @@ HRESULT UpdateArchive(
|
||||
else
|
||||
{
|
||||
if (fi.IsDir())
|
||||
throw "there is no such archive";
|
||||
return errorInfo.SetFromError_DWORD("There is a folder with the name of archive",
|
||||
us2fs(arcPath),
|
||||
#ifdef _WIN32
|
||||
ERROR_ACCESS_DENIED
|
||||
#else
|
||||
EISDIR
|
||||
#endif
|
||||
);
|
||||
if (fi.IsDevice)
|
||||
return E_NOTIMPL;
|
||||
|
||||
if (!options.StdOutMode && options.UpdateArchiveItself)
|
||||
if (fi.IsReadOnly())
|
||||
{
|
||||
errorInfo.SystemError = ERROR_ACCESS_DENIED;
|
||||
errorInfo.Message = "The file is read-only";
|
||||
errorInfo.FileNames.Add(us2fs(arcPath));
|
||||
return errorInfo.Get_HRESULT_Error();
|
||||
return errorInfo.SetFromError_DWORD("The file is read-only",
|
||||
us2fs(arcPath),
|
||||
#ifdef _WIN32
|
||||
ERROR_ACCESS_DENIED
|
||||
#else
|
||||
EACCES
|
||||
#endif
|
||||
);
|
||||
}
|
||||
|
||||
if (options.VolumesSizes.Size() > 0)
|
||||
{
|
||||
errorInfo.FileNames.Add(us2fs(arcPath));
|
||||
errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
errorInfo.Message = kUpdateIsNotSupoorted_MultiVol;
|
||||
// errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
errorInfo.Message = kUpdateIsNotSupported_MultiVol;
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
CObjectVector<COpenType> types2;
|
||||
@@ -1211,8 +1210,8 @@ HRESULT UpdateArchive(
|
||||
|
||||
if (arcLink.VolumePaths.Size() > 1)
|
||||
{
|
||||
errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
errorInfo.Message = kUpdateIsNotSupoorted_MultiVol;
|
||||
// errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
errorInfo.Message = kUpdateIsNotSupported_MultiVol;
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
@@ -1222,7 +1221,7 @@ HRESULT UpdateArchive(
|
||||
|
||||
if (arc.ErrorInfo.ThereIsTail)
|
||||
{
|
||||
errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
// errorInfo.SystemError = (DWORD)E_NOTIMPL;
|
||||
errorInfo.Message = "There is some data block after the end of the archive";
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
@@ -1292,7 +1291,7 @@ HRESULT UpdateArchive(
|
||||
|
||||
HRESULT res = EnumerateItems(censor,
|
||||
options.PathMode,
|
||||
options.AddPathPrefix,
|
||||
UString(), // options.AddPathPrefix,
|
||||
dirItems);
|
||||
|
||||
if (res != S_OK)
|
||||
@@ -1332,8 +1331,6 @@ HRESULT UpdateArchive(
|
||||
dirItems.AddSecurityItem(prefix, secureIndex);
|
||||
#endif
|
||||
parentDirItem.SecureIndex = secureIndex;
|
||||
|
||||
parentDirItem_Ptr = &parentDirItem;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1565,7 +1562,7 @@ HRESULT UpdateArchive(
|
||||
}
|
||||
*/
|
||||
|
||||
LPMAPISENDMAIL sendMail = (LPMAPISENDMAIL)mapiLib.GetProc("MAPISendMail");
|
||||
LPMAPISENDMAIL sendMail = (LPMAPISENDMAIL)(void *)mapiLib.GetProc("MAPISendMail");
|
||||
if (sendMail == 0)
|
||||
{
|
||||
errorInfo.SetFromLastError("7-Zip cannot find MAPISendMail function");
|
||||
@@ -1610,8 +1607,8 @@ HRESULT UpdateArchive(
|
||||
MapiFileDesc &f = files[i];
|
||||
memset(&f, 0, sizeof(f));
|
||||
f.nPosition = 0xFFFFFFFF;
|
||||
f.lpszPathName = (char *)(const char *)paths[i];
|
||||
f.lpszFileName = (char *)(const char *)names[i];
|
||||
f.lpszPathName = paths[i].Ptr_non_const();
|
||||
f.lpszFileName = names[i].Ptr_non_const();
|
||||
}
|
||||
|
||||
{
|
||||
@@ -1626,7 +1623,7 @@ HRESULT UpdateArchive(
|
||||
{
|
||||
memset(&rec, 0, sizeof(rec));
|
||||
rec.ulRecipClass = MAPI_TO;
|
||||
rec.lpszAddress = (char *)(const char *)addr;
|
||||
rec.lpszAddress = addr.Ptr_non_const();
|
||||
m.nRecipCount = 1;
|
||||
m.lpRecips = &rec;
|
||||
}
|
||||
@@ -1660,8 +1657,12 @@ HRESULT UpdateArchive(
|
||||
if (processedItems[i] != 0 || dirItem.Size == 0)
|
||||
{
|
||||
NFind::CFileInfo fileInfo;
|
||||
/* here we compare Raw FileInfo that can be link with actual file info that was processed.
|
||||
we can fix it. */
|
||||
if (fileInfo.Find(phyPath))
|
||||
{
|
||||
// FIXME: here we can check Find_FollowLink() also;
|
||||
|
||||
// maybe we must exclude also files with archive name: "a a.7z * -sdel"
|
||||
if (fileInfo.Size == dirItem.Size
|
||||
&& CompareFileTime(&fileInfo.MTime, &dirItem.MTime) == 0
|
||||
|
||||
@@ -18,7 +18,7 @@ enum EArcNameMode
|
||||
{
|
||||
k_ArcNameMode_Smart,
|
||||
k_ArcNameMode_Exact,
|
||||
k_ArcNameMode_Add,
|
||||
k_ArcNameMode_Add
|
||||
};
|
||||
|
||||
struct CArchivePath
|
||||
@@ -91,6 +91,7 @@ struct CUpdateOptions
|
||||
bool SfxMode;
|
||||
FString SfxModule;
|
||||
|
||||
bool PreserveATime;
|
||||
bool OpenShareForWrite;
|
||||
bool StopAfterOpenError;
|
||||
|
||||
@@ -104,7 +105,7 @@ struct CUpdateOptions
|
||||
|
||||
FString WorkingDir;
|
||||
NWildcard::ECensorPathMode PathMode;
|
||||
UString AddPathPrefix;
|
||||
// UString AddPathPrefix;
|
||||
|
||||
CBoolPair NtSecurity;
|
||||
CBoolPair AltStreams;
|
||||
@@ -122,20 +123,26 @@ struct CUpdateOptions
|
||||
|
||||
CUpdateOptions():
|
||||
UpdateArchiveItself(true),
|
||||
ArcNameMode(k_ArcNameMode_Smart),
|
||||
|
||||
SfxMode(false),
|
||||
StdInMode(false),
|
||||
StdOutMode(false),
|
||||
EMailMode(false),
|
||||
EMailRemoveAfter(false),
|
||||
|
||||
PreserveATime(false),
|
||||
OpenShareForWrite(false),
|
||||
StopAfterOpenError(false),
|
||||
ArcNameMode(k_ArcNameMode_Smart),
|
||||
|
||||
StdInMode(false),
|
||||
StdOutMode(false),
|
||||
|
||||
EMailMode(false),
|
||||
EMailRemoveAfter(false),
|
||||
|
||||
PathMode(NWildcard::k_RelatPath),
|
||||
|
||||
DeleteAfterCompressing(false),
|
||||
SetArcMTime(false)
|
||||
|
||||
{};
|
||||
{};
|
||||
|
||||
void SetActionCommand_Add()
|
||||
{
|
||||
@@ -150,7 +157,7 @@ struct CUpdateOptions
|
||||
|
||||
struct CUpdateErrorInfo
|
||||
{
|
||||
DWORD SystemError;
|
||||
DWORD SystemError; // it's DWORD (WRes) only;
|
||||
AString Message;
|
||||
FStringVector FileNames;
|
||||
|
||||
@@ -158,6 +165,7 @@ struct CUpdateErrorInfo
|
||||
HRESULT Get_HRESULT_Error() const { return SystemError == 0 ? E_FAIL : HRESULT_FROM_WIN32(SystemError); }
|
||||
void SetFromLastError(const char *message);
|
||||
HRESULT SetFromLastError(const char *message, const FString &fileName);
|
||||
HRESULT SetFromError_DWORD(const char *message, const FString &fileName, DWORD error);
|
||||
|
||||
CUpdateErrorInfo(): SystemError(0) {};
|
||||
};
|
||||
|
||||
@@ -2,6 +2,8 @@
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
// #include <stdio.h>
|
||||
|
||||
#ifndef _7ZIP_ST
|
||||
#include "../../../Windows/Synchronization.h"
|
||||
#endif
|
||||
@@ -10,6 +12,7 @@
|
||||
#include "../../../Common/IntToString.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "../../../Common/Wildcard.h"
|
||||
#include "../../../Common/UTFConvert.h"
|
||||
|
||||
#include "../../../Windows/FileDir.h"
|
||||
#include "../../../Windows/FileName.h"
|
||||
@@ -54,6 +57,7 @@ CArchiveUpdateCallback::CArchiveUpdateCallback():
|
||||
CommentIndex(-1),
|
||||
Comment(NULL),
|
||||
|
||||
PreserveATime(false),
|
||||
ShareForWrite(false),
|
||||
StopAfterOpenError(false),
|
||||
StdInMode(false),
|
||||
@@ -124,7 +128,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetUpdateItemInfo(UInt32 index,
|
||||
{
|
||||
*indexInArchive = (UInt32)(Int32)-1;
|
||||
if (up.ExistInArchive())
|
||||
*indexInArchive = (ArcItems == 0) ? up.ArcIndex : (*ArcItems)[up.ArcIndex].IndexInServer;
|
||||
*indexInArchive = ArcItems ? (*ArcItems)[(unsigned)up.ArcIndex].IndexInServer : (UInt32)(Int32)up.ArcIndex;
|
||||
}
|
||||
return S_OK;
|
||||
COM_TRY_END
|
||||
@@ -188,7 +192,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetRootRawProp(PROPID
|
||||
{
|
||||
if (ParentDirItem->SecureIndex < 0)
|
||||
return S_OK;
|
||||
const CByteBuffer &buf = DirItems->SecureBlocks.Bufs[ParentDirItem->SecureIndex];
|
||||
const CByteBuffer &buf = DirItems->SecureBlocks.Bufs[(unsigned)ParentDirItem->SecureIndex];
|
||||
*data = buf;
|
||||
*dataSize = (UInt32)buf.Size();
|
||||
*propType = NPropDataType::kRaw;
|
||||
@@ -220,7 +224,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetRawProp(UInt32 index, PROPID propID, con
|
||||
const CUpdatePair2 &up = (*UpdatePairs)[index];
|
||||
if (up.UseArcProps && up.ExistInArchive() && Arc->GetRawProps)
|
||||
return Arc->GetRawProps->GetRawProp(
|
||||
ArcItems ? (*ArcItems)[up.ArcIndex].IndexInServer : up.ArcIndex,
|
||||
ArcItems ? (*ArcItems)[(unsigned)up.ArcIndex].IndexInServer : (UInt32)(Int32)up.ArcIndex,
|
||||
propID, data, dataSize, propType);
|
||||
{
|
||||
/*
|
||||
@@ -230,8 +234,8 @@ STDMETHODIMP CArchiveUpdateCallback::GetRawProp(UInt32 index, PROPID propID, con
|
||||
if (up.IsAnti)
|
||||
return S_OK;
|
||||
|
||||
#ifndef UNDER_CE
|
||||
const CDirItem &di = DirItems->Items[up.DirIndex];
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
const CDirItem &di = DirItems->Items[(unsigned)up.DirIndex];
|
||||
#endif
|
||||
|
||||
#ifdef _USE_SECURITY_CODE
|
||||
@@ -241,18 +245,19 @@ STDMETHODIMP CArchiveUpdateCallback::GetRawProp(UInt32 index, PROPID propID, con
|
||||
return S_OK;
|
||||
if (di.SecureIndex < 0)
|
||||
return S_OK;
|
||||
const CByteBuffer &buf = DirItems->SecureBlocks.Bufs[di.SecureIndex];
|
||||
const CByteBuffer &buf = DirItems->SecureBlocks.Bufs[(unsigned)di.SecureIndex];
|
||||
*data = buf;
|
||||
*dataSize = (UInt32)buf.Size();
|
||||
*propType = NPropDataType::kRaw;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
if (propID == kpidNtReparse)
|
||||
{
|
||||
// propID == kpidNtReparse
|
||||
if (!StoreSymLinks)
|
||||
return S_OK;
|
||||
#ifndef UNDER_CE
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
// we use ReparseData2 instead of ReparseData for WIM format
|
||||
const CByteBuffer *buf = &di.ReparseData2;
|
||||
if (buf->Size() == 0)
|
||||
buf = &di.ReparseData;
|
||||
@@ -272,7 +277,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetRawProp(UInt32 index, PROPID propID, con
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
#ifndef UNDER_CE
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
|
||||
static UString GetRelativePath(const UString &to, const UString &from)
|
||||
{
|
||||
@@ -340,22 +345,25 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
prop.Detach(value);
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
#if !defined(UNDER_CE)
|
||||
|
||||
if (up.DirIndex >= 0)
|
||||
{
|
||||
#ifndef UNDER_CE
|
||||
const CDirItem &di = DirItems->Items[up.DirIndex];
|
||||
const CDirItem &di = DirItems->Items[(unsigned)up.DirIndex];
|
||||
|
||||
#ifdef _WIN32
|
||||
// if (di.IsDir())
|
||||
{
|
||||
CReparseAttr attr;
|
||||
DWORD errorCode = 0;
|
||||
if (attr.Parse(di.ReparseData, di.ReparseData.Size(), errorCode))
|
||||
if (attr.Parse(di.ReparseData, di.ReparseData.Size()))
|
||||
{
|
||||
UString simpleName = attr.GetPath();
|
||||
if (attr.IsRelative())
|
||||
if (!attr.IsSymLink_WSL() && attr.IsRelative_Win())
|
||||
prop = simpleName;
|
||||
else
|
||||
{
|
||||
const FString phyPath = DirItems->GetPhyPath(up.DirIndex);
|
||||
const FString phyPath = DirItems->GetPhyPath((unsigned)up.DirIndex);
|
||||
FString fullPath;
|
||||
if (NDir::MyGetFullPathName(phyPath, fullPath))
|
||||
{
|
||||
@@ -366,8 +374,26 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#else // _WIN32
|
||||
|
||||
if (di.ReparseData.Size() != 0)
|
||||
{
|
||||
AString utf;
|
||||
utf.SetFrom_CalcLen((const char *)(const Byte *)di.ReparseData, (unsigned)di.ReparseData.Size());
|
||||
|
||||
UString us;
|
||||
if (ConvertUTF8ToUnicode(utf, us))
|
||||
{
|
||||
prop = us;
|
||||
prop.Detach(value);
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
|
||||
#endif // _WIN32
|
||||
}
|
||||
#endif // !defined(UNDER_CE)
|
||||
}
|
||||
else if (propID == kpidHardLink)
|
||||
{
|
||||
@@ -375,7 +401,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
{
|
||||
const CKeyKeyValPair &pair = _map[_hardIndex_To];
|
||||
const CUpdatePair2 &up2 = (*UpdatePairs)[pair.Value];
|
||||
prop = DirItems->GetLogPath(up2.DirIndex);
|
||||
prop = DirItems->GetLogPath((unsigned)up2.DirIndex);
|
||||
prop.Detach(value);
|
||||
return S_OK;
|
||||
}
|
||||
@@ -399,7 +425,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
}
|
||||
}
|
||||
else if (propID == kpidPath && up.NewNameIndex >= 0)
|
||||
prop = (*NewNames)[up.NewNameIndex];
|
||||
prop = (*NewNames)[(unsigned)up.NewNameIndex];
|
||||
else if (propID == kpidComment
|
||||
&& CommentIndex >= 0
|
||||
&& (unsigned)CommentIndex == index
|
||||
@@ -411,13 +437,13 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
}
|
||||
else if ((up.UseArcProps || (KeepOriginalItemNames && (propID == kpidPath || propID == kpidIsAltStream)))
|
||||
&& up.ExistInArchive() && Archive)
|
||||
return Archive->GetProperty(ArcItems ? (*ArcItems)[up.ArcIndex].IndexInServer : up.ArcIndex, propID, value);
|
||||
return Archive->GetProperty(ArcItems ? (*ArcItems)[(unsigned)up.ArcIndex].IndexInServer : (UInt32)(Int32)up.ArcIndex, propID, value);
|
||||
else if (up.ExistOnDisk())
|
||||
{
|
||||
const CDirItem &di = DirItems->Items[up.DirIndex];
|
||||
const CDirItem &di = DirItems->Items[(unsigned)up.DirIndex];
|
||||
switch (propID)
|
||||
{
|
||||
case kpidPath: prop = DirItems->GetLogPath(up.DirIndex); break;
|
||||
case kpidPath: prop = DirItems->GetLogPath((unsigned)up.DirIndex); break;
|
||||
case kpidIsDir: prop = di.IsDir(); break;
|
||||
case kpidSize: prop = di.IsDir() ? (UInt64)0 : di.Size; break;
|
||||
case kpidAttrib: prop = di.Attrib; break;
|
||||
@@ -428,6 +454,16 @@ STDMETHODIMP CArchiveUpdateCallback::GetProperty(UInt32 index, PROPID propID, PR
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
// case kpidShortName: prop = di.ShortName; break;
|
||||
#endif
|
||||
case kpidPosixAttrib:
|
||||
{
|
||||
#ifdef _WIN32
|
||||
prop = di.GetPosixAttrib();
|
||||
#else
|
||||
if (di.Attrib & FILE_ATTRIBUTE_UNIX_EXTENSION)
|
||||
prop = (UInt32)(di.Attrib >> 16);
|
||||
#endif
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
prop.Detach(value);
|
||||
@@ -456,9 +492,9 @@ STDMETHODIMP CArchiveUpdateCallback::GetStream2(UInt32 index, ISequentialInStrea
|
||||
{
|
||||
UString name;
|
||||
if (up.ArcIndex >= 0)
|
||||
name = (*ArcItems)[up.ArcIndex].Name;
|
||||
name = (*ArcItems)[(unsigned)up.ArcIndex].Name;
|
||||
else if (up.DirIndex >= 0)
|
||||
name = DirItems->GetLogPath(up.DirIndex);
|
||||
name = DirItems->GetLogPath((unsigned)up.DirIndex);
|
||||
RINOK(Callback->GetStream(name, isDir, true, mode));
|
||||
|
||||
/* 9.33: fixed. Handlers expect real stream object for files, even for anti-file.
|
||||
@@ -474,7 +510,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetStream2(UInt32 index, ISequentialInStrea
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
RINOK(Callback->GetStream(DirItems->GetLogPath(up.DirIndex), isDir, false, mode));
|
||||
RINOK(Callback->GetStream(DirItems->GetLogPath((unsigned)up.DirIndex), isDir, false, mode));
|
||||
|
||||
if (isDir)
|
||||
return S_OK;
|
||||
@@ -491,27 +527,42 @@ STDMETHODIMP CArchiveUpdateCallback::GetStream2(UInt32 index, ISequentialInStrea
|
||||
}
|
||||
else
|
||||
{
|
||||
CInFileStream *inStreamSpec = new CInFileStream;
|
||||
CMyComPtr<ISequentialInStream> inStreamLoc(inStreamSpec);
|
||||
|
||||
inStreamSpec->SupportHardLinks = StoreHardLinks;
|
||||
inStreamSpec->Callback = this;
|
||||
inStreamSpec->CallbackRef = index;
|
||||
|
||||
const FString path = DirItems->GetPhyPath(up.DirIndex);
|
||||
_openFiles_Indexes.Add(index);
|
||||
_openFiles_Paths.Add(path);
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
if (DirItems->Items[up.DirIndex].AreReparseData())
|
||||
#if !defined(UNDER_CE)
|
||||
const CDirItem &di = DirItems->Items[(unsigned)up.DirIndex];
|
||||
if (di.AreReparseData())
|
||||
{
|
||||
/*
|
||||
// we still need DeviceIoControlOut() instead of Read
|
||||
if (!inStreamSpec->File.OpenReparse(path))
|
||||
{
|
||||
return Callback->OpenFileError(path, ::GetLastError());
|
||||
}
|
||||
*/
|
||||
// 20.03: we use Reparse Data instead of real data
|
||||
|
||||
CBufInStream *inStreamSpec = new CBufInStream();
|
||||
CMyComPtr<ISequentialInStream> inStreamLoc = inStreamSpec;
|
||||
inStreamSpec->Init(di.ReparseData, di.ReparseData.Size());
|
||||
*inStream = inStreamLoc.Detach();
|
||||
return S_OK;
|
||||
}
|
||||
else
|
||||
#endif
|
||||
#endif // !defined(UNDER_CE)
|
||||
|
||||
CInFileStream *inStreamSpec = new CInFileStream;
|
||||
CMyComPtr<ISequentialInStream> inStreamLoc(inStreamSpec);
|
||||
|
||||
inStreamSpec->SupportHardLinks = StoreHardLinks;
|
||||
inStreamSpec->File.PreserveATime = PreserveATime;
|
||||
|
||||
const FString path = DirItems->GetPhyPath((unsigned)up.DirIndex);
|
||||
_openFiles_Indexes.Add(index);
|
||||
_openFiles_Paths.Add(path);
|
||||
|
||||
/* 21.02 : we set Callback/CallbackRef after _openFiles_Indexes adding
|
||||
for correct working if exception was raised in GetPhyPath */
|
||||
inStreamSpec->Callback = this;
|
||||
inStreamSpec->CallbackRef = index;
|
||||
|
||||
if (!inStreamSpec->OpenShared(path, ShareForWrite))
|
||||
{
|
||||
DWORD error = ::GetLastError();
|
||||
@@ -522,6 +573,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetStream2(UInt32 index, ISequentialInStrea
|
||||
return hres;
|
||||
}
|
||||
|
||||
// #if defined(USE_WIN_FILE) || !defined(_WIN32)
|
||||
if (StoreHardLinks)
|
||||
{
|
||||
CStreamFileProps props;
|
||||
@@ -546,6 +598,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetStream2(UInt32 index, ISequentialInStrea
|
||||
}
|
||||
}
|
||||
}
|
||||
// #endif
|
||||
|
||||
if (ProcessedItemsStatuses)
|
||||
{
|
||||
@@ -592,8 +645,8 @@ STDMETHODIMP CArchiveUpdateCallback::ReportOperation(UInt32 indexType, UInt32 in
|
||||
const CUpdatePair2 &up = (*UpdatePairs)[index];
|
||||
if (up.ExistOnDisk())
|
||||
{
|
||||
name = DirItems->GetLogPath(up.DirIndex);
|
||||
isDir = DirItems->Items[up.DirIndex].IsDir();
|
||||
name = DirItems->GetLogPath((unsigned)up.DirIndex);
|
||||
isDir = DirItems->Items[(unsigned)up.DirIndex].IsDir();
|
||||
}
|
||||
}
|
||||
return Callback->ReportUpdateOpeartion(op, name.IsEmpty() ? NULL : name.Ptr(), isDir);
|
||||
@@ -716,7 +769,7 @@ STDMETHODIMP CArchiveUpdateCallback::GetVolumeStream(UInt32 index, ISequentialOu
|
||||
COutFileStream *streamSpec = new COutFileStream;
|
||||
CMyComPtr<ISequentialOutStream> streamLoc(streamSpec);
|
||||
if (!streamSpec->Create(fileName, false))
|
||||
return ::GetLastError();
|
||||
return GetLastError_noZero_HRESULT();
|
||||
*volumeStream = streamLoc.Detach();
|
||||
return S_OK;
|
||||
COM_TRY_END
|
||||
@@ -738,7 +791,10 @@ STDMETHODIMP CArchiveUpdateCallback::CryptoGetTextPassword(BSTR *password)
|
||||
|
||||
HRESULT CArchiveUpdateCallback::InFileStream_On_Error(UINT_PTR val, DWORD error)
|
||||
{
|
||||
if (error == ERROR_LOCK_VIOLATION)
|
||||
#ifdef _WIN32 // FIX IT !!!
|
||||
// why did we check only for ERROR_LOCK_VIOLATION ?
|
||||
// if (error == ERROR_LOCK_VIOLATION)
|
||||
#endif
|
||||
{
|
||||
MT_LOCK
|
||||
UInt32 index = (UInt32)val;
|
||||
@@ -756,6 +812,7 @@ HRESULT CArchiveUpdateCallback::InFileStream_On_Error(UINT_PTR val, DWORD error)
|
||||
|
||||
void CArchiveUpdateCallback::InFileStream_On_Destroy(UINT_PTR val)
|
||||
{
|
||||
{
|
||||
MT_LOCK
|
||||
UInt32 index = (UInt32)val;
|
||||
FOR_VECTOR(i, _openFiles_Indexes)
|
||||
@@ -767,5 +824,11 @@ void CArchiveUpdateCallback::InFileStream_On_Destroy(UINT_PTR val)
|
||||
return;
|
||||
}
|
||||
}
|
||||
throw 20141125;
|
||||
}
|
||||
/* 21.02 : this function can be called in destructor.
|
||||
And destructor can be called after some exception.
|
||||
If we don't want to throw exception in desctructors or after another exceptions,
|
||||
we must disable the code below that raises new exception.
|
||||
*/
|
||||
// throw 20141125;
|
||||
}
|
||||
|
||||
@@ -135,6 +135,7 @@ public:
|
||||
int CommentIndex;
|
||||
const UString *Comment;
|
||||
|
||||
bool PreserveATime;
|
||||
bool ShareForWrite;
|
||||
bool StopAfterOpenError;
|
||||
bool StdInMode;
|
||||
@@ -152,9 +153,9 @@ public:
|
||||
bool IsDir(const CUpdatePair2 &up) const
|
||||
{
|
||||
if (up.DirIndex >= 0)
|
||||
return DirItems->Items[up.DirIndex].IsDir();
|
||||
return DirItems->Items[(unsigned)up.DirIndex].IsDir();
|
||||
else if (up.ArcIndex >= 0)
|
||||
return (*ArcItems)[up.ArcIndex].IsDir;
|
||||
return (*ArcItems)[(unsigned)up.ArcIndex].IsDir;
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -42,7 +42,9 @@ static const char * const k_Duplicate_inArc_Message = "Duplicate filename in arc
|
||||
static const char * const k_Duplicate_inDir_Message = "Duplicate filename on disk:";
|
||||
static const char * const k_NotCensoredCollision_Message = "Internal file name collision (file on disk, file in archive):";
|
||||
|
||||
static void ThrowError(const char *message, const UString &s1, const UString &s2)
|
||||
MY_ATTR_NORETURN
|
||||
static
|
||||
void ThrowError(const char *message, const UString &s1, const UString &s2)
|
||||
{
|
||||
UString m (message);
|
||||
m.Add_LF(); m += s1;
|
||||
@@ -144,18 +146,18 @@ void GetUpdatePairInfoList(
|
||||
|
||||
if (dirIndex < numDirItems)
|
||||
{
|
||||
dirIndex2 = dirIndices[dirIndex];
|
||||
di = &dirItems.Items[dirIndex2];
|
||||
dirIndex2 = (int)dirIndices[dirIndex];
|
||||
di = &dirItems.Items[(unsigned)dirIndex2];
|
||||
}
|
||||
|
||||
if (arcIndex < numArcItems)
|
||||
{
|
||||
arcIndex2 = arcIndices[arcIndex];
|
||||
ai = &arcItems[arcIndex2];
|
||||
arcIndex2 = (int)arcIndices[arcIndex];
|
||||
ai = &arcItems[(unsigned)arcIndex2];
|
||||
compareResult = 1;
|
||||
if (dirIndex < numDirItems)
|
||||
{
|
||||
compareResult = CompareFileNames(dirNames[dirIndex2], ai->Name);
|
||||
compareResult = CompareFileNames(dirNames[(unsigned)dirIndex2], ai->Name);
|
||||
if (compareResult == 0)
|
||||
{
|
||||
if (di->IsDir() != ai->IsDir)
|
||||
@@ -166,7 +168,7 @@ void GetUpdatePairInfoList(
|
||||
|
||||
if (compareResult < 0)
|
||||
{
|
||||
name = &dirNames[dirIndex2];
|
||||
name = &dirNames[(unsigned)dirIndex2];
|
||||
pair.State = NUpdateArchive::NPairState::kOnlyOnDisk;
|
||||
pair.DirIndex = dirIndex2;
|
||||
dirIndex++;
|
||||
@@ -184,9 +186,9 @@ void GetUpdatePairInfoList(
|
||||
{
|
||||
int dupl = duplicatedArcItem[arcIndex];
|
||||
if (dupl != 0)
|
||||
ThrowError(k_Duplicate_inArc_Message, ai->Name, arcItems[arcIndices[arcIndex + dupl]].Name);
|
||||
ThrowError(k_Duplicate_inArc_Message, ai->Name, arcItems[arcIndices[(unsigned)((int)arcIndex + dupl)]].Name);
|
||||
|
||||
name = &dirNames[dirIndex2];
|
||||
name = &dirNames[(unsigned)dirIndex2];
|
||||
if (!ai->Censored)
|
||||
ThrowError(k_NotCensoredCollision_Message, *name, ai->Name);
|
||||
|
||||
@@ -222,7 +224,7 @@ void GetUpdatePairInfoList(
|
||||
}
|
||||
else
|
||||
{
|
||||
prevHostFile = updatePairs.Size();
|
||||
prevHostFile = (int)updatePairs.Size();
|
||||
prevHostName = name;
|
||||
}
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ void UpdateProduce(
|
||||
{
|
||||
case NPairAction::kIgnore:
|
||||
if (pair.ArcIndex >= 0 && callback)
|
||||
callback->ShowDeleteFile(pair.ArcIndex);
|
||||
callback->ShowDeleteFile((unsigned)pair.ArcIndex);
|
||||
continue;
|
||||
|
||||
case NPairAction::kCopy:
|
||||
@@ -43,7 +43,7 @@ void UpdateProduce(
|
||||
1) no such alt stream in Disk
|
||||
2) there is Host file in disk
|
||||
*/
|
||||
if (updatePairs[pair.HostIndex].DirIndex >= 0)
|
||||
if (updatePairs[(unsigned)pair.HostIndex].DirIndex >= 0)
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,12 +18,12 @@ struct CUpdatePair2
|
||||
|
||||
bool IsMainRenameItem;
|
||||
|
||||
void SetAs_NoChangeArcItem(int arcIndex)
|
||||
void SetAs_NoChangeArcItem(unsigned arcIndex) // int
|
||||
{
|
||||
NewData = NewProps = false;
|
||||
UseArcProps = true;
|
||||
IsAnti = false;
|
||||
ArcIndex = arcIndex;
|
||||
ArcIndex = (int)arcIndex;
|
||||
}
|
||||
|
||||
bool ExistOnDisk() const { return DirIndex != -1; }
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "../../../Common/Wildcard.h"
|
||||
|
||||
#include "../../../Windows/FileFind.h"
|
||||
#include "../../../Windows/FileName.h"
|
||||
|
||||
#include "WorkDir.h"
|
||||
@@ -39,13 +40,13 @@ FString GetWorkDir(const NWorkDir::CInfo &workDirInfo, const FString &path, FStr
|
||||
#endif
|
||||
|
||||
int pos = path.ReverseFind_PathSepar() + 1;
|
||||
fileName = path.Ptr(pos);
|
||||
fileName = path.Ptr((unsigned)pos);
|
||||
|
||||
switch (mode)
|
||||
{
|
||||
case NWorkDir::NMode::kCurrent:
|
||||
{
|
||||
return path.Left(pos);
|
||||
return path.Left((unsigned)pos);
|
||||
}
|
||||
case NWorkDir::NMode::kSpecified:
|
||||
{
|
||||
@@ -75,8 +76,7 @@ HRESULT CWorkDirTempFile::CreateTempFile(const FString &originalPath)
|
||||
OutStream = _outStreamSpec;
|
||||
if (!_tempFile.Create(workDir + namePart, &_outStreamSpec->File))
|
||||
{
|
||||
DWORD error = GetLastError();
|
||||
return error ? error : E_FAIL;
|
||||
return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
_originalPath = originalPath;
|
||||
return S_OK;
|
||||
@@ -87,8 +87,7 @@ HRESULT CWorkDirTempFile::MoveToOriginal(bool deleteOriginal)
|
||||
OutStream.Release();
|
||||
if (!_tempFile.MoveTo(_originalPath, deleteOriginal))
|
||||
{
|
||||
DWORD error = GetLastError();
|
||||
return error ? error : E_FAIL;
|
||||
return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
@@ -357,6 +357,14 @@ SOURCE=..\..\..\Windows\System.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\..\..\Windows\SystemInfo.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\..\..\Windows\SystemInfo.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=..\..\..\Windows\Thread.h
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
@@ -4,8 +4,13 @@
|
||||
|
||||
#include "ConsoleClose.h"
|
||||
|
||||
#if !defined(UNDER_CE) && defined(_WIN32)
|
||||
#ifndef UNDER_CE
|
||||
|
||||
#ifdef _WIN32
|
||||
#include "../../../Common/MyWindows.h"
|
||||
#else
|
||||
#include <stdlib.h>
|
||||
#include <signal.h>
|
||||
#endif
|
||||
|
||||
namespace NConsoleClose {
|
||||
@@ -13,7 +18,8 @@ namespace NConsoleClose {
|
||||
unsigned g_BreakCounter = 0;
|
||||
static const unsigned kBreakAbortThreshold = 2;
|
||||
|
||||
#if !defined(UNDER_CE) && defined(_WIN32)
|
||||
#ifdef _WIN32
|
||||
|
||||
static BOOL WINAPI HandlerRoutine(DWORD ctrlType)
|
||||
{
|
||||
if (ctrlType == CTRL_LOGOFF_EVENT)
|
||||
@@ -37,7 +43,49 @@ static BOOL WINAPI HandlerRoutine(DWORD ctrlType)
|
||||
return FALSE;
|
||||
*/
|
||||
}
|
||||
#endif
|
||||
|
||||
CCtrlHandlerSetter::CCtrlHandlerSetter()
|
||||
{
|
||||
if (!SetConsoleCtrlHandler(HandlerRoutine, TRUE))
|
||||
throw "SetConsoleCtrlHandler fails";
|
||||
}
|
||||
|
||||
CCtrlHandlerSetter::~CCtrlHandlerSetter()
|
||||
{
|
||||
if (!SetConsoleCtrlHandler(HandlerRoutine, FALSE))
|
||||
{
|
||||
// warning for throw in destructor.
|
||||
// throw "SetConsoleCtrlHandler fails";
|
||||
}
|
||||
}
|
||||
|
||||
#else // _WIN32
|
||||
|
||||
static void HandlerRoutine(int)
|
||||
{
|
||||
g_BreakCounter++;
|
||||
if (g_BreakCounter < kBreakAbortThreshold)
|
||||
return;
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
CCtrlHandlerSetter::CCtrlHandlerSetter()
|
||||
{
|
||||
memo_sig_int = signal(SIGINT, HandlerRoutine); // CTRL-C
|
||||
if (memo_sig_int == SIG_ERR)
|
||||
throw "SetConsoleCtrlHandler fails (SIGINT)";
|
||||
memo_sig_term = signal(SIGTERM, HandlerRoutine); // for kill -15 (before "kill -9")
|
||||
if (memo_sig_term == SIG_ERR)
|
||||
throw "SetConsoleCtrlHandler fails (SIGTERM)";
|
||||
}
|
||||
|
||||
CCtrlHandlerSetter::~CCtrlHandlerSetter()
|
||||
{
|
||||
signal(SIGINT, memo_sig_int); // CTRL-C
|
||||
signal(SIGTERM, memo_sig_term); // kill {pid}
|
||||
}
|
||||
|
||||
#endif // _WIN32
|
||||
|
||||
/*
|
||||
void CheckCtrlBreak()
|
||||
@@ -47,23 +95,6 @@ void CheckCtrlBreak()
|
||||
}
|
||||
*/
|
||||
|
||||
CCtrlHandlerSetter::CCtrlHandlerSetter()
|
||||
{
|
||||
#if !defined(UNDER_CE) && defined(_WIN32)
|
||||
if (!SetConsoleCtrlHandler(HandlerRoutine, TRUE))
|
||||
throw "SetConsoleCtrlHandler fails";
|
||||
#endif
|
||||
}
|
||||
|
||||
CCtrlHandlerSetter::~CCtrlHandlerSetter()
|
||||
{
|
||||
#if !defined(UNDER_CE) && defined(_WIN32)
|
||||
if (!SetConsoleCtrlHandler(HandlerRoutine, FALSE))
|
||||
{
|
||||
// warning for throw in destructor.
|
||||
// throw "SetConsoleCtrlHandler fails";
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -5,28 +5,34 @@
|
||||
|
||||
namespace NConsoleClose {
|
||||
|
||||
class CCtrlBreakException {};
|
||||
|
||||
#ifdef UNDER_CE
|
||||
|
||||
inline bool TestBreakSignal() { return false; }
|
||||
struct CCtrlHandlerSetter {};
|
||||
|
||||
#else
|
||||
|
||||
extern unsigned g_BreakCounter;
|
||||
|
||||
inline bool TestBreakSignal()
|
||||
{
|
||||
#ifdef UNDER_CE
|
||||
return false;
|
||||
#else
|
||||
return (g_BreakCounter != 0);
|
||||
#endif
|
||||
}
|
||||
|
||||
class CCtrlHandlerSetter
|
||||
{
|
||||
#ifndef _WIN32
|
||||
void (*memo_sig_int)(int);
|
||||
void (*memo_sig_term)(int);
|
||||
#endif
|
||||
public:
|
||||
CCtrlHandlerSetter();
|
||||
virtual ~CCtrlHandlerSetter();
|
||||
};
|
||||
|
||||
class CCtrlBreakException
|
||||
{};
|
||||
|
||||
// void CheckCtrlBreak();
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -69,6 +69,7 @@ HRESULT CExtractScanConsole::ScanError(const FString &path, DWORD systemError)
|
||||
}
|
||||
|
||||
|
||||
void Print_UInt64_and_String(AString &s, UInt64 val, const char *name);
|
||||
void Print_UInt64_and_String(AString &s, UInt64 val, const char *name)
|
||||
{
|
||||
char temp[32];
|
||||
@@ -78,6 +79,7 @@ void Print_UInt64_and_String(AString &s, UInt64 val, const char *name)
|
||||
s += name;
|
||||
}
|
||||
|
||||
void PrintSize_bytes_Smart(AString &s, UInt64 val);
|
||||
void PrintSize_bytes_Smart(AString &s, UInt64 val)
|
||||
{
|
||||
Print_UInt64_and_String(s, val, "bytes");
|
||||
@@ -96,7 +98,7 @@ void PrintSize_bytes_Smart(AString &s, UInt64 val)
|
||||
s += ')';
|
||||
}
|
||||
|
||||
void PrintSize_bytes_Smart_comma(AString &s, UInt64 val)
|
||||
static void PrintSize_bytes_Smart_comma(AString &s, UInt64 val)
|
||||
{
|
||||
if (val == (UInt64)(Int64)-1)
|
||||
return;
|
||||
@@ -106,6 +108,7 @@ void PrintSize_bytes_Smart_comma(AString &s, UInt64 val)
|
||||
|
||||
|
||||
|
||||
void Print_DirItemsStat(AString &s, const CDirItemsStat &st);
|
||||
void Print_DirItemsStat(AString &s, const CDirItemsStat &st)
|
||||
{
|
||||
if (st.NumDirs != 0)
|
||||
@@ -124,6 +127,7 @@ void Print_DirItemsStat(AString &s, const CDirItemsStat &st)
|
||||
}
|
||||
|
||||
|
||||
void Print_DirItemsStat2(AString &s, const CDirItemsStat2 &st);
|
||||
void Print_DirItemsStat2(AString &s, const CDirItemsStat2 &st)
|
||||
{
|
||||
Print_DirItemsStat(s, (CDirItemsStat &)st);
|
||||
@@ -184,9 +188,9 @@ static const char * const kTestString = "T";
|
||||
static const char * const kExtractString = "-";
|
||||
static const char * const kSkipString = ".";
|
||||
|
||||
// static const char * const kCantAutoRename = "can not create file with auto name\n";
|
||||
// static const char * const kCantRenameFile = "can not rename existing file\n";
|
||||
// static const char * const kCantDeleteOutputFile = "can not delete output file ";
|
||||
// static const char * const kCantAutoRename = "cannot create file with auto name\n";
|
||||
// static const char * const kCantRenameFile = "cannot rename existing file\n";
|
||||
// static const char * const kCantDeleteOutputFile = "cannot delete output file ";
|
||||
|
||||
static const char * const kMemoryExceptionMessage = "Can't allocate required memory!";
|
||||
|
||||
@@ -394,6 +398,7 @@ STDMETHODIMP CExtractCallbackConsole::MessageError(const wchar_t *message)
|
||||
return CheckBreak2();
|
||||
}
|
||||
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, AString &dest);
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, AString &dest)
|
||||
{
|
||||
dest.Empty();
|
||||
@@ -436,7 +441,7 @@ void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, AString &dest)
|
||||
else
|
||||
{
|
||||
dest += "Error #";
|
||||
dest.Add_UInt32(opRes);
|
||||
dest.Add_UInt32((UInt32)opRes);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -566,6 +571,7 @@ static AString GetOpenArcErrorMessage(UInt32 errorFlags)
|
||||
return s;
|
||||
}
|
||||
|
||||
void PrintErrorFlags(CStdOutStream &so, const char *s, UInt32 errorFlags);
|
||||
void PrintErrorFlags(CStdOutStream &so, const char *s, UInt32 errorFlags)
|
||||
{
|
||||
if (errorFlags == 0)
|
||||
@@ -573,7 +579,7 @@ void PrintErrorFlags(CStdOutStream &so, const char *s, UInt32 errorFlags)
|
||||
so << s << endl << GetOpenArcErrorMessage(errorFlags) << endl;
|
||||
}
|
||||
|
||||
void Add_Messsage_Pre_ArcType(UString &s, const char *pre, const wchar_t *arcType)
|
||||
static void Add_Messsage_Pre_ArcType(UString &s, const char *pre, const wchar_t *arcType)
|
||||
{
|
||||
s.Add_LF();
|
||||
s += pre;
|
||||
@@ -582,6 +588,7 @@ void Add_Messsage_Pre_ArcType(UString &s, const char *pre, const wchar_t *arcTyp
|
||||
s += "] archive";
|
||||
}
|
||||
|
||||
void Print_ErrorFormatIndex_Warning(CStdOutStream *_so, const CCodecs *codecs, const CArc &arc);
|
||||
void Print_ErrorFormatIndex_Warning(CStdOutStream *_so, const CCodecs *codecs, const CArc &arc)
|
||||
{
|
||||
const CArcErrorInfo &er = arc.ErrorInfo;
|
||||
@@ -596,7 +603,7 @@ void Print_ErrorFormatIndex_Warning(CStdOutStream *_so, const CCodecs *codecs, c
|
||||
}
|
||||
else
|
||||
{
|
||||
Add_Messsage_Pre_ArcType(s, "Can not open the file", codecs->GetFormatNamePtr(er.ErrorFormatIndex));
|
||||
Add_Messsage_Pre_ArcType(s, "Cannot open the file", codecs->GetFormatNamePtr(er.ErrorFormatIndex));
|
||||
Add_Messsage_Pre_ArcType(s, "The file is open", codecs->GetFormatNamePtr(arc.FormatIndex));
|
||||
}
|
||||
|
||||
@@ -806,7 +813,9 @@ HRESULT CExtractCallbackConsole::ExtractResult(HRESULT result)
|
||||
else
|
||||
{
|
||||
NumArcsWithError++;
|
||||
if (result == E_ABORT || result == ERROR_DISK_FULL)
|
||||
if (result == E_ABORT
|
||||
|| result == HRESULT_FROM_WIN32(ERROR_DISK_FULL)
|
||||
)
|
||||
return result;
|
||||
|
||||
if (_se)
|
||||
|
||||
@@ -32,6 +32,9 @@ class CExtractScanConsole: public IDirItemsCallback
|
||||
}
|
||||
|
||||
public:
|
||||
|
||||
virtual ~CExtractScanConsole() {}
|
||||
|
||||
void Init(CStdOutStream *outStream, CStdOutStream *errorStream, CStdOutStream *percentStream)
|
||||
{
|
||||
_so = outStream;
|
||||
|
||||
@@ -222,7 +222,8 @@ void CHashCallbackConsole::PrintResultLine(UInt64 fileSize,
|
||||
s[0] = 0;
|
||||
if (showHash)
|
||||
AddHashHexToString(s, h.Digests[digestIndex], h.DigestSize);
|
||||
SetSpacesAndNul(s + strlen(s), (int)GetColumnWidth(h.DigestSize) - (int)strlen(s));
|
||||
const unsigned pos = (unsigned)strlen(s);
|
||||
SetSpacesAndNul(s + pos, GetColumnWidth(h.DigestSize) - pos);
|
||||
if (i != 0)
|
||||
_s.Add_Space();
|
||||
_s += s;
|
||||
@@ -235,20 +236,15 @@ void CHashCallbackConsole::PrintResultLine(UInt64 fileSize,
|
||||
char s[kSizeField_Len + 32];
|
||||
char *p = s;
|
||||
|
||||
SetSpacesAndNul(s, kSizeField_Len);
|
||||
if (showHash)
|
||||
{
|
||||
p = s + kSizeField_Len;
|
||||
ConvertUInt64ToString(fileSize, p);
|
||||
int numSpaces = kSizeField_Len - (int)strlen(p);
|
||||
int numSpaces = (int)kSizeField_Len - (int)strlen(p);
|
||||
if (numSpaces > 0)
|
||||
{
|
||||
p -= (unsigned)numSpaces;
|
||||
for (unsigned i = 0; i < (unsigned)numSpaces; i++)
|
||||
p[i] = ' ';
|
||||
}
|
||||
}
|
||||
else
|
||||
SetSpacesAndNul(s, kSizeField_Len);
|
||||
|
||||
_s += p;
|
||||
}
|
||||
|
||||
@@ -38,7 +38,7 @@ public:
|
||||
PrintName(true)
|
||||
{}
|
||||
|
||||
~CHashCallbackConsole() { }
|
||||
virtual ~CHashCallbackConsole() {}
|
||||
|
||||
INTERFACE_IHashCallbackUI(;)
|
||||
};
|
||||
|
||||
@@ -351,7 +351,7 @@ struct CListStat2
|
||||
AltStreams.Update(st.AltStreams);
|
||||
NumDirs += st.NumDirs;
|
||||
}
|
||||
const UInt64 GetNumStreams() const { return MainFiles.NumFiles + AltStreams.NumFiles; }
|
||||
UInt64 GetNumStreams() const { return MainFiles.NumFiles + AltStreams.NumFiles; }
|
||||
CListStat &GetStat(bool altStreamsMode) { return altStreamsMode ? AltStreams : MainFiles; }
|
||||
};
|
||||
|
||||
@@ -751,7 +751,7 @@ void CFieldPrinter::PrintSum(const CListStat2 &stat2)
|
||||
PrintSum(stat2.MainFiles, stat2.NumDirs, kString_Files);
|
||||
if (stat2.AltStreams.NumFiles != 0)
|
||||
{
|
||||
PrintSum(stat2.AltStreams, 0, kString_AltStreams);;
|
||||
PrintSum(stat2.AltStreams, 0, kString_AltStreams);
|
||||
CListStat st = stat2.MainFiles;
|
||||
st.Update(stat2.AltStreams);
|
||||
PrintSum(st, 0, kString_Streams);
|
||||
@@ -905,7 +905,7 @@ static HRESULT PrintArcProp(CStdOutStream &so, IInArchive *archive, PROPID propI
|
||||
static void PrintArcTypeError(CStdOutStream &so, const UString &type, bool isWarning)
|
||||
{
|
||||
so << "Open " << (isWarning ? "WARNING" : "ERROR")
|
||||
<< ": Can not open the file as ["
|
||||
<< ": Cannot open the file as ["
|
||||
<< type
|
||||
<< "] archive"
|
||||
<< endl;
|
||||
@@ -926,6 +926,7 @@ static void ErrorInfo_Print(CStdOutStream &so, const CArcErrorInfo &er)
|
||||
PrintPropPair(so, "WARNING", er.WarningMessage, true);
|
||||
}
|
||||
|
||||
HRESULT Print_OpenArchive_Props(CStdOutStream &so, const CCodecs *codecs, const CArchiveLink &arcLink);
|
||||
HRESULT Print_OpenArchive_Props(CStdOutStream &so, const CCodecs *codecs, const CArchiveLink &arcLink)
|
||||
{
|
||||
FOR_VECTOR (r, arcLink.Arcs)
|
||||
@@ -990,11 +991,12 @@ HRESULT Print_OpenArchive_Props(CStdOutStream &so, const CCodecs *codecs, const
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
HRESULT Print_OpenArchive_Error(CStdOutStream &so, const CCodecs *codecs, const CArchiveLink &arcLink);
|
||||
HRESULT Print_OpenArchive_Error(CStdOutStream &so, const CCodecs *codecs, const CArchiveLink &arcLink)
|
||||
{
|
||||
#ifndef _NO_CRYPTO
|
||||
if (arcLink.PasswordWasAsked)
|
||||
so << "Can not open encrypted archive. Wrong password?";
|
||||
so << "Cannot open encrypted archive. Wrong password?";
|
||||
else
|
||||
#endif
|
||||
{
|
||||
@@ -1002,10 +1004,10 @@ HRESULT Print_OpenArchive_Error(CStdOutStream &so, const CCodecs *codecs, const
|
||||
{
|
||||
so.NormalizePrint_UString(arcLink.NonOpen_ArcPath);
|
||||
so << endl;
|
||||
PrintArcTypeError(so, codecs->Formats[arcLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name, false);
|
||||
PrintArcTypeError(so, codecs->Formats[(unsigned)arcLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name, false);
|
||||
}
|
||||
else
|
||||
so << "Can not open the file as archive";
|
||||
so << "Cannot open the file as archive";
|
||||
}
|
||||
|
||||
so << endl;
|
||||
@@ -1065,12 +1067,12 @@ HRESULT ListArchives(CCodecs *codecs,
|
||||
if (!stdInMode)
|
||||
{
|
||||
NFile::NFind::CFileInfo fi;
|
||||
if (!fi.Find(us2fs(arcPath)))
|
||||
if (!fi.Find_FollowLink(us2fs(arcPath)))
|
||||
{
|
||||
DWORD errorCode = GetLastError();
|
||||
if (errorCode == 0)
|
||||
errorCode = ERROR_FILE_NOT_FOUND;
|
||||
lastError = HRESULT_FROM_WIN32(lastError);;
|
||||
lastError = HRESULT_FROM_WIN32(errorCode);
|
||||
g_StdOut.Flush();
|
||||
if (g_ErrStream)
|
||||
{
|
||||
@@ -1279,7 +1281,7 @@ HRESULT ListArchives(CCodecs *codecs,
|
||||
}
|
||||
else
|
||||
{
|
||||
SplitPathToParts(fp.FilePath, pathParts);;
|
||||
SplitPathToParts(fp.FilePath, pathParts);
|
||||
bool include;
|
||||
if (!wildcardCensor.CheckPathVect(pathParts, !fp.IsDir, include))
|
||||
continue;
|
||||
@@ -1331,7 +1333,7 @@ HRESULT ListArchives(CCodecs *codecs,
|
||||
{
|
||||
g_StdOut << "----------\n";
|
||||
PrintPropPair(g_StdOut, "Path", arcLink.NonOpen_ArcPath, false);
|
||||
PrintArcTypeError(g_StdOut, codecs->Formats[arcLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name, false);
|
||||
PrintArcTypeError(g_StdOut, codecs->Formats[(unsigned)arcLink.NonOpen_ErrorInfo.ErrorFormatIndex].Name, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -6,6 +6,11 @@
|
||||
|
||||
#ifdef _WIN32
|
||||
#include <Psapi.h>
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/times.h>
|
||||
#endif
|
||||
|
||||
#include "../../../../C/CpuArch.h"
|
||||
@@ -15,12 +20,13 @@
|
||||
#include "../../../Common/CommandLineParser.h"
|
||||
#include "../../../Common/IntToString.h"
|
||||
#include "../../../Common/MyException.h"
|
||||
#include "../../../Common/StdInStream.h"
|
||||
#include "../../../Common/StdOutStream.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "../../../Common/StringToInt.h"
|
||||
#include "../../../Common/UTFConvert.h"
|
||||
|
||||
#include "../../../Windows/ErrorMsg.h"
|
||||
|
||||
#include "../../../Windows/TimeUtils.h"
|
||||
|
||||
#include "../Common/ArchiveCommandLine.h"
|
||||
@@ -37,12 +43,11 @@
|
||||
#include "BenchCon.h"
|
||||
#include "ConsoleClose.h"
|
||||
#include "ExtractCallbackConsole.h"
|
||||
#include "HashCon.h"
|
||||
#include "List.h"
|
||||
#include "OpenCallbackConsole.h"
|
||||
#include "UpdateCallbackConsole.h"
|
||||
|
||||
#include "HashCon.h"
|
||||
|
||||
#ifdef PROG_VARIANT_R
|
||||
#include "../../../../C/7zVersion.h"
|
||||
#else
|
||||
@@ -66,27 +71,30 @@ extern const CCodecInfo *g_Codecs[];
|
||||
extern unsigned g_NumHashers;
|
||||
extern const CHasherInfo *g_Hashers[];
|
||||
|
||||
static const char * const kCopyrightString = "\n7-Zip"
|
||||
#ifndef EXTERNAL_CODECS
|
||||
#ifdef PROG_VARIANT_R
|
||||
" (r)"
|
||||
#else
|
||||
" (a)"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if defined(PROG_VARIANT_Z)
|
||||
#define PROG_POSTFIX "z"
|
||||
#define PROG_POSTFIX_2 " (z)"
|
||||
#elif defined(PROG_VARIANT_R)
|
||||
#define PROG_POSTFIX "r"
|
||||
#define PROG_POSTFIX_2 " (r)"
|
||||
#elif !defined(EXTERNAL_CODECS)
|
||||
#define PROG_POSTFIX "a"
|
||||
#define PROG_POSTFIX_2 " (a)"
|
||||
#else
|
||||
#define PROG_POSTFIX ""
|
||||
#define PROG_POSTFIX_2 ""
|
||||
#endif
|
||||
|
||||
|
||||
static const char * const kCopyrightString = "\n7-Zip"
|
||||
PROG_POSTFIX_2
|
||||
" " MY_VERSION_CPU
|
||||
" : " MY_COPYRIGHT_DATE "\n\n";
|
||||
" : " MY_COPYRIGHT_DATE "\n";
|
||||
|
||||
static const char * const kHelpString =
|
||||
"Usage: 7z"
|
||||
#ifndef EXTERNAL_CODECS
|
||||
#ifdef PROG_VARIANT_R
|
||||
"r"
|
||||
#else
|
||||
"a"
|
||||
#endif
|
||||
#endif
|
||||
PROG_POSTFIX
|
||||
" <command> [<switches>...] <archive_name> [<file_names>...] [@listfile]\n"
|
||||
"\n"
|
||||
"<Commands>\n"
|
||||
@@ -141,6 +149,7 @@ static const char * const kHelpString =
|
||||
" -spf : use fully qualified file paths\n"
|
||||
" -ssc[-] : set sensitive case mode\n"
|
||||
" -sse : stop archive creating, if it can't open some input file\n"
|
||||
" -ssp : do not change Last Access Time of source files while archiving\n"
|
||||
" -ssw : compress shared files\n"
|
||||
" -stl : set archive timestamp from the most recently modified file\n"
|
||||
" -stm{HexMask} : set CPU thread affinity mask (hexadecimal number)\n"
|
||||
@@ -163,6 +172,7 @@ static const char * const kUnsupportedArcTypeMessage = "Unsupported archive type
|
||||
|
||||
#define kDefaultSfxModule "7zCon.sfx"
|
||||
|
||||
MY_ATTR_NORETURN
|
||||
static void ShowMessageAndThrowException(LPCSTR message, NExitCode::EEnum code)
|
||||
{
|
||||
if (g_ErrStream)
|
||||
@@ -170,15 +180,109 @@ static void ShowMessageAndThrowException(LPCSTR message, NExitCode::EEnum code)
|
||||
throw code;
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
static void GetArguments(int numArgs, const char *args[], UStringVector &parts)
|
||||
|
||||
#ifdef _WIN32
|
||||
#define ShowProgInfo(so)
|
||||
#else
|
||||
static void ShowProgInfo(CStdOutStream *so)
|
||||
{
|
||||
parts.Clear();
|
||||
for (int i = 0; i < numArgs; i++)
|
||||
if (!so)
|
||||
return;
|
||||
|
||||
*so
|
||||
|
||||
/*
|
||||
#ifdef __DATE__
|
||||
<< " " << __DATE__
|
||||
#endif
|
||||
#ifdef __TIME__
|
||||
<< " " << __TIME__
|
||||
#endif
|
||||
*/
|
||||
|
||||
#ifdef __VERSION__
|
||||
<< " compiler: " << __VERSION__
|
||||
#endif
|
||||
|
||||
#ifdef __GNUC__
|
||||
<< " GCC " << __GNUC__ << "." << __GNUC_MINOR__ << "." << __GNUC_PATCHLEVEL__
|
||||
#endif
|
||||
|
||||
#ifdef __clang__
|
||||
<< " CLANG " << __clang_major__ << "." << __clang_minor__
|
||||
#endif
|
||||
|
||||
#ifdef __xlC__
|
||||
<< " XLC " << (__xlC__ >> 8) << "." << (__xlC__ & 0xFF)
|
||||
#ifdef __xlC_ver__
|
||||
<< "." << (__xlC_ver__ >> 8) << "." << (__xlC_ver__ & 0xFF)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifdef _MSC_VER
|
||||
<< " MSC " << _MSC_VER
|
||||
#endif
|
||||
|
||||
#ifdef __ARM_FEATURE_CRC32
|
||||
<< " CRC32"
|
||||
#endif
|
||||
|
||||
<< " " << (unsigned)(sizeof(void *)) * 8 << "-bit"
|
||||
|
||||
#ifdef __ILP32__
|
||||
<< " ILP32"
|
||||
#endif
|
||||
|
||||
#ifdef __ARM_ARCH
|
||||
<< " arm_v:" << __ARM_ARCH
|
||||
#ifdef __ARM_ARCH_ISA_THUMB
|
||||
<< " thumb:" << __ARM_ARCH_ISA_THUMB
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef ENV_HAVE_LOCALE
|
||||
<< " locale=" << GetLocale()
|
||||
#endif
|
||||
#ifndef _WIN32
|
||||
<< " UTF8=" << (IsNativeUTF8() ? "+" : "-")
|
||||
<< " use-UTF8=" << (g_ForceToUTF8 ? "+" : "-")
|
||||
<< " wchar_t=" << (unsigned)(sizeof(wchar_t)) * 8 << "-bit"
|
||||
<< " Files=" << (unsigned)(sizeof(off_t)) * 8 << "-bit"
|
||||
#endif
|
||||
;
|
||||
|
||||
{
|
||||
UString s = MultiByteToUnicodeString(args[i]);
|
||||
parts.Add(s);
|
||||
const UInt32 numCpus = NWindows::NSystem::GetNumberOfProcessors();
|
||||
*so << " Threads:" << numCpus;
|
||||
}
|
||||
|
||||
{
|
||||
AString s;
|
||||
GetCpuName(s);
|
||||
s.Trim();
|
||||
*so << ", " << s;
|
||||
}
|
||||
|
||||
#ifdef _7ZIP_ASM
|
||||
*so << ",ASM";
|
||||
#endif
|
||||
|
||||
#if (defined MY_CPU_X86_OR_AMD64 || defined(MY_CPU_ARM_OR_ARM64))
|
||||
if (CPU_IsSupported_AES()) *so << ",AES";
|
||||
#endif
|
||||
|
||||
#ifdef MY_CPU_ARM_OR_ARM64
|
||||
if (CPU_IsSupported_CRC32()) *so << ",CRC32";
|
||||
#if defined(_WIN32)
|
||||
if (CPU_IsSupported_CRYPTO()) *so << ",CRYPTO";
|
||||
#else
|
||||
if (CPU_IsSupported_SHA1()) *so << ",SHA1";
|
||||
if (CPU_IsSupported_SHA2()) *so << ",SHA2";
|
||||
#endif
|
||||
#endif
|
||||
|
||||
*so << endl;
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -188,6 +292,8 @@ static void ShowCopyrightAndHelp(CStdOutStream *so, bool needHelp)
|
||||
return;
|
||||
*so << kCopyrightString;
|
||||
// *so << "# CPUs: " << (UInt64)NWindows::NSystem::GetNumberOfProcessors() << endl;
|
||||
ShowProgInfo(so);
|
||||
*so << endl;
|
||||
if (needHelp)
|
||||
*so << kHelpString;
|
||||
}
|
||||
@@ -211,7 +317,7 @@ static void PrintUInt32(CStdOutStream &so, UInt32 val, unsigned size)
|
||||
static void PrintLibIndex(CStdOutStream &so, int libIndex)
|
||||
{
|
||||
if (libIndex >= 0)
|
||||
PrintUInt32(so, libIndex, 2);
|
||||
PrintUInt32(so, (UInt32)libIndex, 2);
|
||||
else
|
||||
so << " ";
|
||||
so << ' ';
|
||||
@@ -329,7 +435,6 @@ static void ThrowException_if_Error(HRESULT res)
|
||||
throw CSystemException(res);
|
||||
}
|
||||
|
||||
|
||||
static void PrintNum(UInt64 val, unsigned numDigits, char c = ' ')
|
||||
{
|
||||
char temp[64];
|
||||
@@ -341,6 +446,8 @@ static void PrintNum(UInt64 val, unsigned numDigits, char c = ' ')
|
||||
*g_StdStream << p;
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
|
||||
static void PrintTime(const char *s, UInt64 val, UInt64 total)
|
||||
{
|
||||
*g_StdStream << endl << s << " Time =";
|
||||
@@ -427,19 +534,19 @@ static void PrintStat()
|
||||
|
||||
HMODULE kern = ::GetModuleHandleW(L"kernel32.dll");
|
||||
Func_GetProcessMemoryInfo my_GetProcessMemoryInfo = (Func_GetProcessMemoryInfo)
|
||||
::GetProcAddress(kern, "K32GetProcessMemoryInfo");
|
||||
(void *)::GetProcAddress(kern, "K32GetProcessMemoryInfo");
|
||||
if (!my_GetProcessMemoryInfo)
|
||||
{
|
||||
HMODULE lib = LoadLibraryW(L"Psapi.dll");
|
||||
if (lib)
|
||||
my_GetProcessMemoryInfo = (Func_GetProcessMemoryInfo)::GetProcAddress(lib, "GetProcessMemoryInfo");
|
||||
my_GetProcessMemoryInfo = (Func_GetProcessMemoryInfo)(void *)::GetProcAddress(lib, "GetProcessMemoryInfo");
|
||||
}
|
||||
if (my_GetProcessMemoryInfo)
|
||||
memDefined = my_GetProcessMemoryInfo(GetCurrentProcess(), &m, sizeof(m));
|
||||
// FreeLibrary(lib);
|
||||
|
||||
Func_QueryProcessCycleTime my_QueryProcessCycleTime = (Func_QueryProcessCycleTime)
|
||||
::GetProcAddress(kern, "QueryProcessCycleTime");
|
||||
(void *)::GetProcAddress(kern, "QueryProcessCycleTime");
|
||||
if (my_QueryProcessCycleTime)
|
||||
cycleDefined = my_QueryProcessCycleTime(GetCurrentProcess(), &cycleTime);
|
||||
}
|
||||
@@ -455,18 +562,32 @@ static void PrintStat()
|
||||
|
||||
PrintTime("Kernel ", kernelTime, totalTime);
|
||||
|
||||
const UInt64 processTime = kernelTime + userTime;
|
||||
|
||||
#ifndef UNDER_CE
|
||||
if (cycleDefined)
|
||||
{
|
||||
*g_StdStream << " ";
|
||||
PrintNum(cycleTime / 1000000, 22);
|
||||
*g_StdStream << " Cnt:";
|
||||
PrintNum(cycleTime / 1000000, 15);
|
||||
*g_StdStream << " MCycles";
|
||||
}
|
||||
#endif
|
||||
|
||||
PrintTime("User ", userTime, totalTime);
|
||||
|
||||
#ifndef UNDER_CE
|
||||
if (cycleDefined)
|
||||
{
|
||||
*g_StdStream << " Freq (cnt/ptime):";
|
||||
UInt64 us = processTime / 10;
|
||||
if (us == 0)
|
||||
us = 1;
|
||||
PrintNum(cycleTime / us, 6);
|
||||
*g_StdStream << " MHz";
|
||||
}
|
||||
#endif
|
||||
|
||||
PrintTime("Process", kernelTime + userTime, totalTime);
|
||||
PrintTime("Process", processTime, totalTime);
|
||||
#ifndef UNDER_CE
|
||||
if (memDefined) PrintMemUsage("Virtual ", m.PeakPagefileUsage);
|
||||
#endif
|
||||
@@ -475,10 +596,96 @@ static void PrintStat()
|
||||
#ifndef UNDER_CE
|
||||
if (memDefined) PrintMemUsage("Physical", m.PeakWorkingSetSize);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
#else // ! _WIN32
|
||||
|
||||
static UInt64 Get_timeofday_us()
|
||||
{
|
||||
struct timeval now;
|
||||
if (gettimeofday(&now, 0 ) == 0)
|
||||
return (UInt64)now.tv_sec * 1000000 + (UInt64)now.tv_usec;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void PrintTime(const char *s, UInt64 val, UInt64 total_us, UInt64 kFreq)
|
||||
{
|
||||
*g_StdStream << endl << s << " Time =";
|
||||
|
||||
{
|
||||
UInt64 sec, ms;
|
||||
|
||||
if (kFreq == 0)
|
||||
{
|
||||
sec = val / 1000000;
|
||||
ms = val % 1000000 / 1000;
|
||||
}
|
||||
else
|
||||
{
|
||||
sec = val / kFreq;
|
||||
ms = (UInt32)((val - (sec * kFreq)) * 1000 / kFreq);
|
||||
}
|
||||
|
||||
PrintNum(sec, 6);
|
||||
*g_StdStream << '.';
|
||||
PrintNum(ms, 3, '0');
|
||||
}
|
||||
|
||||
if (total_us == 0)
|
||||
return;
|
||||
|
||||
UInt64 percent = 0;
|
||||
if (kFreq == 0)
|
||||
percent = val * 100 / total_us;
|
||||
else
|
||||
{
|
||||
const UInt64 kMaxVal = (UInt64)(Int64)-1;
|
||||
UInt32 m = 100000000;
|
||||
for (;;)
|
||||
{
|
||||
if (m == 0 || kFreq == 0)
|
||||
break;
|
||||
if (kMaxVal / m > val &&
|
||||
kMaxVal / kFreq > total_us)
|
||||
break;
|
||||
if (val > m)
|
||||
val >>= 1;
|
||||
else
|
||||
m >>= 1;
|
||||
if (kFreq > total_us)
|
||||
kFreq >>= 1;
|
||||
else
|
||||
total_us >>= 1;
|
||||
}
|
||||
const UInt64 total = kFreq * total_us;
|
||||
if (total != 0)
|
||||
percent = val * m / total;
|
||||
}
|
||||
*g_StdStream << " =";
|
||||
PrintNum(percent, 5);
|
||||
*g_StdStream << '%';
|
||||
}
|
||||
|
||||
static void PrintStat(UInt64 startTime)
|
||||
{
|
||||
tms t;
|
||||
/* clock_t res = */ times(&t);
|
||||
const UInt64 totalTime = Get_timeofday_us() - startTime;
|
||||
const UInt64 kFreq = (UInt64)sysconf(_SC_CLK_TCK);
|
||||
PrintTime("Kernel ", (UInt64)t.tms_stime, totalTime, kFreq);
|
||||
PrintTime("User ", (UInt64)t.tms_utime, totalTime, kFreq);
|
||||
PrintTime("Process", (UInt64)t.tms_utime + (UInt64)t.tms_stime, totalTime, kFreq);
|
||||
PrintTime("Global ", totalTime, totalTime, 0);
|
||||
*g_StdStream << endl;
|
||||
}
|
||||
|
||||
#endif // ! _WIN32
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
static void PrintHexId(CStdOutStream &so, UInt64 id)
|
||||
{
|
||||
char s[32];
|
||||
@@ -486,23 +693,62 @@ static void PrintHexId(CStdOutStream &so, UInt64 id)
|
||||
PrintStringRight(so, s, 8);
|
||||
}
|
||||
|
||||
#ifndef _WIN32
|
||||
void Set_ModuleDirPrefix_From_ProgArg0(const char *s);
|
||||
#endif
|
||||
|
||||
int Main2(
|
||||
#ifndef _WIN32
|
||||
int numArgs, char *args[]
|
||||
#endif
|
||||
);
|
||||
int Main2(
|
||||
#ifndef _WIN32
|
||||
int numArgs, char *args[]
|
||||
#endif
|
||||
)
|
||||
{
|
||||
#if defined(MY_CPU_SIZEOF_POINTER)
|
||||
{ unsigned k = sizeof(void *); if (k != MY_CPU_SIZEOF_POINTER) throw "incorrect MY_CPU_PTR_SIZE"; }
|
||||
#endif
|
||||
|
||||
#if defined(_WIN32) && !defined(UNDER_CE)
|
||||
SetFileApisToOEM();
|
||||
#endif
|
||||
|
||||
#ifdef ENV_HAVE_LOCALE
|
||||
// printf("\nBefore SetLocale() : %s\n", IsNativeUtf8() ? "NATIVE UTF-8" : "IS NOT NATIVE UTF-8");
|
||||
MY_SetLocale();
|
||||
// printf("\nAfter SetLocale() : %s\n", IsNativeUtf8() ? "NATIVE UTF-8" : "IS NOT NATIVE UTF-8");
|
||||
#endif
|
||||
|
||||
#ifndef _WIN32
|
||||
UInt64 startTime = Get_timeofday_us();
|
||||
#endif
|
||||
|
||||
UStringVector commandStrings;
|
||||
|
||||
#ifdef _WIN32
|
||||
NCommandLineParser::SplitCommandLine(GetCommandLineW(), commandStrings);
|
||||
#else
|
||||
GetArguments(numArgs, args, commandStrings);
|
||||
{
|
||||
if (numArgs > 0)
|
||||
Set_ModuleDirPrefix_From_ProgArg0(args[0]);
|
||||
|
||||
for (int i = 0; i < numArgs; i++)
|
||||
{
|
||||
AString a (args[i]);
|
||||
/*
|
||||
printf("\n%d %s :", i, a.Ptr());
|
||||
for (unsigned k = 0; k < a.Len(); k++)
|
||||
printf(" %2x", (unsigned)(Byte)a[k]);
|
||||
*/
|
||||
const UString s = MultiByteToUnicodeString(a);
|
||||
commandStrings.Add(s);
|
||||
}
|
||||
// printf("\n");
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef UNDER_CE
|
||||
@@ -542,10 +788,53 @@ int Main2(
|
||||
}
|
||||
|
||||
if (options.EnableHeaders)
|
||||
{
|
||||
ShowCopyrightAndHelp(g_StdStream, false);
|
||||
if (!parser.Parse1Log.IsEmpty())
|
||||
*g_StdStream << parser.Parse1Log;
|
||||
}
|
||||
|
||||
parser.Parse2(options);
|
||||
|
||||
{
|
||||
int cp = options.ConsoleCodePage;
|
||||
|
||||
int stdout_cp = cp;
|
||||
int stderr_cp = cp;
|
||||
int stdin_cp = cp;
|
||||
|
||||
/*
|
||||
// these cases are complicated.
|
||||
// maybe we must use CRT functions instead of console WIN32.
|
||||
// different Windows/CRT versions also can work different ways.
|
||||
// so the following code was not enabled:
|
||||
if (cp == -1)
|
||||
{
|
||||
// we set CodePage only if stream is attached to terminal
|
||||
// maybe we should set CodePage even if is not terminal?
|
||||
#ifdef _WIN32
|
||||
{
|
||||
UINT ccp = GetConsoleOutputCP();
|
||||
if (ccp != 0)
|
||||
{
|
||||
if (options.IsStdOutTerminal) stdout_cp = ccp;
|
||||
if (options.IsStdErrTerminal) stderr_cp = ccp;
|
||||
}
|
||||
}
|
||||
if (options.IsInTerminal)
|
||||
{
|
||||
UINT ccp = GetConsoleCP();
|
||||
if (ccp != 0) stdin_cp = ccp;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
*/
|
||||
|
||||
if (stdout_cp != -1) g_StdOut.CodePage = stdout_cp;
|
||||
if (stderr_cp != -1) g_StdErr.CodePage = stderr_cp;
|
||||
if (stdin_cp != -1) g_StdIn.CodePage = stdin_cp;
|
||||
}
|
||||
|
||||
unsigned percentsNameLevel = 1;
|
||||
if (options.LogLevel == 0 || options.Number_for_Percents != options.Number_for_Out)
|
||||
percentsNameLevel = 2;
|
||||
@@ -559,13 +848,13 @@ int Main2(
|
||||
#if !defined(UNDER_CE)
|
||||
CONSOLE_SCREEN_BUFFER_INFO consoleInfo;
|
||||
if (GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &consoleInfo))
|
||||
consoleWidth = consoleInfo.dwSize.X;
|
||||
consoleWidth = (unsigned)consoleInfo.dwSize.X;
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
||||
struct winsize w;
|
||||
if (ioctl(0, TIOCGWINSZ, &w) == )
|
||||
if (ioctl(0, TIOCGWINSZ, &w) == 0)
|
||||
consoleWidth = w.ws_col;
|
||||
|
||||
#endif
|
||||
@@ -577,6 +866,19 @@ int Main2(
|
||||
codecs->CaseSensitive = options.CaseSensitive;
|
||||
ThrowException_if_Error(codecs->Load());
|
||||
|
||||
#ifdef EXTERNAL_CODECS
|
||||
{
|
||||
UString s;
|
||||
codecs->GetCodecsErrorMessage(s);
|
||||
if (!s.IsEmpty())
|
||||
{
|
||||
CStdOutStream &so = (g_StdStream ? *g_StdStream : g_StdOut);
|
||||
so << endl << s << endl;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
bool isExtractGroupCommand = options.Command.IsFromExtractGroup();
|
||||
|
||||
if (codecs->Formats.Size() == 0 &&
|
||||
@@ -640,14 +942,14 @@ int Main2(
|
||||
so << endl << "Libs:" << endl;
|
||||
for (i = 0; i < codecs->Libs.Size(); i++)
|
||||
{
|
||||
PrintLibIndex(so, i);
|
||||
PrintLibIndex(so, (int)i);
|
||||
so << ' ' << codecs->Libs[i].Path << endl;
|
||||
}
|
||||
#endif
|
||||
|
||||
so << endl << "Formats:" << endl;
|
||||
|
||||
const char * const kArcFlags = "KSNFMGOPBELH";
|
||||
const char * const kArcFlags = "KSNFMGOPBELHX";
|
||||
const unsigned kNumArcFlags = (unsigned)strlen(kArcFlags);
|
||||
|
||||
for (i = 0; i < codecs->Formats.Size(); i++)
|
||||
@@ -804,6 +1106,7 @@ int Main2(
|
||||
options.Properties, options.NumIterations, (FILE *)so);
|
||||
if (hresultMain == S_FALSE)
|
||||
{
|
||||
so << endl;
|
||||
if (g_ErrStream)
|
||||
*g_ErrStream << "\nDecoding ERROR\n";
|
||||
retCode = NExitCode::kFatalError;
|
||||
@@ -863,7 +1166,7 @@ int Main2(
|
||||
}
|
||||
}
|
||||
|
||||
if (hresultMain == S_OK)
|
||||
if (hresultMain == S_OK) {
|
||||
if (isExtractGroupCommand)
|
||||
{
|
||||
CExtractCallbackConsole *ecs = new CExtractCallbackConsole;
|
||||
@@ -992,7 +1295,7 @@ int Main2(
|
||||
if (isError)
|
||||
retCode = NExitCode::kFatalError;
|
||||
|
||||
if (so)
|
||||
if (so) {
|
||||
if (ecs->NumArcsWithError != 0 || ecs->NumFileErrors != 0)
|
||||
{
|
||||
// if (ecs->NumArchives > 1)
|
||||
@@ -1023,8 +1326,9 @@ int Main2(
|
||||
PrintHashStat(*so, hb);
|
||||
}
|
||||
}
|
||||
} // if (so)
|
||||
}
|
||||
else
|
||||
else // if_(!isExtractGroupCommand)
|
||||
{
|
||||
UInt64 numErrors = 0;
|
||||
UInt64 numWarnings = 0;
|
||||
@@ -1060,7 +1364,8 @@ int Main2(
|
||||
g_StdOut << endl << "Errors: " << numErrors << endl;
|
||||
retCode = NExitCode::kFatalError;
|
||||
}
|
||||
}
|
||||
} // if_(isExtractGroupCommand)
|
||||
} // if_(hresultMain == S_OK)
|
||||
}
|
||||
else if (options.Command.IsFromUpdateGroup())
|
||||
{
|
||||
@@ -1146,7 +1451,11 @@ int Main2(
|
||||
ShowMessageAndThrowException(kUserErrorMessage, NExitCode::kUserError);
|
||||
|
||||
if (options.ShowTime && g_StdStream)
|
||||
PrintStat();
|
||||
PrintStat(
|
||||
#ifndef _WIN32
|
||||
startTime
|
||||
#endif
|
||||
);
|
||||
|
||||
ThrowException_if_Error(hresultMain);
|
||||
|
||||
|
||||
@@ -19,7 +19,11 @@
|
||||
|
||||
using namespace NWindows;
|
||||
|
||||
extern
|
||||
CStdOutStream *g_StdStream;
|
||||
CStdOutStream *g_StdStream = NULL;
|
||||
extern
|
||||
CStdOutStream *g_ErrStream;
|
||||
CStdOutStream *g_ErrStream = NULL;
|
||||
|
||||
extern int Main2(
|
||||
@@ -48,7 +52,9 @@ static void PrintError(const char *message)
|
||||
*g_ErrStream << "\n\n" << message << endl;
|
||||
}
|
||||
|
||||
#if defined(_WIN32) && defined(_UNICODE) && !defined(_WIN64) && !defined(UNDER_CE)
|
||||
#define NT_CHECK_FAIL_ACTION *g_StdStream << "Unsupported Windows version"; return NExitCode::kFatalError;
|
||||
#endif
|
||||
|
||||
int MY_CDECL main
|
||||
(
|
||||
|
||||
@@ -46,6 +46,8 @@ public:
|
||||
#endif
|
||||
|
||||
{}
|
||||
|
||||
virtual ~COpenCallbackConsole() {}
|
||||
|
||||
void Init(CStdOutStream *outStream, CStdOutStream *errorStream, CStdOutStream *percentStream)
|
||||
{
|
||||
|
||||
@@ -143,7 +143,7 @@ void CPercentPrinter::Print()
|
||||
|
||||
_tempU = FileName;
|
||||
_so->Normalize_UString(_tempU);
|
||||
StdOut_Convert_UString_to_AString(_tempU, _temp);
|
||||
_so->Convert_UString_to_AString(_tempU, _temp);
|
||||
if (_s.Len() + _temp.Len() > MaxLen)
|
||||
{
|
||||
unsigned len = FileName.Len();
|
||||
@@ -157,7 +157,7 @@ void CPercentPrinter::Print()
|
||||
_tempU.Delete(len / 2, _tempU.Len() - len);
|
||||
_tempU.Insert(len / 2, L" . ");
|
||||
_so->Normalize_UString(_tempU);
|
||||
StdOut_Convert_UString_to_AString(_tempU, _temp);
|
||||
_so->Convert_UString_to_AString(_tempU, _temp);
|
||||
if (_s.Len() + _temp.Len() <= MaxLen)
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -209,6 +209,7 @@ HRESULT CCallbackConsoleBase::OpenFileError_Base(const FString &path, DWORD syst
|
||||
{
|
||||
MT_LOCK
|
||||
FailedFiles.AddError(path, systemError);
|
||||
NumNonOpenFiles++;
|
||||
/*
|
||||
if (systemError == ERROR_SHARING_VIOLATION)
|
||||
{
|
||||
@@ -282,6 +283,12 @@ HRESULT CUpdateCallbackConsole::StartOpenArchive(const wchar_t *name)
|
||||
|
||||
HRESULT CUpdateCallbackConsole::StartArchive(const wchar_t *name, bool updating)
|
||||
{
|
||||
if (NeedPercents())
|
||||
_percent.ClosePrint(true);
|
||||
|
||||
_percent.ClearCurState();
|
||||
NumNonOpenFiles = 0;
|
||||
|
||||
if (_so)
|
||||
{
|
||||
*_so << (updating ? kUpdatingArchiveMessage : kCreatingArchiveMessage);
|
||||
@@ -302,7 +309,7 @@ HRESULT CUpdateCallbackConsole::FinishArchive(const CFinishArchiveStat &st)
|
||||
{
|
||||
AString s;
|
||||
// Print_UInt64_and_String(s, _percent.Files == 1 ? "file" : "files", _percent.Files);
|
||||
PrintPropPair(s, "Files read from disk", _percent.Files);
|
||||
PrintPropPair(s, "Files read from disk", _percent.Files - NumNonOpenFiles);
|
||||
s.Add_LF();
|
||||
s += "Archive size: ";
|
||||
PrintSize_bytes_Smart(s, st.OutArcFileSize);
|
||||
|
||||
@@ -56,7 +56,8 @@ public:
|
||||
StdOutMode(false),
|
||||
NeedFlush(false),
|
||||
PercentsNameLevel(1),
|
||||
LogLevel(0)
|
||||
LogLevel(0),
|
||||
NumNonOpenFiles(0)
|
||||
{}
|
||||
|
||||
void SetWindowWidth(unsigned width) { _percent.MaxLen = width - 1; }
|
||||
@@ -82,9 +83,9 @@ public:
|
||||
_percent.ClosePrint(false);
|
||||
}
|
||||
|
||||
|
||||
CErrorPathCodes FailedFiles;
|
||||
CErrorPathCodes ScanErrors;
|
||||
UInt64 NumNonOpenFiles;
|
||||
|
||||
HRESULT PrintProgress(const wchar_t *name, const char *command, bool showInLog);
|
||||
|
||||
@@ -95,21 +96,23 @@ class CUpdateCallbackConsole: public IUpdateCallbackUI2, public CCallbackConsole
|
||||
// void PrintPropPair(const char *name, const wchar_t *val);
|
||||
|
||||
public:
|
||||
bool DeleteMessageWasShown;
|
||||
|
||||
#ifndef _NO_CRYPTO
|
||||
bool PasswordIsDefined;
|
||||
UString Password;
|
||||
bool AskPassword;
|
||||
#endif
|
||||
|
||||
bool DeleteMessageWasShown;
|
||||
|
||||
CUpdateCallbackConsole()
|
||||
: DeleteMessageWasShown(false)
|
||||
CUpdateCallbackConsole():
|
||||
DeleteMessageWasShown(false)
|
||||
#ifndef _NO_CRYPTO
|
||||
, PasswordIsDefined(false)
|
||||
, AskPassword(false)
|
||||
#endif
|
||||
{}
|
||||
|
||||
virtual ~CUpdateCallbackConsole() {}
|
||||
|
||||
/*
|
||||
void Init(CStdOutStream *outStream)
|
||||
|
||||
@@ -78,7 +78,7 @@ static bool GetPassword(CStdOutStream *outStream, UString &psw)
|
||||
DWORD mode = 0;
|
||||
if (console != INVALID_HANDLE_VALUE && console != 0)
|
||||
if (GetConsoleMode(console, &mode))
|
||||
wasChanged = (SetConsoleMode(console, mode & ~ENABLE_ECHO_INPUT) != 0);
|
||||
wasChanged = (SetConsoleMode(console, mode & ~(DWORD)ENABLE_ECHO_INPUT) != 0);
|
||||
bool res = g_StdIn.ScanUStringUntilNewLine(psw);
|
||||
if (wasChanged)
|
||||
SetConsoleMode(console, mode);
|
||||
|
||||
@@ -31,6 +31,7 @@ WIN_OBJS = \
|
||||
$O\PropVariantConv.obj \
|
||||
$O\Registry.obj \
|
||||
$O\System.obj \
|
||||
$O\SystemInfo.obj \
|
||||
$O\TimeUtils.obj \
|
||||
|
||||
7ZIP_COMMON_OBJS = \
|
||||
|
||||
171
CPP/7zip/UI/Console/makefile.gcc
Normal file
171
CPP/7zip/UI/Console/makefile.gcc
Normal file
@@ -0,0 +1,171 @@
|
||||
PROG = 7z
|
||||
IS_NOT_STANDALONE = 1
|
||||
|
||||
# IS_X64 = 1
|
||||
# USE_ASM = 1
|
||||
# ST_MODE = 1
|
||||
|
||||
|
||||
LOCAL_FLAGS_ST =
|
||||
MT_OBJS =
|
||||
|
||||
ifdef ST_MODE
|
||||
|
||||
LOCAL_FLAGS_ST = -D_7ZIP_ST
|
||||
|
||||
ifdef SystemDrive
|
||||
MT_OBJS = \
|
||||
$O/Threads.o \
|
||||
|
||||
endif
|
||||
|
||||
else
|
||||
|
||||
MT_OBJS = \
|
||||
$O/Synchronization.o \
|
||||
$O/Threads.o \
|
||||
|
||||
endif
|
||||
|
||||
|
||||
|
||||
LOCAL_FLAGS_WIN=
|
||||
|
||||
ifdef SystemDrive
|
||||
|
||||
LOCAL_FLAGS_WIN = \
|
||||
-D_7ZIP_LARGE_PAGES \
|
||||
-DWIN_LONG_PATH \
|
||||
-DSUPPORT_DEVICE_FILE \
|
||||
|
||||
SYS_OBJS = \
|
||||
$O/FileSystem.o \
|
||||
$O/Registry.o \
|
||||
$O/MemoryLock.o \
|
||||
$O/DllSecur.o \
|
||||
$O/resource.o \
|
||||
|
||||
else
|
||||
|
||||
SYS_OBJS = \
|
||||
$O/MyWindows.o \
|
||||
|
||||
endif
|
||||
|
||||
|
||||
|
||||
LOCAL_FLAGS = \
|
||||
$(LOCAL_FLAGS_WIN) \
|
||||
$(LOCAL_FLAGS_ST) \
|
||||
-DEXTERNAL_CODECS \
|
||||
|
||||
|
||||
|
||||
CONSOLE_OBJS = \
|
||||
$O/BenchCon.o \
|
||||
$O/ConsoleClose.o \
|
||||
$O/ExtractCallbackConsole.o \
|
||||
$O/HashCon.o \
|
||||
$O/List.o \
|
||||
$O/Main.o \
|
||||
$O/MainAr.o \
|
||||
$O/OpenCallbackConsole.o \
|
||||
$O/PercentPrinter.o \
|
||||
$O/UpdateCallbackConsole.o \
|
||||
$O/UserInputUtils.o \
|
||||
|
||||
UI_COMMON_OBJS = \
|
||||
$O/ArchiveCommandLine.o \
|
||||
$O/ArchiveExtractCallback.o \
|
||||
$O/ArchiveOpenCallback.o \
|
||||
$O/Bench.o \
|
||||
$O/DefaultName.o \
|
||||
$O/EnumDirItems.o \
|
||||
$O/Extract.o \
|
||||
$O/ExtractingFilePath.o \
|
||||
$O/HashCalc.o \
|
||||
$O/LoadCodecs.o \
|
||||
$O/OpenArchive.o \
|
||||
$O/PropIDUtils.o \
|
||||
$O/SetProperties.o \
|
||||
$O/SortUtils.o \
|
||||
$O/TempFiles.o \
|
||||
$O/Update.o \
|
||||
$O/UpdateAction.o \
|
||||
$O/UpdateCallback.o \
|
||||
$O/UpdatePair.o \
|
||||
$O/UpdateProduce.o \
|
||||
|
||||
COMMON_OBJS = \
|
||||
$O/CommandLineParser.o \
|
||||
$O/CRC.o \
|
||||
$O/CrcReg.o \
|
||||
$O/IntToString.o \
|
||||
$O/ListFileUtils.o \
|
||||
$O/NewHandler.o \
|
||||
$O/StdInStream.o \
|
||||
$O/StdOutStream.o \
|
||||
$O/MyString.o \
|
||||
$O/StringConvert.o \
|
||||
$O/StringToInt.o \
|
||||
$O/UTFConvert.o \
|
||||
$O/MyVector.o \
|
||||
$O/Wildcard.o \
|
||||
|
||||
WIN_OBJS = \
|
||||
$O/DLL.o \
|
||||
$O/ErrorMsg.o \
|
||||
$O/FileDir.o \
|
||||
$O/FileFind.o \
|
||||
$O/FileIO.o \
|
||||
$O/FileLink.o \
|
||||
$O/FileName.o \
|
||||
$O/PropVariant.o \
|
||||
$O/PropVariantConv.o \
|
||||
$O/System.o \
|
||||
$O/SystemInfo.o \
|
||||
$O/TimeUtils.o \
|
||||
|
||||
7ZIP_COMMON_OBJS = \
|
||||
$O/CreateCoder.o \
|
||||
$O/CWrappers.o \
|
||||
$O/FilePathAutoRename.o \
|
||||
$O/FileStreams.o \
|
||||
$O/InBuffer.o \
|
||||
$O/InOutTempBuffer.o \
|
||||
$O/FilterCoder.o \
|
||||
$O/LimitedStreams.o \
|
||||
$O/MethodId.o \
|
||||
$O/MethodProps.o \
|
||||
$O/OffsetStream.o \
|
||||
$O/OutBuffer.o \
|
||||
$O/ProgressUtils.o \
|
||||
$O/PropId.o \
|
||||
$O/StreamObjects.o \
|
||||
$O/StreamUtils.o \
|
||||
$O/UniqBlocks.o \
|
||||
|
||||
COMPRESS_OBJS = \
|
||||
$O/CopyCoder.o \
|
||||
|
||||
C_OBJS = \
|
||||
$O/Alloc.o \
|
||||
$O/CpuArch.o \
|
||||
$O/Sort.o \
|
||||
$O/7zCrc.o \
|
||||
$O/7zCrcOpt.o \
|
||||
|
||||
|
||||
OBJS = \
|
||||
$(C_OBJS) \
|
||||
$(MT_OBJS) \
|
||||
$(COMMON_OBJS) \
|
||||
$(WIN_OBJS) \
|
||||
$(SYS_OBJS) \
|
||||
$(COMPRESS_OBJS) \
|
||||
$(7ZIP_COMMON_OBJS) \
|
||||
$(UI_COMMON_OBJS) \
|
||||
$(CONSOLE_OBJS) \
|
||||
|
||||
|
||||
include ../../7zip_gcc.mak
|
||||
@@ -2,6 +2,7 @@
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#include "../../../Common/ComTry.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
|
||||
#include "../../../Windows/COM.h"
|
||||
@@ -31,6 +32,12 @@
|
||||
|
||||
#include "resource.h"
|
||||
|
||||
// #define SHOW_DEBUG_CTX_MENU
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
#include <stdio.h>
|
||||
#endif
|
||||
|
||||
using namespace NWindows;
|
||||
using namespace NFile;
|
||||
using namespace NDir;
|
||||
@@ -63,8 +70,8 @@ CZipContextMenu::~CZipContextMenu()
|
||||
HRESULT CZipContextMenu::GetFileNames(LPDATAOBJECT dataObject, UStringVector &fileNames)
|
||||
{
|
||||
fileNames.Clear();
|
||||
if (dataObject == NULL)
|
||||
return E_FAIL;
|
||||
if (!dataObject)
|
||||
return E_INVALIDARG;
|
||||
|
||||
#ifndef UNDER_CE
|
||||
|
||||
@@ -146,76 +153,24 @@ struct CContextMenuCommand
|
||||
UINT ResourceID;
|
||||
};
|
||||
|
||||
#define CMD_REC(cns, verb, ids) { NContextMenuFlags::cns, CZipContextMenu::cns, verb, ids }
|
||||
|
||||
static const CContextMenuCommand g_Commands[] =
|
||||
{
|
||||
{
|
||||
NContextMenuFlags::kOpen,
|
||||
CZipContextMenu::kOpen,
|
||||
"Open",
|
||||
IDS_CONTEXT_OPEN
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kExtract,
|
||||
CZipContextMenu::kExtract,
|
||||
"Extract",
|
||||
IDS_CONTEXT_EXTRACT
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kExtractHere,
|
||||
CZipContextMenu::kExtractHere,
|
||||
"ExtractHere",
|
||||
IDS_CONTEXT_EXTRACT_HERE
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kExtractTo,
|
||||
CZipContextMenu::kExtractTo,
|
||||
"ExtractTo",
|
||||
IDS_CONTEXT_EXTRACT_TO
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kTest,
|
||||
CZipContextMenu::kTest,
|
||||
"Test",
|
||||
IDS_CONTEXT_TEST
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompress,
|
||||
CZipContextMenu::kCompress,
|
||||
"Compress",
|
||||
IDS_CONTEXT_COMPRESS
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompressEmail,
|
||||
CZipContextMenu::kCompressEmail,
|
||||
"CompressEmail",
|
||||
IDS_CONTEXT_COMPRESS_EMAIL
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompressTo7z,
|
||||
CZipContextMenu::kCompressTo7z,
|
||||
"CompressTo7z",
|
||||
IDS_CONTEXT_COMPRESS_TO
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompressTo7zEmail,
|
||||
CZipContextMenu::kCompressTo7zEmail,
|
||||
"CompressTo7zEmail",
|
||||
IDS_CONTEXT_COMPRESS_TO_EMAIL
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompressToZip,
|
||||
CZipContextMenu::kCompressToZip,
|
||||
"CompressToZip",
|
||||
IDS_CONTEXT_COMPRESS_TO
|
||||
},
|
||||
{
|
||||
NContextMenuFlags::kCompressToZipEmail,
|
||||
CZipContextMenu::kCompressToZipEmail,
|
||||
"CompressToZipEmail",
|
||||
IDS_CONTEXT_COMPRESS_TO_EMAIL
|
||||
}
|
||||
CMD_REC( kOpen, "Open", IDS_CONTEXT_OPEN),
|
||||
CMD_REC( kExtract, "Extract", IDS_CONTEXT_EXTRACT),
|
||||
CMD_REC( kExtractHere, "ExtractHere", IDS_CONTEXT_EXTRACT_HERE),
|
||||
CMD_REC( kExtractTo, "ExtractTo", IDS_CONTEXT_EXTRACT_TO),
|
||||
CMD_REC( kTest, "Test", IDS_CONTEXT_TEST),
|
||||
CMD_REC( kCompress, "Compress", IDS_CONTEXT_COMPRESS),
|
||||
CMD_REC( kCompressEmail, "CompressEmail", IDS_CONTEXT_COMPRESS_EMAIL),
|
||||
CMD_REC( kCompressTo7z, "CompressTo7z", IDS_CONTEXT_COMPRESS_TO),
|
||||
CMD_REC( kCompressTo7zEmail, "CompressTo7zEmail", IDS_CONTEXT_COMPRESS_TO_EMAIL),
|
||||
CMD_REC( kCompressToZip, "CompressToZip", IDS_CONTEXT_COMPRESS_TO),
|
||||
CMD_REC( kCompressToZipEmail, "CompressToZipEmail", IDS_CONTEXT_COMPRESS_TO_EMAIL)
|
||||
};
|
||||
|
||||
|
||||
struct CHashCommand
|
||||
{
|
||||
CZipContextMenu::ECommandInternalID CommandInternalID;
|
||||
@@ -232,6 +187,7 @@ static const CHashCommand g_HashCommands[] =
|
||||
{ CZipContextMenu::kHash_All, "*", "*" }
|
||||
};
|
||||
|
||||
|
||||
static int FindCommand(CZipContextMenu::ECommandInternalID &id)
|
||||
{
|
||||
for (unsigned i = 0; i < ARRAY_SIZE(g_Commands); i++)
|
||||
@@ -240,22 +196,31 @@ static int FindCommand(CZipContextMenu::ECommandInternalID &id)
|
||||
return -1;
|
||||
}
|
||||
|
||||
bool CZipContextMenu::FillCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &commandMapItem)
|
||||
|
||||
void CZipContextMenu::FillCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &cmi)
|
||||
{
|
||||
mainString.Empty();
|
||||
int i = FindCommand(id);
|
||||
if (i < 0)
|
||||
return false;
|
||||
const CContextMenuCommand &command = g_Commands[i];
|
||||
commandMapItem.CommandInternalID = command.CommandInternalID;
|
||||
commandMapItem.Verb = kMainVerb;
|
||||
commandMapItem.Verb += command.Verb;
|
||||
// LangString(command.ResourceHelpID, command.LangID + 1, commandMapItem.HelpString);
|
||||
throw 201908;
|
||||
const CContextMenuCommand &command = g_Commands[(unsigned)i];
|
||||
cmi.CommandInternalID = command.CommandInternalID;
|
||||
cmi.Verb = kMainVerb;
|
||||
cmi.Verb += command.Verb;
|
||||
// cmi.HelpString = cmi.Verb;
|
||||
LangString(command.ResourceID, mainString);
|
||||
return true;
|
||||
// return true;
|
||||
}
|
||||
|
||||
static bool MyInsertMenu(CMenu &menu, int pos, UINT id, const UString &s, HBITMAP bitmap)
|
||||
|
||||
void CZipContextMenu::AddCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &cmi)
|
||||
{
|
||||
FillCommand(id, mainString, cmi);
|
||||
_commandMap.Add(cmi);
|
||||
}
|
||||
|
||||
|
||||
static void MyInsertMenu(CMenu &menu, int pos, UINT id, const UString &s, HBITMAP bitmap)
|
||||
{
|
||||
CMenuItem mi;
|
||||
mi.fType = MFT_STRING;
|
||||
@@ -266,12 +231,40 @@ static bool MyInsertMenu(CMenu &menu, int pos, UINT id, const UString &s, HBITMA
|
||||
mi.StringValue = s;
|
||||
mi.hbmpUnchecked = bitmap;
|
||||
// mi.hbmpChecked = bitmap; // do we need hbmpChecked ???
|
||||
return menu.InsertItem(pos, true, mi);
|
||||
if (!menu.InsertItem(pos, true, mi))
|
||||
throw 20190816;
|
||||
|
||||
// SetMenuItemBitmaps also works
|
||||
// ::SetMenuItemBitmaps(menu, pos, MF_BYPOSITION, bitmap, NULL);
|
||||
}
|
||||
|
||||
|
||||
static void MyAddSubMenu(
|
||||
CObjectVector<CZipContextMenu::CCommandMapItem> &_commandMap,
|
||||
const char *verb,
|
||||
CMenu &menu, int pos, UINT id, const UString &s, HMENU hSubMenu, HBITMAP bitmap)
|
||||
{
|
||||
CZipContextMenu::CCommandMapItem cmi;
|
||||
cmi.CommandInternalID = CZipContextMenu::kCommandNULL;
|
||||
cmi.Verb = verb;
|
||||
// cmi.HelpString = verb;
|
||||
_commandMap.Add(cmi);
|
||||
|
||||
CMenuItem mi;
|
||||
mi.fType = MFT_STRING;
|
||||
mi.fMask = MIIM_SUBMENU | MIIM_TYPE | MIIM_ID;
|
||||
if (bitmap)
|
||||
mi.fMask |= MIIM_CHECKMARKS;
|
||||
mi.wID = id;
|
||||
mi.hSubMenu = hSubMenu;
|
||||
mi.hbmpUnchecked = bitmap;
|
||||
|
||||
mi.StringValue = s;
|
||||
if (!menu.InsertItem(pos, true, mi))
|
||||
throw 20190817;
|
||||
}
|
||||
|
||||
|
||||
static const char * const kArcExts[] =
|
||||
{
|
||||
"7z"
|
||||
@@ -289,6 +282,7 @@ static bool IsItArcExt(const UString &ext)
|
||||
return false;
|
||||
}
|
||||
|
||||
UString GetSubFolderNameForExtract(const UString &arcName);
|
||||
UString GetSubFolderNameForExtract(const UString &arcName)
|
||||
{
|
||||
int dotPos = arcName.ReverseFind_Dot();
|
||||
@@ -302,11 +296,11 @@ UString GetSubFolderNameForExtract(const UString &arcName)
|
||||
if (dotPos > 0)
|
||||
{
|
||||
const UString ext2 = res.Ptr(dotPos + 1);
|
||||
if (ext.IsEqualTo_Ascii_NoCase("001") && IsItArcExt(ext2)
|
||||
|| ext.IsEqualTo_Ascii_NoCase("rar") &&
|
||||
if ((ext.IsEqualTo_Ascii_NoCase("001") && IsItArcExt(ext2))
|
||||
|| (ext.IsEqualTo_Ascii_NoCase("rar") &&
|
||||
( ext2.IsEqualTo_Ascii_NoCase("part001")
|
||||
|| ext2.IsEqualTo_Ascii_NoCase("part01")
|
||||
|| ext2.IsEqualTo_Ascii_NoCase("part1")))
|
||||
|| ext2.IsEqualTo_Ascii_NoCase("part1"))))
|
||||
res.DeleteFrom(dotPos);
|
||||
res.TrimRight();
|
||||
}
|
||||
@@ -415,17 +409,44 @@ static bool DoNeedExtract(const FString &name)
|
||||
// we must use diferent Verbs for Popup subMenu.
|
||||
void CZipContextMenu::AddMapItem_ForSubMenu(const char *verb)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
commandMapItem.CommandInternalID = kCommandNULL;
|
||||
commandMapItem.Verb = verb;
|
||||
_commandMap.Add(commandMapItem);
|
||||
CCommandMapItem cmi;
|
||||
cmi.CommandInternalID = kCommandNULL;
|
||||
cmi.Verb = verb;
|
||||
// cmi.HelpString = verb;
|
||||
_commandMap.Add(cmi);
|
||||
}
|
||||
|
||||
|
||||
static HRESULT RETURN_WIN32_LastError_AS_HRESULT()
|
||||
{
|
||||
DWORD lastError = ::GetLastError();
|
||||
if (lastError == 0)
|
||||
return E_FAIL;
|
||||
return HRESULT_FROM_WIN32(lastError);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
we add CCommandMapItem to _commandMap for each new Mene ID.
|
||||
so then we use _commandMap[offset].
|
||||
That way we can execute commands that have menu item.
|
||||
Another non-implemented way:
|
||||
We can return the number off all possible commnad in QueryContextMenu().
|
||||
so the caller could call InvokeCommand() via string verb aven
|
||||
without using menu items.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
UINT commandIDFirst, UINT commandIDLast, UINT flags)
|
||||
{
|
||||
// OutputDebugStringA("QueryContextMenu");
|
||||
COM_TRY_BEGIN
|
||||
try {
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
{ char s[256]; sprintf(s, "QueryContextMenu: index=%d first=%d last=%d flags=%x _files=%d",
|
||||
indexMenu, commandIDFirst, commandIDLast, flags, _fileNames.Size()); OutputDebugStringA(s); }
|
||||
|
||||
/*
|
||||
for (UInt32 i = 0; i < _fileNames.Size(); i++)
|
||||
@@ -433,15 +454,29 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
OutputDebugStringW(_fileNames[i]);
|
||||
}
|
||||
*/
|
||||
#endif
|
||||
|
||||
LoadLangOneTime();
|
||||
|
||||
if (_fileNames.Size() == 0)
|
||||
return E_FAIL;
|
||||
{
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, 0);
|
||||
// return E_INVALIDARG;
|
||||
}
|
||||
|
||||
if (commandIDFirst > commandIDLast)
|
||||
return E_INVALIDARG;
|
||||
|
||||
|
||||
UINT currentCommandID = commandIDFirst;
|
||||
if ((flags & 0x000F) != CMF_NORMAL &&
|
||||
(flags & CMF_VERBSONLY) == 0 &&
|
||||
(flags & CMF_EXPLORE) == 0)
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, currentCommandID);
|
||||
|
||||
if ((flags & 0x000F) != CMF_NORMAL
|
||||
&& (flags & CMF_VERBSONLY) == 0
|
||||
&& (flags & CMF_EXPLORE) == 0)
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, currentCommandID - commandIDFirst);
|
||||
// return MAKE_HRESULT(SEVERITY_SUCCESS, 0, currentCommandID);
|
||||
// 19.01 : we changed from (currentCommandID) to (currentCommandID - commandIDFirst)
|
||||
// why it was so before?
|
||||
|
||||
_commandMap.Clear();
|
||||
|
||||
@@ -462,7 +497,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
if (ci.Cascaded.Val)
|
||||
{
|
||||
if (!popupMenu.CreatePopup())
|
||||
return E_FAIL;
|
||||
return RETURN_WIN32_LastError_AS_HRESULT();
|
||||
menuDestroyer.Attach(popupMenu);
|
||||
|
||||
/* 9.31: we commented the following code. Probably we don't need.
|
||||
@@ -508,7 +543,10 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
#endif
|
||||
{
|
||||
if (!fi0.Find(us2fs(fileName)))
|
||||
return E_FAIL;
|
||||
{
|
||||
throw 20190820;
|
||||
// return RETURN_WIN32_LastError_AS_HRESULT();
|
||||
}
|
||||
GetOnlyDirPrefix(us2fs(fileName), folderPrefix);
|
||||
}
|
||||
}
|
||||
@@ -523,10 +561,9 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
bool thereIsMainOpenItem = ((contextMenuFlags & NContextMenuFlags::kOpen) != 0);
|
||||
if (thereIsMainOpenItem)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
FillCommand(kOpen, mainString, commandMapItem);
|
||||
CCommandMapItem cmi;
|
||||
AddCommand(kOpen, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
if ((contextMenuFlags & NContextMenuFlags::kOpenAs) != 0
|
||||
// && (!thereIsMainOpenItem || !FindExt(kNoOpenAsExtensions, fi0.Name))
|
||||
@@ -535,37 +572,26 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
CMenu subMenu;
|
||||
if (subMenu.CreatePopup())
|
||||
{
|
||||
CMenuItem mi;
|
||||
mi.fType = MFT_STRING;
|
||||
mi.fMask = MIIM_SUBMENU | MIIM_TYPE | MIIM_ID;
|
||||
if (bitmap)
|
||||
mi.fMask |= MIIM_CHECKMARKS;
|
||||
mi.wID = currentCommandID++;
|
||||
mi.hSubMenu = subMenu;
|
||||
mi.hbmpUnchecked = bitmap;
|
||||
|
||||
LangString(IDS_CONTEXT_OPEN, mi.StringValue);
|
||||
popupMenu.InsertItem(subIndex++, true, mi);
|
||||
AddMapItem_ForSubMenu(kOpenCascadedVerb);
|
||||
MyAddSubMenu(_commandMap, kOpenCascadedVerb, popupMenu, subIndex++, currentCommandID++, LangString(IDS_CONTEXT_OPEN), subMenu, bitmap);
|
||||
|
||||
UINT subIndex2 = 0;
|
||||
for (unsigned i = (thereIsMainOpenItem ? 1 : 0); i < ARRAY_SIZE(kOpenTypes); i++)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
if (i == 0)
|
||||
FillCommand(kOpen, mainString, commandMapItem);
|
||||
FillCommand(kOpen, mainString, cmi);
|
||||
else
|
||||
{
|
||||
mainString = kOpenTypes[i];
|
||||
commandMapItem.CommandInternalID = kOpen;
|
||||
commandMapItem.Verb = kMainVerb;
|
||||
commandMapItem.Verb += ".Open.";
|
||||
commandMapItem.Verb += mainString;
|
||||
commandMapItem.HelpString = mainString;
|
||||
commandMapItem.ArcType = mainString;
|
||||
cmi.CommandInternalID = kOpen;
|
||||
cmi.Verb = kMainVerb;
|
||||
cmi.Verb += ".Open.";
|
||||
cmi.Verb += mainString;
|
||||
// cmi.HelpString = cmi.Verb;
|
||||
cmi.ArcType = mainString;
|
||||
}
|
||||
_commandMap.Add(cmi);
|
||||
MyInsertMenu(subMenu, subIndex2++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
subMenu.Detach();
|
||||
@@ -584,7 +610,10 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
{
|
||||
NFind::CFileInfo fi;
|
||||
if (!fi.Find(us2fs(_fileNames[i])))
|
||||
return E_FAIL;
|
||||
{
|
||||
throw 20190821;
|
||||
// return RETURN_WIN32_LastError_AS_HRESULT();
|
||||
}
|
||||
if (!fi.IsDir() && DoNeedExtract(fi.Name))
|
||||
{
|
||||
needExtract = true;
|
||||
@@ -610,43 +639,39 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
if ((contextMenuFlags & NContextMenuFlags::kExtract) != 0)
|
||||
{
|
||||
// Extract
|
||||
CCommandMapItem commandMapItem;
|
||||
FillCommand(kExtract, mainString, commandMapItem);
|
||||
commandMapItem.Folder = baseFolder + specFolder;
|
||||
CCommandMapItem cmi;
|
||||
cmi.Folder = baseFolder + specFolder;
|
||||
AddCommand(kExtract, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
if ((contextMenuFlags & NContextMenuFlags::kExtractHere) != 0)
|
||||
{
|
||||
// Extract Here
|
||||
CCommandMapItem commandMapItem;
|
||||
FillCommand(kExtractHere, mainString, commandMapItem);
|
||||
commandMapItem.Folder = baseFolder;
|
||||
CCommandMapItem cmi;
|
||||
cmi.Folder = baseFolder;
|
||||
AddCommand(kExtractHere, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
if ((contextMenuFlags & NContextMenuFlags::kExtractTo) != 0)
|
||||
{
|
||||
// Extract To
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
UString s;
|
||||
FillCommand(kExtractTo, s, commandMapItem);
|
||||
commandMapItem.Folder = baseFolder + specFolder;
|
||||
cmi.Folder = baseFolder + specFolder;
|
||||
AddCommand(kExtractTo, s, cmi);
|
||||
MyFormatNew_ReducedName(s, specFolder);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
}
|
||||
|
||||
if ((contextMenuFlags & NContextMenuFlags::kTest) != 0)
|
||||
{
|
||||
// Test
|
||||
CCommandMapItem commandMapItem;
|
||||
FillCommand(kTest, mainString, commandMapItem);
|
||||
CCommandMapItem cmi;
|
||||
AddCommand(kTest, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -660,26 +685,24 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
// Compress
|
||||
if ((contextMenuFlags & NContextMenuFlags::kCompress) != 0)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
if (_dropMode)
|
||||
commandMapItem.Folder = _dropPath;
|
||||
cmi.Folder = _dropPath;
|
||||
else
|
||||
commandMapItem.Folder = fs2us(folderPrefix);
|
||||
commandMapItem.ArcName = arcName;
|
||||
FillCommand(kCompress, mainString, commandMapItem);
|
||||
cmi.Folder = fs2us(folderPrefix);
|
||||
cmi.ArcName = arcName;
|
||||
AddCommand(kCompress, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
#ifdef EMAIL_SUPPORT
|
||||
// CompressEmail
|
||||
if ((contextMenuFlags & NContextMenuFlags::kCompressEmail) != 0 && !_dropMode)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
commandMapItem.ArcName = arcName;
|
||||
FillCommand(kCompressEmail, mainString, commandMapItem);
|
||||
CCommandMapItem cmi;
|
||||
cmi.ArcName = arcName;
|
||||
AddCommand(kCompressEmail, mainString, cmi);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, mainString, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -687,32 +710,30 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
if (contextMenuFlags & NContextMenuFlags::kCompressTo7z &&
|
||||
!arcName7z.IsEqualTo_NoCase(fs2us(fi0.Name)))
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
UString s;
|
||||
FillCommand(kCompressTo7z, s, commandMapItem);
|
||||
if (_dropMode)
|
||||
commandMapItem.Folder = _dropPath;
|
||||
cmi.Folder = _dropPath;
|
||||
else
|
||||
commandMapItem.Folder = fs2us(folderPrefix);
|
||||
commandMapItem.ArcName = arcName7z;
|
||||
commandMapItem.ArcType = "7z";
|
||||
cmi.Folder = fs2us(folderPrefix);
|
||||
cmi.ArcName = arcName7z;
|
||||
cmi.ArcType = "7z";
|
||||
AddCommand(kCompressTo7z, s, cmi);
|
||||
MyFormatNew_ReducedName(s, arcName7z);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
#ifdef EMAIL_SUPPORT
|
||||
// CompressTo7zEmail
|
||||
if ((contextMenuFlags & NContextMenuFlags::kCompressTo7zEmail) != 0 && !_dropMode)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
UString s;
|
||||
FillCommand(kCompressTo7zEmail, s, commandMapItem);
|
||||
commandMapItem.ArcName = arcName7z;
|
||||
commandMapItem.ArcType = "7z";
|
||||
cmi.ArcName = arcName7z;
|
||||
cmi.ArcType = "7z";
|
||||
AddCommand(kCompressTo7zEmail, s, cmi);
|
||||
MyFormatNew_ReducedName(s, arcName7z);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -720,32 +741,30 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
if (contextMenuFlags & NContextMenuFlags::kCompressToZip &&
|
||||
!arcNameZip.IsEqualTo_NoCase(fs2us(fi0.Name)))
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
UString s;
|
||||
FillCommand(kCompressToZip, s, commandMapItem);
|
||||
if (_dropMode)
|
||||
commandMapItem.Folder = _dropPath;
|
||||
cmi.Folder = _dropPath;
|
||||
else
|
||||
commandMapItem.Folder = fs2us(folderPrefix);
|
||||
commandMapItem.ArcName = arcNameZip;
|
||||
commandMapItem.ArcType = "zip";
|
||||
cmi.Folder = fs2us(folderPrefix);
|
||||
cmi.ArcName = arcNameZip;
|
||||
cmi.ArcType = "zip";
|
||||
AddCommand(kCompressToZip, s, cmi);
|
||||
MyFormatNew_ReducedName(s, arcNameZip);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
#ifdef EMAIL_SUPPORT
|
||||
// CompressToZipEmail
|
||||
if ((contextMenuFlags & NContextMenuFlags::kCompressToZipEmail) != 0 && !_dropMode)
|
||||
{
|
||||
CCommandMapItem commandMapItem;
|
||||
CCommandMapItem cmi;
|
||||
UString s;
|
||||
FillCommand(kCompressToZipEmail, s, commandMapItem);
|
||||
commandMapItem.ArcName = arcNameZip;
|
||||
commandMapItem.ArcType = "zip";
|
||||
cmi.ArcName = arcNameZip;
|
||||
cmi.ArcType = "zip";
|
||||
AddCommand(kCompressToZipEmail, s, cmi);
|
||||
MyFormatNew_ReducedName(s, arcNameZip);
|
||||
MyInsertMenu(popupMenu, subIndex++, currentCommandID++, s, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@@ -757,22 +776,10 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
|
||||
if (ci.Cascaded.Val)
|
||||
{
|
||||
CMenuItem mi;
|
||||
mi.fType = MFT_STRING;
|
||||
mi.fMask = MIIM_SUBMENU | MIIM_TYPE | MIIM_ID;
|
||||
if (bitmap)
|
||||
mi.fMask |= MIIM_CHECKMARKS;
|
||||
mi.wID = currentCommandID++;
|
||||
mi.hSubMenu = popupMenu.Detach();
|
||||
mi.StringValue = "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);
|
||||
MyAddSubMenu(_commandMap, kMainVerb, menu, indexMenu++, currentCommandID++, (UString)"7-Zip", popupMenu.Detach(), bitmap);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -783,7 +790,7 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
|
||||
if (!_isMenuForFM &&
|
||||
((contextMenuFlags & NContextMenuFlags::kCRC) != 0
|
||||
&& currentCommandID + 6 <= commandIDLast))
|
||||
&& currentCommandID + 1 < commandIDLast))
|
||||
{
|
||||
CMenu subMenu;
|
||||
// CMenuDestroyer menuDestroyer_CRC;
|
||||
@@ -793,40 +800,58 @@ STDMETHODIMP CZipContextMenu::QueryContextMenu(HMENU hMenu, UINT indexMenu,
|
||||
if (subMenu.CreatePopup())
|
||||
{
|
||||
// menuDestroyer_CRC.Attach(subMenu);
|
||||
CMenuItem mi;
|
||||
mi.fType = MFT_STRING;
|
||||
mi.fMask = MIIM_SUBMENU | MIIM_TYPE | MIIM_ID;
|
||||
if (bitmap)
|
||||
mi.fMask |= MIIM_CHECKMARKS;
|
||||
mi.wID = currentCommandID++;
|
||||
mi.hSubMenu = subMenu;
|
||||
mi.StringValue = "CRC SHA";
|
||||
mi.hbmpUnchecked = bitmap;
|
||||
|
||||
CMenu menu;
|
||||
menu.Attach(hMenu);
|
||||
// menuDestroyer_CRC.Disable();
|
||||
menu.InsertItem(indexMenu++, true, mi);
|
||||
|
||||
AddMapItem_ForSubMenu(kCheckSumCascadedVerb);
|
||||
MyAddSubMenu(_commandMap, kCheckSumCascadedVerb, menu, indexMenu++, currentCommandID++, (UString)"CRC SHA", subMenu, bitmap);
|
||||
|
||||
for (unsigned i = 0; i < ARRAY_SIZE(g_HashCommands); i++)
|
||||
{
|
||||
if (currentCommandID >= commandIDLast)
|
||||
break;
|
||||
const CHashCommand &hc = g_HashCommands[i];
|
||||
CCommandMapItem commandMapItem;
|
||||
commandMapItem.CommandInternalID = hc.CommandInternalID;
|
||||
commandMapItem.Verb = kCheckSumCascadedVerb;
|
||||
commandMapItem.Verb += hc.MethodName;
|
||||
// commandMapItem.HelpString = hc.Name;
|
||||
CCommandMapItem cmi;
|
||||
cmi.CommandInternalID = hc.CommandInternalID;
|
||||
cmi.Verb = kCheckSumCascadedVerb;
|
||||
cmi.Verb += '.';
|
||||
cmi.Verb += hc.MethodName;
|
||||
// cmi.HelpString = cmi.Verb;
|
||||
_commandMap.Add(cmi);
|
||||
MyInsertMenu(subMenu, subIndex_CRC++, currentCommandID++, (UString)hc.UserName, bitmap);
|
||||
_commandMap.Add(commandMapItem);
|
||||
}
|
||||
|
||||
subMenu.Detach();
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
{ char s[256]; sprintf(s, "Commands=%d currentCommandID - commandIDFirst = %d",
|
||||
_commandMap.Size(), currentCommandID - commandIDFirst); OutputDebugStringA(s); }
|
||||
#endif
|
||||
|
||||
if (_commandMap.Size() != currentCommandID - commandIDFirst)
|
||||
throw 20190818;
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, currentCommandID - commandIDFirst);
|
||||
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
/* we added some menu items already : num_added_menu_items,
|
||||
So we MUST return (number_of_defined_ids), where (number_of_defined_ids >= num_added_menu_items)
|
||||
This will prevent incorrect menu working, when same IDs can be
|
||||
assigned in multiple menu items from different subhandlers.
|
||||
And we must add items to _commandMap before adding to menu.
|
||||
*/
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
{ char s[256]; sprintf(s, "catch() exception: Commands=%d",
|
||||
_commandMap.Size()); OutputDebugStringA(s); }
|
||||
#endif
|
||||
// if (_commandMap.Size() != 0)
|
||||
return MAKE_HRESULT(SEVERITY_SUCCESS, 0, _commandMap.Size());
|
||||
// throw;
|
||||
}
|
||||
COM_TRY_END
|
||||
}
|
||||
|
||||
|
||||
@@ -843,35 +868,122 @@ static UString Get7zFmPath()
|
||||
return fs2us(NWindows::NDLL::GetModuleDirPrefix()) + L"7zFM.exe";
|
||||
}
|
||||
|
||||
|
||||
#ifdef UNDER_CE
|
||||
#define MY__IS_INTRESOURCE(_r) ((((ULONG_PTR)(_r)) >> 16) == 0)
|
||||
#else
|
||||
#define MY__IS_INTRESOURCE(_r) IS_INTRESOURCE(_r)
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
static void PrintStringA(const char *name, LPCSTR ptr)
|
||||
{
|
||||
AString m;
|
||||
m += name;
|
||||
m += ": ";
|
||||
char s[32];
|
||||
sprintf(s, "%p", ptr);
|
||||
m += s;
|
||||
if (!MY__IS_INTRESOURCE(ptr))
|
||||
{
|
||||
m += ": \"";
|
||||
m += ptr;
|
||||
m += "\"";
|
||||
}
|
||||
OutputDebugStringA(m);
|
||||
}
|
||||
|
||||
#if !defined(UNDER_CE)
|
||||
static void PrintStringW(const char *name, LPCWSTR ptr)
|
||||
{
|
||||
UString m;
|
||||
m += name;
|
||||
m += ": ";
|
||||
char s[32];
|
||||
sprintf(s, "%p", ptr);
|
||||
m += s;
|
||||
if (!MY__IS_INTRESOURCE(ptr))
|
||||
{
|
||||
m += ": \"";
|
||||
m += ptr;
|
||||
m += "\"";
|
||||
}
|
||||
OutputDebugStringW(m);
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
||||
STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
{
|
||||
// ::OutputDebugStringA("1");
|
||||
int commandOffset;
|
||||
COM_TRY_BEGIN
|
||||
|
||||
// It's fix for bug: crashing in XP. See example in MSDN: "Creating Context Menu Handlers".
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
|
||||
#if !defined(UNDER_CE) && defined(_MSC_VER)
|
||||
{ char s[1280]; sprintf(s,
|
||||
#ifdef _WIN64
|
||||
"64"
|
||||
#else
|
||||
"32"
|
||||
#endif
|
||||
": InvokeCommand: cbSize=%d flags=%x "
|
||||
, commandInfo->cbSize, commandInfo->fMask); OutputDebugStringA(s); }
|
||||
|
||||
PrintStringA("Verb", commandInfo->lpVerb);
|
||||
PrintStringA("Parameters", commandInfo->lpParameters);
|
||||
PrintStringA("Directory", commandInfo->lpDirectory);
|
||||
#endif
|
||||
|
||||
int commandOffset = -1;
|
||||
|
||||
// xp64 / Win10 : explorer.exe sends 0 in lpVerbW
|
||||
// MSDN: if (IS_INTRESOURCE(lpVerbW)), we must use LOWORD(lpVerb) as sommand offset
|
||||
|
||||
// FIXME: MINGW doesn't define CMINVOKECOMMANDINFOEX
|
||||
#if !defined(UNDER_CE) /* && defined(_MSC_VER) */
|
||||
bool unicodeVerb = false;
|
||||
if (commandInfo->cbSize == sizeof(CMINVOKECOMMANDINFOEX) &&
|
||||
(commandInfo->fMask & CMIC_MASK_UNICODE) != 0)
|
||||
{
|
||||
LPCMINVOKECOMMANDINFOEX commandInfoEx = (LPCMINVOKECOMMANDINFOEX)commandInfo;
|
||||
if (HIWORD(commandInfoEx->lpVerbW) == 0)
|
||||
commandOffset = LOWORD(commandInfo->lpVerb);
|
||||
else
|
||||
if (!MY__IS_INTRESOURCE(commandInfoEx->lpVerbW))
|
||||
{
|
||||
unicodeVerb = true;
|
||||
commandOffset = FindVerb(commandInfoEx->lpVerbW);
|
||||
}
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
PrintStringW("VerbW", commandInfoEx->lpVerbW);
|
||||
PrintStringW("ParametersW", commandInfoEx->lpParametersW);
|
||||
PrintStringW("DirectoryW", commandInfoEx->lpDirectoryW);
|
||||
PrintStringW("TitleW", commandInfoEx->lpTitleW);
|
||||
PrintStringA("Title", commandInfoEx->lpTitle);
|
||||
#endif
|
||||
}
|
||||
else
|
||||
if (!unicodeVerb)
|
||||
#endif
|
||||
if (HIWORD(commandInfo->lpVerb) == 0)
|
||||
{
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
OutputDebugStringA("use non-UNICODE verb");
|
||||
#endif
|
||||
// if (HIWORD(commandInfo->lpVerb) == 0)
|
||||
if (MY__IS_INTRESOURCE(commandInfo->lpVerb))
|
||||
commandOffset = LOWORD(commandInfo->lpVerb);
|
||||
else
|
||||
commandOffset = FindVerb(GetUnicodeString(commandInfo->lpVerb));
|
||||
}
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
{ char s[128]; sprintf(s, "commandOffset=%d",
|
||||
commandOffset); OutputDebugStringA(s); }
|
||||
#endif
|
||||
|
||||
if (commandOffset < 0 || (unsigned)commandOffset >= _commandMap.Size())
|
||||
return E_FAIL;
|
||||
return E_INVALIDARG;
|
||||
|
||||
const CCommandMapItem commandMapItem = _commandMap[commandOffset];
|
||||
ECommandInternalID cmdID = commandMapItem.CommandInternalID;
|
||||
const CCommandMapItem &cmi = _commandMap[(unsigned)commandOffset];
|
||||
ECommandInternalID cmdID = cmi.CommandInternalID;
|
||||
|
||||
try
|
||||
{
|
||||
@@ -881,10 +993,10 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
{
|
||||
UString params;
|
||||
params = GetQuotedString(_fileNames[0]);
|
||||
if (!commandMapItem.ArcType.IsEmpty())
|
||||
if (!cmi.ArcType.IsEmpty())
|
||||
{
|
||||
params += " -t";
|
||||
params += commandMapItem.ArcType;
|
||||
params += cmi.ArcType;
|
||||
}
|
||||
MyCreateProcess(Get7zFmPath(), params);
|
||||
break;
|
||||
@@ -893,7 +1005,7 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
case kExtractHere:
|
||||
case kExtractTo:
|
||||
{
|
||||
ExtractArchives(_fileNames, commandMapItem.Folder,
|
||||
ExtractArchives(_fileNames, cmi.Folder,
|
||||
(cmdID == kExtract), // showDialog
|
||||
(cmdID == kExtractTo) && _elimDup.Val // elimDup
|
||||
);
|
||||
@@ -919,8 +1031,8 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
(cmdID == kCompress) ||
|
||||
(cmdID == kCompressEmail);
|
||||
bool addExtension = (cmdID == kCompress || cmdID == kCompressEmail);
|
||||
CompressFiles(commandMapItem.Folder,
|
||||
commandMapItem.ArcName, commandMapItem.ArcType,
|
||||
CompressFiles(cmi.Folder,
|
||||
cmi.ArcName, cmi.ArcType,
|
||||
addExtension,
|
||||
_fileNames, email, showDialog, false);
|
||||
break;
|
||||
@@ -943,6 +1055,8 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
}
|
||||
break;
|
||||
}
|
||||
case kCommandNULL:
|
||||
break;
|
||||
}
|
||||
}
|
||||
catch(...)
|
||||
@@ -950,66 +1064,75 @@ STDMETHODIMP CZipContextMenu::InvokeCommand(LPCMINVOKECOMMANDINFO commandInfo)
|
||||
::MessageBoxW(0, L"Error", L"7-Zip", MB_ICONERROR);
|
||||
}
|
||||
return S_OK;
|
||||
COM_TRY_END
|
||||
}
|
||||
|
||||
static void MyCopyString(void *dest, const wchar_t *src, bool writeInUnicode)
|
||||
|
||||
|
||||
static void MyCopyString(void *dest, const UString &src, bool writeInUnicode, UINT size)
|
||||
{
|
||||
if (size != 0)
|
||||
size--;
|
||||
if (writeInUnicode)
|
||||
{
|
||||
MyStringCopy((wchar_t *)dest, src);
|
||||
UString s = src;
|
||||
s.DeleteFrom(size);
|
||||
MyStringCopy((wchar_t *)dest, s);
|
||||
}
|
||||
else
|
||||
MyStringCopy((char *)dest, (const char *)GetAnsiString(src));
|
||||
{
|
||||
AString s = GetAnsiString(src);
|
||||
s.DeleteFrom(size);
|
||||
MyStringCopy((char *)dest, s);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
STDMETHODIMP CZipContextMenu::GetCommandString(UINT_PTR commandOffset, UINT uType,
|
||||
UINT * /* pwReserved */ , LPSTR pszName, UINT /* cchMax */)
|
||||
UINT * /* pwReserved */ , LPSTR pszName, UINT cchMax)
|
||||
{
|
||||
int cmdOffset = (int)commandOffset;
|
||||
switch (uType)
|
||||
COM_TRY_BEGIN
|
||||
|
||||
const int cmdOffset = (int)commandOffset;
|
||||
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
{ char s[256]; sprintf(s, "GetCommandString: cmdOffset=%d uType=%d cchMax = %d",
|
||||
cmdOffset, uType, cchMax); OutputDebugStringA(s); }
|
||||
#endif
|
||||
|
||||
if (uType == GCS_VALIDATEA || uType == GCS_VALIDATEW)
|
||||
{
|
||||
#ifdef UNDER_CE
|
||||
case GCS_VALIDATE:
|
||||
#else
|
||||
case GCS_VALIDATEA:
|
||||
case GCS_VALIDATEW:
|
||||
#endif
|
||||
if (cmdOffset < 0 || (unsigned)cmdOffset >= _commandMap.Size())
|
||||
return S_FALSE;
|
||||
else
|
||||
return S_OK;
|
||||
if (cmdOffset < 0 || (unsigned)cmdOffset >= _commandMap.Size())
|
||||
return S_FALSE;
|
||||
else
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
if (cmdOffset < 0 || (unsigned)cmdOffset >= _commandMap.Size())
|
||||
return E_FAIL;
|
||||
#ifdef UNDER_CE
|
||||
if (uType == GCS_HELPTEXT)
|
||||
#else
|
||||
{
|
||||
#ifdef SHOW_DEBUG_CTX_MENU
|
||||
OutputDebugStringA("---------------- cmdOffset: E_INVALIDARG");
|
||||
#endif
|
||||
return E_INVALIDARG;
|
||||
}
|
||||
|
||||
const CCommandMapItem &cmi = _commandMap[(unsigned)cmdOffset];
|
||||
|
||||
if (uType == GCS_HELPTEXTA || uType == GCS_HELPTEXTW)
|
||||
#endif
|
||||
{
|
||||
MyCopyString(pszName, _commandMap[cmdOffset].HelpString,
|
||||
#ifdef UNDER_CE
|
||||
true
|
||||
#else
|
||||
uType == GCS_HELPTEXTW
|
||||
#endif
|
||||
);
|
||||
return NO_ERROR;
|
||||
// we can return "Verb" here for debug purposes.
|
||||
// HelpString;
|
||||
MyCopyString(pszName, cmi.Verb, uType == GCS_HELPTEXTW, cchMax);
|
||||
return S_OK;
|
||||
}
|
||||
#ifdef UNDER_CE
|
||||
if (uType == GCS_VERB)
|
||||
#else
|
||||
|
||||
if (uType == GCS_VERBA || uType == GCS_VERBW)
|
||||
#endif
|
||||
{
|
||||
MyCopyString(pszName, _commandMap[cmdOffset].Verb,
|
||||
#ifdef UNDER_CE
|
||||
true
|
||||
#else
|
||||
uType == GCS_VERBW
|
||||
#endif
|
||||
);
|
||||
return NO_ERROR;
|
||||
MyCopyString(pszName, cmi.Verb, uType == GCS_VERBW, cchMax);
|
||||
return S_OK;
|
||||
}
|
||||
return E_FAIL;
|
||||
|
||||
return E_INVALIDARG;
|
||||
|
||||
COM_TRY_END
|
||||
}
|
||||
|
||||
@@ -54,18 +54,18 @@ public:
|
||||
CZipContextMenu();
|
||||
~CZipContextMenu();
|
||||
|
||||
private:
|
||||
|
||||
struct CCommandMapItem
|
||||
{
|
||||
ECommandInternalID CommandInternalID;
|
||||
UString Verb;
|
||||
UString HelpString;
|
||||
// UString HelpString;
|
||||
UString Folder;
|
||||
UString ArcName;
|
||||
UString ArcType;
|
||||
};
|
||||
|
||||
private:
|
||||
|
||||
bool _isMenuForFM;
|
||||
UStringVector _fileNames;
|
||||
bool _dropMode;
|
||||
@@ -78,7 +78,8 @@ private:
|
||||
|
||||
HRESULT GetFileNames(LPDATAOBJECT dataObject, UStringVector &fileNames);
|
||||
int FindVerb(const UString &verb);
|
||||
bool FillCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &commandMapItem);
|
||||
void FillCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &cmi);
|
||||
void AddCommand(ECommandInternalID id, UString &mainString, CCommandMapItem &cmi);
|
||||
void AddMapItem_ForSubMenu(const char *ver);
|
||||
};
|
||||
|
||||
|
||||
@@ -39,9 +39,16 @@ DEFINE_GUID(CLSID_CZipContextMenu,
|
||||
|
||||
using namespace NWindows;
|
||||
|
||||
extern
|
||||
HINSTANCE g_hInstance;
|
||||
HINSTANCE g_hInstance = 0;
|
||||
|
||||
extern
|
||||
HWND g_HWND;
|
||||
HWND g_HWND = 0;
|
||||
|
||||
extern
|
||||
LONG g_DllRefCount;
|
||||
LONG g_DllRefCount = 0; // Reference count of this DLL.
|
||||
|
||||
|
||||
@@ -91,7 +98,18 @@ STDMETHODIMP CShellExtClassFactory::LockServer(BOOL /* fLock */)
|
||||
}
|
||||
|
||||
|
||||
#if defined(_UNICODE) && !defined(_WIN64) && !defined(UNDER_CE)
|
||||
#define NT_CHECK_FAIL_ACTION return FALSE;
|
||||
#endif
|
||||
|
||||
extern "C"
|
||||
BOOL WINAPI DllMain(
|
||||
#ifdef UNDER_CE
|
||||
HANDLE hInstance
|
||||
#else
|
||||
HINSTANCE hInstance
|
||||
#endif
|
||||
, DWORD dwReason, LPVOID);
|
||||
|
||||
extern "C"
|
||||
BOOL WINAPI DllMain(
|
||||
|
||||
@@ -26,7 +26,7 @@ void ShowErrorMessageRes(UINT resID)
|
||||
ShowErrorMessageHwndRes(0, resID);
|
||||
}
|
||||
|
||||
void ShowErrorMessageDWORD(HWND window, DWORD errorCode)
|
||||
static void ShowErrorMessageDWORD(HWND window, DWORD errorCode)
|
||||
{
|
||||
ShowErrorMessage(window, NError::MyFormatMessage(errorCode));
|
||||
}
|
||||
|
||||
@@ -59,14 +59,16 @@ static const bool k_shellex_Statuses[2][4] =
|
||||
#else
|
||||
*/
|
||||
|
||||
typedef WINADVAPI LONG (APIENTRY *Func_RegDeleteKeyExW)(HKEY hKey, LPCWSTR lpSubKey, REGSAM samDesired, DWORD Reserved);
|
||||
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");
|
||||
(void *)GetProcAddress(GetModuleHandleW(L"advapi32.dll"), "RegDeleteKeyExW");
|
||||
}
|
||||
|
||||
#define INIT_REG_WOW if (wow != 0) Init_RegDeleteKeyExW();
|
||||
@@ -80,12 +82,12 @@ static LONG MyRegistry_DeleteKey(HKEY parentKey, LPCTSTR name, UInt32 wow)
|
||||
|
||||
/*
|
||||
#ifdef _WIN64
|
||||
return RegDeleteKeyExW
|
||||
return RegDeleteKeyExW
|
||||
#else
|
||||
*/
|
||||
if (!func_RegDeleteKeyExW)
|
||||
return E_NOTIMPL;
|
||||
return func_RegDeleteKeyExW
|
||||
if (!func_RegDeleteKeyExW)
|
||||
return E_NOTIMPL;
|
||||
return func_RegDeleteKeyExW
|
||||
// #endif
|
||||
(parentKey, GetUnicodeString(name), wow, 0);
|
||||
}
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
// StdAfx.cpp
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "StdAfx.h"
|
||||
|
||||
@@ -167,6 +167,7 @@ STDMETHODIMP CExtractCallbackImp::MessageError(const wchar_t *message)
|
||||
return CheckBreak2();
|
||||
}
|
||||
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, AString &s);
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, AString &s)
|
||||
{
|
||||
s.Empty();
|
||||
|
||||
@@ -3,6 +3,10 @@
|
||||
|
||||
#include "StdAfx.h"
|
||||
|
||||
#ifdef __clang__
|
||||
#pragma clang diagnostic ignored "-Wmissing-prototypes"
|
||||
#endif
|
||||
|
||||
#include "../../../Common/MyWindows.h"
|
||||
|
||||
#include "../../../Common/MyInitGuid.h"
|
||||
@@ -39,7 +43,9 @@ const char *g_PluginName_for_Error = "7-Zip";
|
||||
|
||||
}
|
||||
|
||||
#if defined(_UNICODE) && !defined(_WIN64) && !defined(UNDER_CE)
|
||||
#define NT_CHECK_FAIL_ACTION return FALSE;
|
||||
#endif
|
||||
|
||||
BOOL WINAPI DllMain(
|
||||
#ifdef UNDER_CE
|
||||
|
||||
@@ -53,7 +53,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"C:\Program Files\Far\Plugins\7-Zip\7-ZipFar.dll" /opt:NOWIN98
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"C:\Progs\Far\Plugins\7-Zip\7-ZipFar.dll" /opt:NOWIN98
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "Far - Win32 Debug"
|
||||
@@ -80,7 +80,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"C:\Program Files\Far\Plugins\7-Zip\7-ZipFar.dll" /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"C:\Progs\Far\Plugins\7-Zip\7-ZipFar.dll" /pdbtype:sept
|
||||
|
||||
!ENDIF
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@ struct CFileInfoStrings
|
||||
AString Time;
|
||||
};
|
||||
|
||||
void SetFileInfoStrings(const CFileInfo &fileInfo,
|
||||
static void SetFileInfoStrings(const CFileInfo &fileInfo,
|
||||
CFileInfoStrings &fileInfoStrings)
|
||||
{
|
||||
char buffer[256];
|
||||
|
||||
@@ -197,10 +197,12 @@ void CPlugin::EnterToDirectory(const UString &dirName)
|
||||
s = "..";
|
||||
_folder->BindToFolder(s, &newFolder);
|
||||
if (!newFolder)
|
||||
{
|
||||
if (dirName.IsEmpty())
|
||||
return;
|
||||
else
|
||||
throw 40325;
|
||||
}
|
||||
_folder = newFolder;
|
||||
}
|
||||
|
||||
@@ -457,7 +459,7 @@ static AString PropToString2(const NCOM::CPropVariant &prop, PROPID propID)
|
||||
return s;
|
||||
}
|
||||
|
||||
static void AddPropertyString(InfoPanelLine *lines, int &numItems, PROPID propID, const wchar_t *name,
|
||||
static void AddPropertyString(InfoPanelLine *lines, unsigned &numItems, PROPID propID, const wchar_t *name,
|
||||
const NCOM::CPropVariant &prop)
|
||||
{
|
||||
if (prop.vt != VT_EMPTY)
|
||||
@@ -472,7 +474,7 @@ static void AddPropertyString(InfoPanelLine *lines, int &numItems, PROPID propID
|
||||
}
|
||||
}
|
||||
|
||||
static void InsertSeparator(InfoPanelLine *lines, int &numItems)
|
||||
static void InsertSeparator(InfoPanelLine *lines, unsigned &numItems)
|
||||
{
|
||||
if (numItems < kNumInfoLinesMax)
|
||||
{
|
||||
@@ -528,7 +530,7 @@ void CPlugin::GetOpenPluginInfo(struct OpenPluginInfo *info)
|
||||
MyStringCopy(m_InfoLines[1].Text, g_StartupInfo.GetMsgString(NMessageID::kArchiveType));
|
||||
MyStringCopy(m_InfoLines[1].Data, (const char *)UnicodeStringToMultiByte(_archiveTypeName, CP_OEMCP));
|
||||
|
||||
int numItems = 2;
|
||||
unsigned numItems = 2;
|
||||
|
||||
{
|
||||
CMyComPtr<IFolderProperties> folderProperties;
|
||||
|
||||
@@ -4,6 +4,9 @@
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "../../../Common/StringConvert.h"
|
||||
#include "FarUtils.h"
|
||||
|
||||
#include "Messages.h"
|
||||
#include "Plugin.h"
|
||||
#include "UpdateCallbackFar.h"
|
||||
@@ -28,16 +31,37 @@ int CPlugin::DeleteFiles(PluginPanelItem *panelItems, int numItems, int opMode)
|
||||
g_StartupInfo.GetMsgString(NMessageID::kDeleteDelete),
|
||||
g_StartupInfo.GetMsgString(NMessageID::kDeleteCancel)
|
||||
};
|
||||
char msg[1024];
|
||||
|
||||
// char msg[1024];
|
||||
AString str1;
|
||||
|
||||
if (numItems == 1)
|
||||
{
|
||||
sprintf(msg, g_StartupInfo.GetMsgString(NMessageID::kDeleteFile), panelItems[0].FindData.cFileName);
|
||||
msgItems[1] = msg;
|
||||
str1 = g_StartupInfo.GetMsgString(NMessageID::kDeleteFile);
|
||||
AString name (panelItems[0].FindData.cFileName);
|
||||
const unsigned kSizeLimit = 48;
|
||||
if (name.Len() > kSizeLimit)
|
||||
{
|
||||
UString s = MultiByteToUnicodeString(name, CP_OEMCP);
|
||||
ReduceString(s, kSizeLimit);
|
||||
name = UnicodeStringToMultiByte(s, CP_OEMCP);
|
||||
}
|
||||
str1.Replace(AString ("%.40s"), name);
|
||||
msgItems[1] = str1;
|
||||
// sprintf(msg, g_StartupInfo.GetMsgString(NMessageID::kDeleteFile), panelItems[0].FindData.cFileName);
|
||||
// msgItems[2] = msg;
|
||||
}
|
||||
else if (numItems > 1)
|
||||
{
|
||||
sprintf(msg, g_StartupInfo.GetMsgString(NMessageID::kDeleteNumberOfFiles), numItems);
|
||||
msgItems[1] = msg;
|
||||
str1 = g_StartupInfo.GetMsgString(NMessageID::kDeleteNumberOfFiles);
|
||||
{
|
||||
AString n;
|
||||
n.Add_UInt32(numItems);
|
||||
str1.Replace(AString ("%d"), n);
|
||||
}
|
||||
msgItems[1] = str1;
|
||||
// sprintf(msg, g_StartupInfo.GetMsgString(NMessageID::kDeleteNumberOfFiles), numItems);
|
||||
// msgItems[1] = msg;
|
||||
}
|
||||
if (g_StartupInfo.ShowMessage(FMSG_WARNING, NULL, msgItems, ARRAY_SIZE(msgItems), 2) != 0)
|
||||
return (FALSE);
|
||||
|
||||
@@ -89,7 +89,7 @@ NFileOperationReturnCode::EEnum CPlugin::PutFiles(
|
||||
}
|
||||
*/
|
||||
|
||||
if (numItems == 0)
|
||||
if (numItems <= 0)
|
||||
return NFileOperationReturnCode::kError;
|
||||
|
||||
if (_agent->IsThereReadOnlyArc())
|
||||
@@ -104,14 +104,18 @@ NFileOperationReturnCode::EEnum CPlugin::PutFiles(
|
||||
NCompression::CInfo compressionInfo;
|
||||
compressionInfo.Load();
|
||||
|
||||
int methodIndex = 0;
|
||||
int i;
|
||||
for (i = ARRAY_SIZE(g_MethodMap) - 1; i >= 0; i--)
|
||||
unsigned methodIndex = 0;
|
||||
|
||||
unsigned i;
|
||||
for (i = ARRAY_SIZE(g_MethodMap); i != 0;)
|
||||
{
|
||||
i--;
|
||||
if (compressionInfo.Level >= g_MethodMap[i])
|
||||
{
|
||||
methodIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
const int kMethodRadioIndex = 2;
|
||||
const int kModeRadioIndex = kMethodRadioIndex + 7;
|
||||
@@ -200,10 +204,10 @@ NFileOperationReturnCode::EEnum CPlugin::PutFiles(
|
||||
|
||||
UStringVector fileNames;
|
||||
fileNames.ClearAndReserve(numItems);
|
||||
for (i = 0; i < numItems; i++)
|
||||
for (i = 0; i < (unsigned)numItems; i++)
|
||||
fileNames.AddInReserved(MultiByteToUnicodeString(panelItems[i].FindData.cFileName, CP_OEMCP));
|
||||
CObjArray<const wchar_t *> fileNamePointers(numItems);
|
||||
for (i = 0; i < numItems; i++)
|
||||
for (i = 0; i < (unsigned)numItems; i++)
|
||||
fileNamePointers[i] = fileNames[i];
|
||||
|
||||
CMyComPtr<IOutFolderArchive> outArchive;
|
||||
@@ -459,29 +463,36 @@ HRESULT CompressFiles(const CObjectVector<PluginPanelItem> &pluginPanelItems)
|
||||
const int kMethodRadioIndex = kArchiveNameIndex + 2;
|
||||
const int kModeRadioIndex = kMethodRadioIndex + 7;
|
||||
|
||||
|
||||
char updateAddToArchiveString[512];
|
||||
// char updateAddToArchiveString[512];
|
||||
AString str1;
|
||||
{
|
||||
const CArcInfoEx &arcInfo = codecs->Formats[archiverIndex];
|
||||
const AString s (UnicodeStringToMultiByte(arcInfo.Name, CP_OEMCP));
|
||||
str1 = g_StartupInfo.GetMsgString(NMessageID::kUpdateAddToArchive);
|
||||
str1.Replace(AString ("%s"), s);
|
||||
/*
|
||||
sprintf(updateAddToArchiveString,
|
||||
g_StartupInfo.GetMsgString(NMessageID::kUpdateAddToArchive), (const char *)s);
|
||||
*/
|
||||
}
|
||||
|
||||
int methodIndex = 0;
|
||||
int i;
|
||||
for (i = ARRAY_SIZE(g_MethodMap) - 1; i >= 0; i--)
|
||||
unsigned methodIndex = 0;
|
||||
unsigned i;
|
||||
for (i = ARRAY_SIZE(g_MethodMap); i != 0;)
|
||||
{
|
||||
i--;
|
||||
if (compressionInfo.Level >= g_MethodMap[i])
|
||||
{
|
||||
methodIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
const struct CInitDialogItem initItems[]=
|
||||
{
|
||||
{ DI_DOUBLEBOX, 3, 1, 72, kYSize - 2, false, false, 0, false, NMessageID::kUpdateTitle, NULL, NULL },
|
||||
|
||||
{ DI_TEXT, 5, 2, 0, 0, false, false, 0, false, -1, updateAddToArchiveString, NULL },
|
||||
{ DI_TEXT, 5, 2, 0, 0, false, false, 0, false, -1, str1, NULL },
|
||||
|
||||
{ DI_EDIT, 5, 3, 70, 3, true, false, DIF_HISTORY, false, -1, archiveNameA, kArchiveHistoryKeyName},
|
||||
// { DI_EDIT, 5, 3, 70, 3, true, false, 0, false, -1, arcName, NULL},
|
||||
|
||||
@@ -20,7 +20,6 @@ CURRENT_OBJS = \
|
||||
$O\PluginWrite.obj \
|
||||
$O\ProgressBox.obj \
|
||||
$O\UpdateCallbackFar.obj \
|
||||
$O\UTFConvert.obj \
|
||||
|
||||
COMMON_OBJS = \
|
||||
$O\IntToString.obj \
|
||||
@@ -29,6 +28,7 @@ COMMON_OBJS = \
|
||||
$O\StringConvert.obj \
|
||||
$O\StringToInt.obj \
|
||||
$O\MyVector.obj \
|
||||
$O\UTFConvert.obj \
|
||||
$O\Wildcard.obj \
|
||||
|
||||
WIN_OBJS = \
|
||||
|
||||
@@ -6,6 +6,8 @@
|
||||
|
||||
#include "../../MyVersion.h"
|
||||
|
||||
#include "../Common/LoadCodecs.h"
|
||||
|
||||
#include "AboutDialog.h"
|
||||
#include "PropertyNameRes.h"
|
||||
|
||||
@@ -23,8 +25,20 @@ static const UInt32 kLangIDs[] =
|
||||
#define LLL_(quote) L##quote
|
||||
#define LLL(quote) LLL_(quote)
|
||||
|
||||
extern CCodecs *g_CodecsObj;
|
||||
|
||||
bool CAboutDialog::OnInit()
|
||||
{
|
||||
#ifdef EXTERNAL_CODECS
|
||||
if (g_CodecsObj)
|
||||
{
|
||||
UString s;
|
||||
g_CodecsObj->GetCodecsErrorMessage(s);
|
||||
if (!s.IsEmpty())
|
||||
MessageBoxW(GetParent(), s, L"7-Zip", MB_ICONERROR);
|
||||
}
|
||||
#endif
|
||||
|
||||
LangSetDlgItems(*this, kLangIDs, ARRAY_SIZE(kLangIDs));
|
||||
SetItemText(IDT_ABOUT_VERSION, UString("7-Zip " MY_VERSION_CPU));
|
||||
SetItemText(IDT_ABOUT_DATE, LLL(MY_DATE));
|
||||
|
||||
@@ -18,7 +18,7 @@ CAPTION "About 7-Zip"
|
||||
{
|
||||
DEFPUSHBUTTON "OK", IDOK, bx1, by, bxs, bys
|
||||
PUSHBUTTON "www.7-zip.org", IDB_ABOUT_HOMEPAGE, bx2, by, bxs, bys
|
||||
ICON IDI_LOGO, -1, m, m, 32, 32, SS_REALSIZEIMAGE,
|
||||
ICON IDI_LOGO, -1, m, m, 32, 32, SS_REALSIZEIMAGE
|
||||
LTEXT "", IDT_ABOUT_VERSION, m, 54, xc, 8
|
||||
LTEXT "", IDT_ABOUT_DATE, m, 67, xc, 8
|
||||
LTEXT MY_COPYRIGHT, -1, m, 80, xc, 8
|
||||
|
||||
@@ -86,7 +86,7 @@ HRESULT CAltStreamsFolder::Init(const FString &path /* , IFolderFolder *parentFo
|
||||
{
|
||||
CFileInfo fi;
|
||||
if (!fi.Find(_pathBaseFile))
|
||||
return GetLastError();
|
||||
return GetLastError_noZero_HRESULT();
|
||||
}
|
||||
|
||||
unsigned prefixSize = GetFsParentPrefixSize(_pathBaseFile);
|
||||
@@ -612,7 +612,7 @@ static HRESULT CopyStream(
|
||||
FString destPath = destPathSpec;
|
||||
if (CompareFileNames(destPath, srcPath) == 0)
|
||||
{
|
||||
RINOK(SendMessageError(callback, "can not copy file onto itself", destPath));
|
||||
RINOK(SendMessageError(callback, "Cannot copy file onto itself", destPath));
|
||||
return E_ABORT;
|
||||
}
|
||||
|
||||
@@ -716,7 +716,7 @@ STDMETHODIMP CAltStreamsFolder::CopyTo(Int32 moveMode, const UInt32 *indices, UI
|
||||
if (destPath.IsEmpty() /* && !ExtractToStreamCallback */)
|
||||
return E_INVALIDARG;
|
||||
|
||||
bool isAltDest = NName::IsAltPathPrefix(destPath);;
|
||||
bool isAltDest = NName::IsAltPathPrefix(destPath);
|
||||
bool isDirectPath = (!isAltDest && !IsPathSepar(destPath.Back()));
|
||||
|
||||
if (isDirectPath)
|
||||
@@ -764,7 +764,7 @@ STDMETHODIMP CAltStreamsFolder::CopyFrom(Int32 /* moveMode */, const wchar_t * /
|
||||
|
||||
if (CompareFileNames(fromFolderPath, fs2us(_pathPrefix)) == 0)
|
||||
{
|
||||
RINOK(SendMessageError(callback, "can not copy file onto itself", _pathPrefix));
|
||||
RINOK(SendMessageError(callback, "Cannot copy file onto itself", _pathPrefix));
|
||||
return E_ABORT;
|
||||
}
|
||||
|
||||
|
||||
@@ -117,7 +117,7 @@ void CApp::SetListSettings()
|
||||
|
||||
HRESULT CApp::CreateOnePanel(int panelIndex, const UString &mainPath, const UString &arcFormat,
|
||||
bool needOpenArc,
|
||||
bool &archiveIsOpened, bool &encrypted)
|
||||
COpenResult &openRes)
|
||||
{
|
||||
if (Panels[panelIndex].PanelCreated)
|
||||
return S_OK;
|
||||
@@ -138,7 +138,7 @@ HRESULT CApp::CreateOnePanel(int panelIndex, const UString &mainPath, const UStr
|
||||
return Panels[panelIndex].Create(_window, _window,
|
||||
id, path, arcFormat, &m_PanelCallbackImp[panelIndex], &AppState,
|
||||
needOpenArc,
|
||||
archiveIsOpened, encrypted);
|
||||
openRes);
|
||||
}
|
||||
|
||||
|
||||
@@ -282,7 +282,7 @@ void CApp::SaveToolbarChanges()
|
||||
}
|
||||
|
||||
|
||||
HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcFormat, int xSizes[2], bool needOpenArc, bool &archiveIsOpened, bool &encrypted)
|
||||
HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcFormat, int xSizes[2], bool needOpenArc, COpenResult &openRes)
|
||||
{
|
||||
_window.Attach(hwnd);
|
||||
|
||||
@@ -334,21 +334,19 @@ HRESULT CApp::Create(HWND hwnd, const UString &mainPath, const UString &arcForma
|
||||
{
|
||||
if (NumPanels == 1)
|
||||
Panels[panelIndex]._xSize = xSizes[0] + xSizes[1];
|
||||
bool archiveIsOpened2 = false;
|
||||
bool encrypted2 = false;
|
||||
|
||||
COpenResult openRes2;
|
||||
UString path;
|
||||
if (isMainPanel)
|
||||
path = mainPath;
|
||||
|
||||
RINOK(CreateOnePanel(panelIndex, path, arcFormat,
|
||||
isMainPanel && needOpenArc,
|
||||
archiveIsOpened2, encrypted2));
|
||||
*(isMainPanel ? &openRes : &openRes2)));
|
||||
|
||||
if (isMainPanel)
|
||||
{
|
||||
archiveIsOpened = archiveIsOpened2;
|
||||
encrypted = encrypted2;
|
||||
if (needOpenArc && !archiveIsOpened2)
|
||||
if (needOpenArc && !openRes.ArchiveIsOpened)
|
||||
return S_OK;
|
||||
}
|
||||
}
|
||||
@@ -365,10 +363,10 @@ HRESULT CApp::SwitchOnOffOnePanel()
|
||||
if (NumPanels == 1)
|
||||
{
|
||||
NumPanels++;
|
||||
bool archiveIsOpened, encrypted;
|
||||
COpenResult openRes;
|
||||
RINOK(CreateOnePanel(1 - LastFocusedPanel, UString(), UString(),
|
||||
false, // needOpenArc
|
||||
archiveIsOpened, encrypted));
|
||||
openRes));
|
||||
Panels[1 - LastFocusedPanel].Enable(true);
|
||||
Panels[1 - LastFocusedPanel].Show(SW_SHOWNORMAL);
|
||||
}
|
||||
@@ -414,13 +412,13 @@ void CApp::Release()
|
||||
|
||||
// reduces path to part that exists on disk (or root prefix of path)
|
||||
// output path is normalized (with WCHAR_PATH_SEPARATOR)
|
||||
static void ReducePathToRealFileSystemPath(UString &path)
|
||||
static void Reduce_Path_To_RealFileSystemPath(UString &path)
|
||||
{
|
||||
unsigned prefixSize = GetRootPrefixSize(path);
|
||||
|
||||
while (!path.IsEmpty())
|
||||
{
|
||||
if (NFind::DoesDirExist(us2fs(path)))
|
||||
if (NFind::DoesDirExist_FollowLink(us2fs(path)))
|
||||
{
|
||||
NName::NormalizeDirPathPrefix(path);
|
||||
break;
|
||||
@@ -431,10 +429,10 @@ static void ReducePathToRealFileSystemPath(UString &path)
|
||||
path.Empty();
|
||||
break;
|
||||
}
|
||||
path.DeleteFrom(pos + 1);
|
||||
path.DeleteFrom((unsigned)(pos + 1));
|
||||
if ((unsigned)pos + 1 == prefixSize)
|
||||
break;
|
||||
path.DeleteFrom(pos);
|
||||
path.DeleteFrom((unsigned)pos);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -443,7 +441,7 @@ static void ReducePathToRealFileSystemPath(UString &path)
|
||||
static bool CheckFolderPath(const UString &path)
|
||||
{
|
||||
UString pathReduced = path;
|
||||
ReducePathToRealFileSystemPath(pathReduced);
|
||||
Reduce_Path_To_RealFileSystemPath(pathReduced);
|
||||
return (pathReduced == path);
|
||||
}
|
||||
*/
|
||||
@@ -463,6 +461,7 @@ static void AddValuePair1(UString &s, UINT resourceID, UInt64 size)
|
||||
s.Add_LF();
|
||||
}
|
||||
|
||||
void AddValuePair2(UString &s, UINT resourceID, UInt64 num, UInt64 size);
|
||||
void AddValuePair2(UString &s, UINT resourceID, UInt64 num, UInt64 size)
|
||||
{
|
||||
if (num == 0)
|
||||
@@ -601,7 +600,7 @@ void CApp::OnCopy(bool move, bool copyToSame, int srcPanelIndex)
|
||||
return;
|
||||
destPath = destPanel.GetFsPath();
|
||||
if (NumPanels == 1)
|
||||
ReducePathToRealFileSystemPath(destPath);
|
||||
Reduce_Path_To_RealFileSystemPath(destPath);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -660,7 +659,7 @@ void CApp::OnCopy(bool move, bool copyToSame, int srcPanelIndex)
|
||||
{
|
||||
if (NumPanels == 1 || CompareFileNames(destPath, srcPanel.GetFsPath()) == 0)
|
||||
{
|
||||
srcPanel.MessageBox_Error(L"Can not copy files onto itself");
|
||||
srcPanel.MessageBox_Error(L"Cannot copy files onto itself");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -882,9 +881,11 @@ void CApp::OnSetSubFolder(int srcPanelIndex)
|
||||
return;
|
||||
if (!newFolder)
|
||||
{
|
||||
const UString parentPrefix = srcPanel.GetParentDirPrefix();
|
||||
bool archiveIsOpened, encrypted;
|
||||
destPanel.BindToPath(parentPrefix, UString(), archiveIsOpened, encrypted);
|
||||
{
|
||||
const UString parentPrefix = srcPanel.GetParentDirPrefix();
|
||||
COpenResult openRes;
|
||||
destPanel.BindToPath(parentPrefix, UString(), openRes);
|
||||
}
|
||||
destPanel.RefreshListCtrl();
|
||||
return;
|
||||
}
|
||||
@@ -936,7 +937,7 @@ void CApp::OnNotify(int /* ctrlID */, LPNMHDR pnmh)
|
||||
g_ToolTipBuffer.Empty();
|
||||
SetButtonText((int)info->hdr.idFrom, g_ToolTipBuffer);
|
||||
g_ToolTipBufferSys = GetSystemString(g_ToolTipBuffer);
|
||||
info->lpszText = (LPTSTR)(LPCTSTR)g_ToolTipBufferSys;
|
||||
info->lpszText = g_ToolTipBufferSys.Ptr_non_const();
|
||||
return;
|
||||
}
|
||||
#ifndef _UNICODE
|
||||
@@ -946,7 +947,7 @@ void CApp::OnNotify(int /* ctrlID */, LPNMHDR pnmh)
|
||||
info->hinst = 0;
|
||||
g_ToolTipBuffer.Empty();
|
||||
SetButtonText((int)info->hdr.idFrom, g_ToolTipBuffer);
|
||||
info->lpszText = (LPWSTR)(LPCWSTR)g_ToolTipBuffer;
|
||||
info->lpszText = g_ToolTipBuffer.Ptr_non_const();
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
@@ -971,7 +972,7 @@ void CApp::RefreshTitlePanel(unsigned panelIndex, bool always)
|
||||
RefreshTitle(always);
|
||||
}
|
||||
|
||||
void AddUniqueStringToHead(UStringVector &list, const UString &s)
|
||||
static void AddUniqueStringToHead(UStringVector &list, const UString &s)
|
||||
{
|
||||
for (unsigned i = 0; i < list.Size();)
|
||||
if (s.IsEqualTo_NoCase(list[i]))
|
||||
|
||||
@@ -89,22 +89,24 @@ public:
|
||||
STDMETHOD(Drop)(IDataObject * dataObject, DWORD keyState, POINTL pt, DWORD *effect);
|
||||
|
||||
CDropTarget():
|
||||
TargetPanelIndex(-1),
|
||||
SrcPanelIndex(-1),
|
||||
m_IsAppTarget(false),
|
||||
m_Panel(0),
|
||||
App(0),
|
||||
m_PanelDropIsAllowed(false),
|
||||
m_DropIsAllowed(false),
|
||||
m_SelectionIndex(-1),
|
||||
m_DropIsAllowed(false),
|
||||
m_PanelDropIsAllowed(false),
|
||||
m_SubFolderIndex(-1),
|
||||
m_SetPathIsOK(false) {}
|
||||
m_Panel(NULL),
|
||||
m_IsAppTarget(false),
|
||||
m_SetPathIsOK(false),
|
||||
App(NULL),
|
||||
SrcPanelIndex(-1),
|
||||
TargetPanelIndex(-1)
|
||||
{}
|
||||
|
||||
CApp *App;
|
||||
int SrcPanelIndex; // index of D&D source_panel
|
||||
int TargetPanelIndex; // what panel to use as target_panel of Application
|
||||
};
|
||||
|
||||
|
||||
class CApp
|
||||
{
|
||||
public:
|
||||
@@ -173,8 +175,8 @@ public:
|
||||
void OnSetSameFolder(int srcPanelIndex);
|
||||
void OnSetSubFolder(int srcPanelIndex);
|
||||
|
||||
HRESULT CreateOnePanel(int panelIndex, const UString &mainPath, const UString &arcFormat, bool needOpenArc, bool &archiveIsOpened, bool &encrypted);
|
||||
HRESULT Create(HWND hwnd, const UString &mainPath, const UString &arcFormat, int xSizes[2], bool needOpenArc, bool &archiveIsOpened, bool &encrypted);
|
||||
HRESULT CreateOnePanel(int panelIndex, const UString &mainPath, const UString &arcFormat, bool needOpenArc, COpenResult &openRes);
|
||||
HRESULT Create(HWND hwnd, const UString &mainPath, const UString &arcFormat, int xSizes[2], bool needOpenArc, COpenResult &openRes);
|
||||
void Read();
|
||||
void Save();
|
||||
void Release();
|
||||
@@ -196,7 +198,12 @@ public:
|
||||
void Delete(bool toRecycleBin) { GetFocusedPanel().DeleteItems(toRecycleBin); }
|
||||
HRESULT CalculateCrc2(const UString &methodName);
|
||||
void CalculateCrc(const char *methodName);
|
||||
|
||||
void DiffFiles(const UString &path1, const UString &path2);
|
||||
void DiffFiles();
|
||||
|
||||
void VerCtrl(unsigned id);
|
||||
|
||||
void Split();
|
||||
void Combine();
|
||||
void Properties() { GetFocusedPanel().Properties(); }
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
#include "../../../Common/MyWindows.h"
|
||||
|
||||
#include <commctrl.h>
|
||||
#include <CommCtrl.h>
|
||||
|
||||
#ifndef UNDER_CE
|
||||
#include "../../../Windows/CommonDialog.h"
|
||||
@@ -139,7 +139,7 @@ public:
|
||||
UStringVector Filters;
|
||||
UString FilterDescription;
|
||||
|
||||
CBrowseDialog(): FolderMode(false), _showDots(false), ShowAllFiles(true) {}
|
||||
CBrowseDialog(): _showDots(false), FolderMode(false), ShowAllFiles(true) {}
|
||||
void SetFilter(const UString &s);
|
||||
INT_PTR Create(HWND parent = 0) { return CModalDialog::Create(IDD_BROWSE, parent); }
|
||||
int CompareItems(LPARAM lParam1, LPARAM lParam2);
|
||||
@@ -235,7 +235,7 @@ bool CBrowseDialog::OnInit()
|
||||
column.fmt = LVCFMT_RIGHT;
|
||||
column.cx = 100;
|
||||
const UString s = LangString(IDS_PROP_SIZE);
|
||||
column.pszText = (wchar_t *)(const wchar_t *)s;
|
||||
column.pszText = s.Ptr_non_const();
|
||||
_list.InsertColumn(2, &column);
|
||||
}
|
||||
|
||||
@@ -476,7 +476,7 @@ bool CBrowseDialog::GetParentPath(const UString &path, UString &parentPrefix, US
|
||||
return false;
|
||||
int pos = s.ReverseFind_PathSepar();
|
||||
parentPrefix.SetFrom(s, pos + 1);
|
||||
name = s.Ptr(pos + 1);
|
||||
name = s.Ptr((unsigned)(pos + 1));
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -604,7 +604,7 @@ HRESULT CBrowseDialog::Reload(const UString &pathPrefix, const UString &selected
|
||||
int subItem = 0;
|
||||
item.iSubItem = subItem++;
|
||||
item.lParam = kParentIndex;
|
||||
item.pszText = (wchar_t *)(const wchar_t *)itemName;
|
||||
item.pszText = itemName.Ptr_non_const();
|
||||
item.iImage = _extToIconMap.GetIconIndex(FILE_ATTRIBUTE_DIRECTORY, DirPrefix);
|
||||
if (item.iImage < 0)
|
||||
item.iImage = 0;
|
||||
@@ -626,7 +626,7 @@ HRESULT CBrowseDialog::Reload(const UString &pathPrefix, const UString &selected
|
||||
int subItem = 0;
|
||||
item.iSubItem = subItem++;
|
||||
item.lParam = i;
|
||||
item.pszText = (wchar_t *)(const wchar_t *)name;
|
||||
item.pszText = name.Ptr_non_const();
|
||||
|
||||
const UString fullPath = DirPrefix + name;
|
||||
#ifndef UNDER_CE
|
||||
@@ -953,7 +953,7 @@ bool CorrectFsPath(const UString &relBase, const UString &path2, UString &result
|
||||
if (path.Back() == WCHAR_PATH_SEPARATOR)
|
||||
{
|
||||
path.DeleteBack();
|
||||
result.Insert(0, WCHAR_PATH_SEPARATOR);;
|
||||
result.Insert(0, WCHAR_PATH_SEPARATOR);
|
||||
}
|
||||
int pos = path.ReverseFind(WCHAR_PATH_SEPARATOR) + 1;
|
||||
UString cur = path.Ptr(pos);
|
||||
|
||||
@@ -58,7 +58,7 @@ CEnumFormatEtc::~CEnumFormatEtc()
|
||||
for (ULONG i = 0; i < m_NumFormats; i++)
|
||||
if (m_Formats[i].ptd)
|
||||
CoTaskMemFree(m_Formats[i].ptd);
|
||||
delete[]m_Formats;
|
||||
delete []m_Formats;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
#ifndef __ENUMFORMATETC_H
|
||||
#define __ENUMFORMATETC_H
|
||||
|
||||
#include <windows.h>
|
||||
#include "../../../Common/MyWindows.h"
|
||||
|
||||
HRESULT CreateEnumFormatEtc(UINT numFormats, const FORMATETC *formats, IEnumFORMATETC **enumFormat);
|
||||
|
||||
|
||||
@@ -262,6 +262,7 @@ STDMETHODIMP CExtractCallbackImp::ShowMessage(const wchar_t *s)
|
||||
|
||||
#endif
|
||||
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, const wchar_t *fileName, UString &s);
|
||||
void SetExtractErrorMessage(Int32 opRes, Int32 encrypted, const wchar_t *fileName, UString &s)
|
||||
{
|
||||
s.Empty();
|
||||
@@ -449,6 +450,7 @@ static void AddNewLineString(UString &s, const UString &m)
|
||||
s.Add_LF();
|
||||
}
|
||||
|
||||
UString GetOpenArcErrorMessage(UInt32 errorFlags);
|
||||
UString GetOpenArcErrorMessage(UInt32 errorFlags)
|
||||
{
|
||||
UString s;
|
||||
@@ -523,6 +525,7 @@ static UString GetBracedType(const wchar_t *type)
|
||||
return s;
|
||||
}
|
||||
|
||||
void OpenResult_GUI(UString &s, const CCodecs *codecs, const CArchiveLink &arcLink, const wchar_t *name, HRESULT result);
|
||||
void OpenResult_GUI(UString &s, const CCodecs *codecs, const CArchiveLink &arcLink, const wchar_t *name, HRESULT result)
|
||||
{
|
||||
FOR_VECTOR (level, arcLink.Arcs)
|
||||
@@ -632,7 +635,9 @@ HRESULT CExtractCallbackImp::ExtractResult(HRESULT result)
|
||||
if (result == S_OK)
|
||||
return result;
|
||||
NumArchiveErrors++;
|
||||
if (result == E_ABORT || result == ERROR_DISK_FULL)
|
||||
if (result == E_ABORT
|
||||
|| result == HRESULT_FROM_WIN32(ERROR_DISK_FULL)
|
||||
)
|
||||
return result;
|
||||
|
||||
Add_ArchiveName_Error();
|
||||
@@ -702,7 +707,7 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
|
||||
{
|
||||
if (!destFileInfo.IsDir())
|
||||
{
|
||||
RINOK(MessageError("can not replace file with folder with same name", destPathSys));
|
||||
RINOK(MessageError("Cannot replace file with folder with same name", destPathSys));
|
||||
return E_ABORT;
|
||||
}
|
||||
*writeAnswer = BoolToInt(false);
|
||||
@@ -711,7 +716,7 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
|
||||
|
||||
if (destFileInfo.IsDir())
|
||||
{
|
||||
RINOK(MessageError("can not replace folder with file with same name", destPathSys));
|
||||
RINOK(MessageError("Cannot replace folder with file with same name", destPathSys));
|
||||
*writeAnswer = BoolToInt(false);
|
||||
return S_OK;
|
||||
}
|
||||
@@ -725,7 +730,7 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
|
||||
Int32 overwriteResult;
|
||||
UString destPathSpec = destPath;
|
||||
int slashPos = destPathSpec.ReverseFind_PathSepar();
|
||||
destPathSpec.DeleteFrom(slashPos + 1);
|
||||
destPathSpec.DeleteFrom((unsigned)(slashPos + 1));
|
||||
destPathSpec += fs2us(destFileInfo.Name);
|
||||
|
||||
RINOK(AskOverwrite(
|
||||
@@ -746,25 +751,28 @@ STDMETHODIMP CExtractCallbackImp::AskWrite(
|
||||
default:
|
||||
return E_FAIL;
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
if (OverwriteMode == NExtract::NOverwriteMode::kRename)
|
||||
{
|
||||
if (!AutoRenamePath(destPathSys))
|
||||
{
|
||||
RINOK(MessageError("can not create name for file", destPathSys));
|
||||
RINOK(MessageError("Cannot create name for file", destPathSys));
|
||||
return E_ABORT;
|
||||
}
|
||||
destPathResultTemp = fs2us(destPathSys);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (NFind::DoesFileExist(destPathSys))
|
||||
if (NFind::DoesFileExist_Raw(destPathSys))
|
||||
if (!NDir::DeleteFileAlways(destPathSys))
|
||||
if (GetLastError() != ERROR_FILE_NOT_FOUND)
|
||||
{
|
||||
RINOK(MessageError("can not delete output file", destPathSys));
|
||||
RINOK(MessageError("Cannot delete output file", destPathSys));
|
||||
return E_ABORT;
|
||||
}
|
||||
}
|
||||
@@ -950,9 +958,8 @@ STDMETHODIMP CExtractCallbackImp::SetOperationResult7(Int32 opRes, Int32 encrypt
|
||||
}
|
||||
|
||||
|
||||
static const size_t k_SizeT_MAX = (size_t)((size_t)0 - 1);
|
||||
|
||||
static const UInt32 kBlockSize = ((UInt32)1 << 31);
|
||||
// static const UInt32 kBlockSize = ((UInt32)1 << 31);
|
||||
|
||||
STDMETHODIMP CVirtFileSystem::Write(const void *data, UInt32 size, UInt32 *processedSize)
|
||||
{
|
||||
@@ -977,8 +984,9 @@ STDMETHODIMP CVirtFileSystem::Write(const void *data, UInt32 size, UInt32 *proce
|
||||
if (b < a)
|
||||
b = a;
|
||||
useMem = false;
|
||||
if (b <= k_SizeT_MAX && b <= MaxTotalAllocSize)
|
||||
useMem = file.Data.ReAlloc_KeepData((size_t)b, (size_t)file.Size);
|
||||
const size_t b_sizet = (size_t)b;
|
||||
if (b == b_sizet && b <= MaxTotalAllocSize)
|
||||
useMem = file.Data.ReAlloc_KeepData(b_sizet, (size_t)file.Size);
|
||||
}
|
||||
if (useMem)
|
||||
{
|
||||
|
||||
@@ -289,21 +289,19 @@ public:
|
||||
bool MultiArcMode;
|
||||
|
||||
CExtractCallbackImp():
|
||||
#ifndef _SFX
|
||||
_hashCalc(NULL),
|
||||
#endif
|
||||
ProcessAltStreams(true),
|
||||
StreamMode(false),
|
||||
OverwriteMode(NExtract::NOverwriteMode::kAsk),
|
||||
#ifndef _NO_CRYPTO
|
||||
PasswordIsDefined(false),
|
||||
PasswordWasAsked(false),
|
||||
#endif
|
||||
OverwriteMode(NExtract::NOverwriteMode::kAsk),
|
||||
StreamMode(false),
|
||||
ProcessAltStreams(true),
|
||||
|
||||
_totalFilesDefined(false),
|
||||
_totalBytesDefined(false),
|
||||
MultiArcMode(false)
|
||||
|
||||
#ifndef _SFX
|
||||
, _hashCalc(NULL)
|
||||
#endif
|
||||
{}
|
||||
|
||||
~CExtractCallbackImp();
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
#include "../../../Common/MyWindows.h"
|
||||
|
||||
#include <shlwapi.h>
|
||||
#include <Shlwapi.h>
|
||||
|
||||
#include "../../../../C/Alloc.h"
|
||||
#ifdef _WIN32
|
||||
@@ -40,19 +40,24 @@ using namespace NWindows;
|
||||
using namespace NFile;
|
||||
using namespace NFind;
|
||||
|
||||
#define MAX_LOADSTRING 100
|
||||
|
||||
#define MENU_HEIGHT 26
|
||||
// #define MAX_LOADSTRING 100
|
||||
|
||||
extern
|
||||
bool g_RAM_Size_Defined;
|
||||
bool g_LargePagesMode = false;
|
||||
bool g_OpenArchive = false;
|
||||
bool g_RAM_Size_Defined;
|
||||
|
||||
static bool g_LargePagesMode = false;
|
||||
// static bool g_OpenArchive = false;
|
||||
|
||||
static bool g_Maximized = false;
|
||||
|
||||
extern
|
||||
UInt64 g_RAM_Size;
|
||||
UInt64 g_RAM_Size;
|
||||
|
||||
#ifdef _WIN32
|
||||
extern
|
||||
HINSTANCE g_hInstance;
|
||||
HINSTANCE g_hInstance;
|
||||
#endif
|
||||
|
||||
@@ -66,6 +71,8 @@ void FreeGlobalCodecs();
|
||||
|
||||
#ifndef UNDER_CE
|
||||
|
||||
extern
|
||||
DWORD g_ComCtl32Version;
|
||||
DWORD g_ComCtl32Version;
|
||||
|
||||
static DWORD GetDllVersion(LPCTSTR dllName)
|
||||
@@ -74,7 +81,7 @@ static DWORD GetDllVersion(LPCTSTR dllName)
|
||||
HINSTANCE hinstDll = LoadLibrary(dllName);
|
||||
if (hinstDll)
|
||||
{
|
||||
DLLGETVERSIONPROC pDllGetVersion = (DLLGETVERSIONPROC)GetProcAddress(hinstDll, "DllGetVersion");
|
||||
DLLGETVERSIONPROC pDllGetVersion = (DLLGETVERSIONPROC)(void *)GetProcAddress(hinstDll, "DllGetVersion");
|
||||
if (pDllGetVersion)
|
||||
{
|
||||
DLLVERSIONINFO dvi;
|
||||
@@ -93,19 +100,19 @@ static DWORD GetDllVersion(LPCTSTR dllName)
|
||||
|
||||
bool g_IsSmallScreen = false;
|
||||
|
||||
extern
|
||||
bool g_LVN_ITEMACTIVATE_Support;
|
||||
bool g_LVN_ITEMACTIVATE_Support = true;
|
||||
// LVN_ITEMACTIVATE replaces both NM_DBLCLK & NM_RETURN
|
||||
// Windows 2000
|
||||
// NT/98 + IE 3 (g_ComCtl32Version >= 4.70)
|
||||
|
||||
|
||||
const int kNumDefaultPanels = 1;
|
||||
static const int kNumDefaultPanels = 1;
|
||||
static const int kSplitterWidth = 4;
|
||||
static const int kSplitterRateMax = 1 << 16;
|
||||
static const int kPanelSizeMin = 120;
|
||||
|
||||
const int kSplitterWidth = 4;
|
||||
int kSplitterRateMax = 1 << 16;
|
||||
int kPanelSizeMin = 120;
|
||||
|
||||
// bool OnMenuCommand(HWND hWnd, int id);
|
||||
|
||||
class CSplitterPos
|
||||
{
|
||||
@@ -343,7 +350,7 @@ typedef BOOL (WINAPI *Func_IsWow64Process)(HANDLE, PBOOL);
|
||||
static void Set_Wow64()
|
||||
{
|
||||
g_Is_Wow64 = false;
|
||||
Func_IsWow64Process fnIsWow64Process = (Func_IsWow64Process)GetProcAddress(
|
||||
Func_IsWow64Process fnIsWow64Process = (Func_IsWow64Process)(void *)GetProcAddress(
|
||||
GetModuleHandleA("kernel32.dll"), "IsWow64Process");
|
||||
if (fnIsWow64Process)
|
||||
{
|
||||
@@ -356,6 +363,7 @@ static void Set_Wow64()
|
||||
#endif
|
||||
|
||||
|
||||
bool IsLargePageSupported();
|
||||
bool IsLargePageSupported()
|
||||
{
|
||||
#ifdef _WIN64
|
||||
@@ -383,7 +391,7 @@ static void SetMemoryLock()
|
||||
if (!IsLargePageSupported())
|
||||
return;
|
||||
// if (ReadLockMemoryAdd())
|
||||
NSecurity::AddLockMemoryPrivilege();
|
||||
NSecurity::AddLockMemoryPrivilege();
|
||||
|
||||
if (ReadLockMemoryEnable())
|
||||
if (NSecurity::Get_LargePages_RiskLevel() == 0)
|
||||
@@ -393,6 +401,8 @@ static void SetMemoryLock()
|
||||
}
|
||||
}
|
||||
|
||||
extern
|
||||
bool g_SymLink_Supported;
|
||||
bool g_SymLink_Supported = false;
|
||||
|
||||
static void Set_SymLink_Supported()
|
||||
@@ -443,7 +453,9 @@ static void ErrorMessage(const char *s)
|
||||
}
|
||||
|
||||
|
||||
#if defined(_UNICODE) && !defined(_WIN64) && !defined(UNDER_CE)
|
||||
#define NT_CHECK_FAIL_ACTION ErrorMessage("Unsupported Windows version"); return 1;
|
||||
#endif
|
||||
|
||||
static int WINAPI WinMain2(int nCmdShow)
|
||||
{
|
||||
@@ -756,12 +768,12 @@ static void ExecuteCommand(UINT commandID)
|
||||
|
||||
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
int wmId, wmEvent;
|
||||
switch (message)
|
||||
{
|
||||
case WM_COMMAND:
|
||||
wmId = LOWORD(wParam);
|
||||
wmEvent = HIWORD(wParam);
|
||||
{
|
||||
unsigned wmId = LOWORD(wParam);
|
||||
unsigned wmEvent = HIWORD(wParam);
|
||||
if ((HWND) lParam != NULL && wmEvent != 0)
|
||||
break;
|
||||
if (wmId >= kMenuCmdID_Toolbar_Start && wmId < kMenuCmdID_Toolbar_End)
|
||||
@@ -772,6 +784,7 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
if (OnMenuCommand(hWnd, wmId))
|
||||
return 0;
|
||||
break;
|
||||
}
|
||||
case WM_INITMENUPOPUP:
|
||||
OnMenuActivating(hWnd, HMENU(wParam), LOWORD(lParam));
|
||||
break;
|
||||
@@ -837,9 +850,8 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
|
||||
g_App.CreateDragTarget();
|
||||
|
||||
bool archiveIsOpened;
|
||||
bool encrypted;
|
||||
bool needOpenFile = false;
|
||||
COpenResult openRes;
|
||||
bool needOpenArc = false;
|
||||
|
||||
UString fullPath = g_MainPath;
|
||||
if (!fullPath.IsEmpty() /* && g_OpenArchive */)
|
||||
@@ -850,29 +862,34 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
if (NFile::NName::GetFullPath(us2fs(fullPath), fullPathF))
|
||||
fullPath = fs2us(fullPathF);
|
||||
}
|
||||
if (NFile::NFind::DoesFileExist(us2fs(fullPath)))
|
||||
needOpenFile = true;
|
||||
if (NFile::NFind::DoesFileExist_FollowLink(us2fs(fullPath)))
|
||||
needOpenArc = true;
|
||||
}
|
||||
|
||||
HRESULT res = g_App.Create(hWnd, fullPath, g_ArcFormat, xSizes,
|
||||
needOpenFile,
|
||||
archiveIsOpened, encrypted);
|
||||
needOpenArc,
|
||||
openRes);
|
||||
|
||||
if (res == E_ABORT)
|
||||
return -1;
|
||||
|
||||
if (needOpenFile && !archiveIsOpened || res != S_OK)
|
||||
if ((needOpenArc && !openRes.ArchiveIsOpened) || res != S_OK)
|
||||
{
|
||||
UString m ("Error");
|
||||
if (res == S_FALSE || res == S_OK)
|
||||
{
|
||||
m = MyFormatNew(encrypted ?
|
||||
m = MyFormatNew(openRes.Encrypted ?
|
||||
IDS_CANT_OPEN_ENCRYPTED_ARCHIVE :
|
||||
IDS_CANT_OPEN_ARCHIVE,
|
||||
fullPath);
|
||||
}
|
||||
else if (res != S_OK)
|
||||
m = HResultToMessage(res);
|
||||
if (!openRes.ErrorMessage.IsEmpty())
|
||||
{
|
||||
m.Add_LF();
|
||||
m += openRes.ErrorMessage;
|
||||
}
|
||||
ErrorMessage(m);
|
||||
return -1;
|
||||
}
|
||||
@@ -954,7 +971,7 @@ LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||||
g_Panel[1]._listView.MoveWindow(xSize - xWidth, 0, xWidth, ySize);
|
||||
*/
|
||||
return 0;
|
||||
break;
|
||||
// break;
|
||||
}
|
||||
|
||||
case WM_SETFOCUS:
|
||||
|
||||
@@ -55,7 +55,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /machine:I386
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /machine:I386 /out:"C:\Program Files\7-ZIP\7zFM.exe" /opt:NOWIN98
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /machine:I386 /out:"C:\Util\7zFM.exe" /opt:NOWIN98
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "FM - Win32 Debug"
|
||||
@@ -82,7 +82,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /debug /machine:I386 /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /debug /machine:I386 /out:"C:\Program Files\7-ZIP\7zFM.exe" /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /debug /machine:I386 /out:"C:\Util\7zFM.exe" /pdbtype:sept
|
||||
|
||||
!ELSEIF "$(CFG)" == "FM - Win32 ReleaseU"
|
||||
|
||||
@@ -109,7 +109,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib /nologo /subsystem:windows /machine:I386
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /machine:I386 /out:"C:\Program Files\7-ZIP\7zFM.exe" /opt:NOWIN98
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /machine:I386 /out:"C:\Util\7zFM.exe" /opt:NOWIN98
|
||||
# SUBTRACT LINK32 /pdb:none
|
||||
|
||||
!ELSEIF "$(CFG)" == "FM - Win32 DebugU"
|
||||
@@ -137,7 +137,7 @@ BSC32=bscmake.exe
|
||||
# ADD BSC32 /nologo
|
||||
LINK32=link.exe
|
||||
# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib /nologo /subsystem:windows /debug /machine:I386 /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /debug /machine:I386 /out:"C:\Program Files\7-ZIP\7zFM.exe" /pdbtype:sept
|
||||
# ADD LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib comctl32.lib Mpr.lib htmlhelp.lib Urlmon.lib /nologo /subsystem:windows /debug /machine:I386 /out:"C:\Util\7zFM.exe" /pdbtype:sept
|
||||
|
||||
!ENDIF
|
||||
|
||||
@@ -393,6 +393,10 @@ SOURCE=.\PanelSort.cpp
|
||||
|
||||
SOURCE=.\PanelSplitFile.cpp
|
||||
# End Source File
|
||||
# Begin Source File
|
||||
|
||||
SOURCE=.\VerCtrl.cpp
|
||||
# End Source File
|
||||
# End Group
|
||||
# Begin Group "Dialog"
|
||||
|
||||
|
||||
@@ -7,8 +7,8 @@ LIBS = $(LIBS) ceshell.lib Commctrl.lib
|
||||
!ELSE
|
||||
LIBS = $(LIBS) comctl32.lib htmlhelp.lib comdlg32.lib Mpr.lib Gdi32.lib
|
||||
CFLAGS = $(CFLAGS) -DWIN_LONG_PATH -DSUPPORT_DEVICE_FILE
|
||||
LFLAGS = $(LFLAGS) /DELAYLOAD:mpr.dll
|
||||
LIBS = $(LIBS) delayimp.lib
|
||||
LFLAGS = $(LFLAGS) /DELAYLOAD:mpr.dll
|
||||
LIBS = $(LIBS) delayimp.lib
|
||||
!ENDIF
|
||||
|
||||
FM_OBJS = \
|
||||
@@ -70,6 +70,7 @@ FM_OBJS = \
|
||||
$O\SettingsPage.obj \
|
||||
$O\SplitDialog.obj \
|
||||
$O\SystemPage.obj \
|
||||
$O\VerCtrl.obj \
|
||||
|
||||
!IFNDEF UNDER_CE
|
||||
|
||||
|
||||
@@ -115,15 +115,15 @@ HRESULT CFsFolderStat::Enumerate()
|
||||
const unsigned len = Path.Len();
|
||||
CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(Path);
|
||||
CFileInfo fi;
|
||||
CDirEntry fi;
|
||||
while (enumerator.Next(fi))
|
||||
{
|
||||
if (fi.IsDir())
|
||||
{
|
||||
NumFolders++;
|
||||
Path.DeleteFrom(len);
|
||||
Path += fi.Name;
|
||||
RINOK(Enumerate());
|
||||
NumFolders++;
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -136,6 +136,7 @@ HRESULT CFsFolderStat::Enumerate()
|
||||
|
||||
#ifndef UNDER_CE
|
||||
|
||||
bool MyGetCompressedFileSizeW(CFSTR path, UInt64 &size);
|
||||
bool MyGetCompressedFileSizeW(CFSTR path, UInt64 &size)
|
||||
{
|
||||
DWORD highPart;
|
||||
@@ -171,7 +172,7 @@ bool MyGetCompressedFileSizeW(CFSTR path, UInt64 &size)
|
||||
|
||||
HRESULT CFSFolder::LoadSubItems(int dirItem, const FString &relPrefix)
|
||||
{
|
||||
unsigned startIndex = Folders.Size();
|
||||
const unsigned startIndex = Folders.Size();
|
||||
{
|
||||
CEnumerator enumerator;
|
||||
enumerator.SetDirPrefix(_path + relPrefix);
|
||||
@@ -261,7 +262,7 @@ HRESULT CFSFolder::LoadSubItems(int dirItem, const FString &relPrefix)
|
||||
if (!_flatMode)
|
||||
return S_OK;
|
||||
|
||||
unsigned endIndex = Folders.Size();
|
||||
const unsigned endIndex = Folders.Size();
|
||||
for (unsigned i = startIndex; i < endIndex; i++)
|
||||
LoadSubItems(i, Folders[i]);
|
||||
return S_OK;
|
||||
@@ -293,8 +294,9 @@ bool CFSFolder::LoadComments()
|
||||
return false;
|
||||
AString s;
|
||||
char *p = s.GetBuf((unsigned)(size_t)len);
|
||||
UInt32 processedSize;
|
||||
file.Read(p, (UInt32)len, processedSize);
|
||||
size_t processedSize;
|
||||
if (!file.ReadFull(p, (unsigned)(size_t)len, processedSize))
|
||||
return false;
|
||||
s.ReleaseBuf_CalcLen((unsigned)(size_t)len);
|
||||
if (processedSize != len)
|
||||
return false;
|
||||
@@ -506,7 +508,7 @@ STDMETHODIMP CFSFolder::GetProperty(UInt32 index, PROPID propID, PROPVARIANT *va
|
||||
{
|
||||
int pos = comment.Find((wchar_t)4);
|
||||
if (pos >= 0)
|
||||
comment.DeleteFrom(pos);
|
||||
comment.DeleteFrom((unsigned)pos);
|
||||
prop = comment;
|
||||
}
|
||||
break;
|
||||
@@ -784,7 +786,7 @@ STDMETHODIMP CFSFolder::BindToParentFolder(IFolderFolder **resultFolder)
|
||||
return E_FAIL;
|
||||
FString parentPath = _path.Left(pos);
|
||||
pos = parentPath.ReverseFind_PathSepar();
|
||||
parentPath.DeleteFrom(pos + 1);
|
||||
parentPath.DeleteFrom((unsigned)(pos + 1));
|
||||
|
||||
if (NName::IsDrivePath_SuperAllowed(parentPath))
|
||||
{
|
||||
|
||||
@@ -203,7 +203,7 @@ struct CCopyStateIO
|
||||
int ErrorFileIndex;
|
||||
UString ErrorMessage;
|
||||
|
||||
CCopyStateIO(): DeleteSrcFile(false), TotalSize(0), StartPos(0) {}
|
||||
CCopyStateIO(): TotalSize(0), StartPos(0), DeleteSrcFile(false) {}
|
||||
|
||||
HRESULT MyCopyFile(CFSTR inPath, CFSTR outPath, DWORD attrib = INVALID_FILE_ATTRIBUTES);
|
||||
};
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
#include "../../../Common/MyWindows.h"
|
||||
|
||||
#include <Winbase.h>
|
||||
#include <WinBase.h>
|
||||
|
||||
#include "../../../Common/Defs.h"
|
||||
#include "../../../Common/StringConvert.h"
|
||||
@@ -397,8 +397,8 @@ static HRESULT CopyFile_Ask(
|
||||
{
|
||||
RINOK(SendMessageError(state.Callback,
|
||||
state.MoveMode ?
|
||||
"can not move file onto itself" :
|
||||
"can not copy file onto itself"
|
||||
"Cannot move file onto itself" :
|
||||
"Cannot copy file onto itself"
|
||||
, destPath));
|
||||
return E_ABORT;
|
||||
}
|
||||
@@ -497,8 +497,8 @@ static HRESULT CopyFolder(
|
||||
{
|
||||
RINOK(SendMessageError(state.Callback,
|
||||
state.MoveMode ?
|
||||
"can not copy folder onto itself" :
|
||||
"can not move folder onto itself"
|
||||
"Cannot copy folder onto itself" :
|
||||
"Cannot move folder onto itself"
|
||||
, destPath));
|
||||
return E_ABORT;
|
||||
}
|
||||
@@ -513,7 +513,7 @@ static HRESULT CopyFolder(
|
||||
|
||||
if (!CreateComplexDir(destPath))
|
||||
{
|
||||
RINOK(SendMessageError(state.Callback, "can not create folder", destPath));
|
||||
RINOK(SendMessageError(state.Callback, "Cannot create folder", destPath));
|
||||
return E_ABORT;
|
||||
}
|
||||
|
||||
@@ -547,7 +547,7 @@ static HRESULT CopyFolder(
|
||||
{
|
||||
if (!RemoveDir(srcPath))
|
||||
{
|
||||
RINOK(SendMessageError(state.Callback, "can not remove folder", srcPath));
|
||||
RINOK(SendMessageError(state.Callback, "Cannot remove folder", srcPath));
|
||||
return E_ABORT;
|
||||
}
|
||||
}
|
||||
@@ -566,7 +566,7 @@ STDMETHODIMP CFSFolder::CopyTo(Int32 moveMode, const UInt32 *indices, UInt32 num
|
||||
if (destPath.IsEmpty())
|
||||
return E_INVALIDARG;
|
||||
|
||||
bool isAltDest = NName::IsAltPathPrefix(destPath);;
|
||||
bool isAltDest = NName::IsAltPathPrefix(destPath);
|
||||
bool isDirectPath = (!isAltDest && !IsPathSepar(destPath.Back()));
|
||||
|
||||
if (isDirectPath)
|
||||
|
||||
@@ -8,10 +8,14 @@
|
||||
#include "../../../Windows/Thread.h"
|
||||
|
||||
#include "../Agent/Agent.h"
|
||||
#include "../GUI/ExtractRes.h"
|
||||
|
||||
#include "FileFolderPluginOpen.h"
|
||||
#include "FormatUtils.h"
|
||||
#include "LangUtils.h"
|
||||
#include "OpenCallback.h"
|
||||
#include "PluginLoader.h"
|
||||
#include "PropertyName.h"
|
||||
#include "RegistryPlugins.h"
|
||||
|
||||
using namespace NWindows;
|
||||
@@ -69,18 +73,165 @@ static void SplitNameToPureNameAndExtension(const FString &fullName,
|
||||
{
|
||||
pureName.SetFrom(fullName, index);
|
||||
extensionDelimiter = '.';
|
||||
extension = fullName.Ptr(index + 1);
|
||||
extension = fullName.Ptr((unsigned)index + 1);
|
||||
}
|
||||
}
|
||||
|
||||
HRESULT OpenFileFolderPlugin(
|
||||
IInStream *inStream,
|
||||
const FString &path,
|
||||
const UString &arcFormat,
|
||||
HMODULE *module,
|
||||
IFolderFolder **resultFolder,
|
||||
HWND parentWindow,
|
||||
bool &encrypted, UString &password)
|
||||
|
||||
struct CArcLevelInfo
|
||||
{
|
||||
UString Error;
|
||||
UString Path;
|
||||
UString Type;
|
||||
UString ErrorType;
|
||||
UString ErrorFlags;
|
||||
};
|
||||
|
||||
|
||||
struct CArcLevelsInfo
|
||||
{
|
||||
CObjectVector<CArcLevelInfo> Levels; // LastLevel Is NON-OPEN
|
||||
};
|
||||
|
||||
|
||||
UString GetOpenArcErrorMessage(UInt32 errorFlags);
|
||||
|
||||
|
||||
static void GetFolderLevels(CMyComPtr<IFolderFolder> &folder, CArcLevelsInfo &levels)
|
||||
{
|
||||
levels.Levels.Clear();
|
||||
|
||||
CMyComPtr<IGetFolderArcProps> getFolderArcProps;
|
||||
folder.QueryInterface(IID_IGetFolderArcProps, &getFolderArcProps);
|
||||
|
||||
if (!getFolderArcProps)
|
||||
return;
|
||||
CMyComPtr<IFolderArcProps> arcProps;
|
||||
getFolderArcProps->GetFolderArcProps(&arcProps);
|
||||
if (!arcProps)
|
||||
return;
|
||||
|
||||
UInt32 numLevels;
|
||||
if (arcProps->GetArcNumLevels(&numLevels) != S_OK)
|
||||
numLevels = 0;
|
||||
|
||||
for (UInt32 level = 0; level <= numLevels; level++)
|
||||
{
|
||||
const PROPID propIDs[] = { kpidError, kpidPath, kpidType, kpidErrorType };
|
||||
|
||||
CArcLevelInfo lev;
|
||||
|
||||
for (Int32 i = 0; i < 4; i++)
|
||||
{
|
||||
CMyComBSTR name;
|
||||
NCOM::CPropVariant prop;
|
||||
if (arcProps->GetArcProp(level, propIDs[i], &prop) != S_OK)
|
||||
continue;
|
||||
if (prop.vt != VT_EMPTY)
|
||||
{
|
||||
UString *s = NULL;
|
||||
switch (propIDs[i])
|
||||
{
|
||||
case kpidError: s = &lev.Error; break;
|
||||
case kpidPath: s = &lev.Path; break;
|
||||
case kpidType: s = &lev.Type; break;
|
||||
case kpidErrorType: s = &lev.ErrorType; break;
|
||||
}
|
||||
*s = (prop.vt == VT_BSTR) ? prop.bstrVal : L"?";
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
NCOM::CPropVariant prop;
|
||||
if (arcProps->GetArcProp(level, kpidErrorFlags, &prop) == S_OK)
|
||||
{
|
||||
UInt32 flags = GetOpenArcErrorFlags(prop);
|
||||
if (flags != 0)
|
||||
lev.ErrorFlags = GetOpenArcErrorMessage(flags);
|
||||
}
|
||||
}
|
||||
|
||||
levels.Levels.Add(lev);
|
||||
}
|
||||
}
|
||||
|
||||
static UString GetBracedType(const wchar_t *type)
|
||||
{
|
||||
UString s ('[');
|
||||
s += type;
|
||||
s += ']';
|
||||
return s;
|
||||
}
|
||||
|
||||
static void GetFolderError(CMyComPtr<IFolderFolder> &folder, UString &open_Errors, UString &nonOpen_Errors)
|
||||
{
|
||||
CArcLevelsInfo levs;
|
||||
GetFolderLevels(folder, levs);
|
||||
open_Errors.Empty();
|
||||
nonOpen_Errors.Empty();
|
||||
|
||||
FOR_VECTOR (i, levs.Levels)
|
||||
{
|
||||
bool isNonOpenLevel = (i == 0);
|
||||
const CArcLevelInfo &lev = levs.Levels[levs.Levels.Size() - 1 - i];
|
||||
|
||||
UString m;
|
||||
|
||||
if (!lev.ErrorType.IsEmpty())
|
||||
{
|
||||
m = MyFormatNew(IDS_CANT_OPEN_AS_TYPE, GetBracedType(lev.ErrorType));
|
||||
if (!isNonOpenLevel)
|
||||
{
|
||||
m.Add_LF();
|
||||
m += MyFormatNew(IDS_IS_OPEN_AS_TYPE, GetBracedType(lev.Type));
|
||||
}
|
||||
}
|
||||
|
||||
if (!lev.Error.IsEmpty())
|
||||
{
|
||||
if (!m.IsEmpty())
|
||||
m.Add_LF();
|
||||
m += GetBracedType(lev.Type);
|
||||
m += " : ";
|
||||
m += GetNameOfProperty(kpidError, L"Error");
|
||||
m += " : ";
|
||||
m += lev.Error;
|
||||
}
|
||||
|
||||
if (!lev.ErrorFlags.IsEmpty())
|
||||
{
|
||||
if (!m.IsEmpty())
|
||||
m.Add_LF();
|
||||
m += GetNameOfProperty(kpidErrorFlags, L"Errors");
|
||||
m += ": ";
|
||||
m += lev.ErrorFlags;
|
||||
}
|
||||
|
||||
if (!m.IsEmpty())
|
||||
{
|
||||
if (isNonOpenLevel)
|
||||
{
|
||||
UString &s = nonOpen_Errors;
|
||||
s += lev.Path;
|
||||
s.Add_LF();
|
||||
s += m;
|
||||
}
|
||||
else
|
||||
{
|
||||
UString &s = open_Errors;
|
||||
if (!s.IsEmpty())
|
||||
s += "--------------------\n";
|
||||
s += lev.Path;
|
||||
s.Add_LF();
|
||||
s += m;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
HRESULT CFfpOpen::OpenFileFolderPlugin(IInStream *inStream,
|
||||
const FString &path, const UString &arcFormat, HWND parentWindow)
|
||||
{
|
||||
CObjectVector<CPluginInfo> plugins;
|
||||
ReadFileFolderPluginInfoList(plugins);
|
||||
@@ -92,8 +243,8 @@ HRESULT OpenFileFolderPlugin(
|
||||
FString fileName;
|
||||
if (slashPos >= 0)
|
||||
{
|
||||
dirPrefix.SetFrom(path, slashPos + 1);
|
||||
fileName = path.Ptr(slashPos + 1);
|
||||
dirPrefix.SetFrom(path, (unsigned)(slashPos + 1));
|
||||
fileName = path.Ptr((unsigned)(slashPos + 1));
|
||||
}
|
||||
else
|
||||
fileName = path;
|
||||
@@ -120,6 +271,8 @@ HRESULT OpenFileFolderPlugin(
|
||||
}
|
||||
*/
|
||||
|
||||
ErrorMessage.Empty();
|
||||
|
||||
FOR_VECTOR (i, plugins)
|
||||
{
|
||||
const CPluginInfo &plugin = plugins[i];
|
||||
@@ -136,24 +289,29 @@ HRESULT OpenFileFolderPlugin(
|
||||
|
||||
t.OpenCallbackSpec = new COpenArchiveCallback;
|
||||
t.OpenCallback = t.OpenCallbackSpec;
|
||||
t.OpenCallbackSpec->PasswordIsDefined = encrypted;
|
||||
t.OpenCallbackSpec->Password = password;
|
||||
t.OpenCallbackSpec->PasswordIsDefined = Encrypted;
|
||||
t.OpenCallbackSpec->Password = Password;
|
||||
t.OpenCallbackSpec->ParentWindow = parentWindow;
|
||||
|
||||
if (inStream)
|
||||
t.OpenCallbackSpec->SetSubArchiveName(fs2us(fileName));
|
||||
else
|
||||
t.OpenCallbackSpec->LoadFileInfo(dirPrefix, fileName);
|
||||
{
|
||||
RINOK(t.OpenCallbackSpec->LoadFileInfo2(dirPrefix, fileName));
|
||||
}
|
||||
|
||||
t.InStream = inStream;
|
||||
t.Path = fs2us(path);
|
||||
t.ArcFormat = arcFormat;
|
||||
|
||||
UString progressTitle = LangString(IDS_OPENNING);
|
||||
t.OpenCallbackSpec->ProgressDialog.MainWindow = parentWindow;
|
||||
t.OpenCallbackSpec->ProgressDialog.MainTitle = "7-Zip"; // LangString(IDS_APP_TITLE);
|
||||
t.OpenCallbackSpec->ProgressDialog.MainAddTitle = progressTitle + L' ';
|
||||
t.OpenCallbackSpec->ProgressDialog.WaitMode = true;
|
||||
const UString progressTitle = LangString(IDS_OPENNING);
|
||||
{
|
||||
CProgressDialog &pd = t.OpenCallbackSpec->ProgressDialog;
|
||||
pd.MainWindow = parentWindow;
|
||||
pd.MainTitle = "7-Zip"; // LangString(IDS_APP_TITLE);
|
||||
pd.MainAddTitle = progressTitle + L' ';
|
||||
pd.WaitMode = true;
|
||||
}
|
||||
|
||||
{
|
||||
NWindows::CThread thread;
|
||||
@@ -161,23 +319,39 @@ HRESULT OpenFileFolderPlugin(
|
||||
t.OpenCallbackSpec->StartProgressDialog(progressTitle, thread);
|
||||
}
|
||||
|
||||
if (t.Result == E_ABORT)
|
||||
if (t.Result != S_FALSE && t.Result != S_OK)
|
||||
return t.Result;
|
||||
|
||||
encrypted = t.OpenCallbackSpec->PasswordIsDefined;
|
||||
if (t.Folder)
|
||||
{
|
||||
UString open_Errors, nonOpen_Errors;
|
||||
GetFolderError(t.Folder, open_Errors, nonOpen_Errors);
|
||||
if (!nonOpen_Errors.IsEmpty())
|
||||
{
|
||||
ErrorMessage = nonOpen_Errors;
|
||||
// if (t.Result != S_OK) return t.Result;
|
||||
/* if there are good open leves, and non0open level,
|
||||
we could force error as critical error and return error here
|
||||
but it's better to allow to open such rachives */
|
||||
// return S_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
// if (openCallbackSpec->PasswordWasAsked)
|
||||
{
|
||||
Encrypted = t.OpenCallbackSpec->PasswordIsDefined;
|
||||
Password = t.OpenCallbackSpec->Password;
|
||||
}
|
||||
|
||||
if (t.Result == S_OK)
|
||||
{
|
||||
// if (openCallbackSpec->PasswordWasAsked)
|
||||
{
|
||||
password = t.OpenCallbackSpec->Password;
|
||||
}
|
||||
*module = library.Detach();
|
||||
*resultFolder = t.Folder.Detach();
|
||||
return S_OK;
|
||||
Library.Attach(library.Detach());
|
||||
// Folder.Attach(t.Folder.Detach());
|
||||
Folder = t.Folder;
|
||||
}
|
||||
|
||||
if (t.Result != S_FALSE)
|
||||
return t.Result;
|
||||
return t.Result;
|
||||
}
|
||||
|
||||
return S_FALSE;
|
||||
}
|
||||
|
||||
@@ -3,7 +3,25 @@
|
||||
#ifndef __FILE_FOLDER_PLUGIN_OPEN_H
|
||||
#define __FILE_FOLDER_PLUGIN_OPEN_H
|
||||
|
||||
HRESULT OpenFileFolderPlugin(IInStream *inStream, const FString &path, const UString &arcFormat,
|
||||
HMODULE *module, IFolderFolder **resultFolder, HWND parentWindow, bool &encrypted, UString &password);
|
||||
#include "../../../Windows/DLL.h"
|
||||
|
||||
struct CFfpOpen
|
||||
{
|
||||
CLASS_NO_COPY(CFfpOpen)
|
||||
public:
|
||||
// out:
|
||||
bool Encrypted;
|
||||
UString Password;
|
||||
|
||||
NWindows::NDLL::CLibrary Library;
|
||||
CMyComPtr<IFolderFolder> Folder;
|
||||
UString ErrorMessage;
|
||||
|
||||
CFfpOpen(): Encrypted (false) {}
|
||||
|
||||
HRESULT OpenFileFolderPlugin(IInStream *inStream,
|
||||
const FString &path, const UString &arcFormat, HWND parentWindow);
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -4,7 +4,7 @@
|
||||
|
||||
#include "HelpUtils.h"
|
||||
|
||||
#if defined(UNDER_CE) || !defined(_WIN32)
|
||||
#if defined(UNDER_CE) || !defined(_WIN32) /* || !defined(_MSC_VER) */
|
||||
|
||||
void ShowHelpWindow(LPCSTR)
|
||||
{
|
||||
|
||||
@@ -23,6 +23,7 @@ static CLang g_Lang;
|
||||
static bool g_Loaded = false;
|
||||
static NSynchronization::CCriticalSection g_CriticalSection;
|
||||
|
||||
bool LangOpen(CLang &lang, CFSTR fileName);
|
||||
bool LangOpen(CLang &lang, CFSTR fileName)
|
||||
{
|
||||
return lang.Open(fileName, "7-Zip");
|
||||
@@ -145,7 +146,7 @@ static const char * const kLangs =
|
||||
"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."
|
||||
"ky.sw.tk.uz.-latn.-cyrl.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.."
|
||||
|
||||
@@ -36,46 +36,50 @@ static const UInt32 kLangIDs[] =
|
||||
IDR_LINK_TYPE_HARD,
|
||||
IDR_LINK_TYPE_SYM_FILE,
|
||||
IDR_LINK_TYPE_SYM_DIR,
|
||||
IDR_LINK_TYPE_JUNCTION
|
||||
IDR_LINK_TYPE_JUNCTION,
|
||||
IDR_LINK_TYPE_WSL
|
||||
};
|
||||
#endif
|
||||
|
||||
static bool GetSymLink(CFSTR path, CReparseAttr &attr)
|
||||
{
|
||||
NIO::CInFile file;
|
||||
if (!file.Open(path,
|
||||
FILE_SHARE_READ,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OPEN_REPARSE_POINT | FILE_FLAG_BACKUP_SEMANTICS))
|
||||
return false;
|
||||
|
||||
const unsigned kBufSize = MAXIMUM_REPARSE_DATA_BUFFER_SIZE;
|
||||
CByteArr buf(kBufSize);
|
||||
DWORD returnedSize;
|
||||
if (!file.DeviceIoControlOut(my_FSCTL_GET_REPARSE_POINT, buf, kBufSize, &returnedSize))
|
||||
static bool GetSymLink(CFSTR path, CReparseAttr &attr, UString &errorMessage)
|
||||
{
|
||||
CByteBuffer buf;
|
||||
if (!NIO::GetReparseData(path, buf, NULL))
|
||||
return false;
|
||||
|
||||
DWORD errorCode = 0;
|
||||
if (!attr.Parse(buf, returnedSize, errorCode))
|
||||
if (!attr.Parse(buf, buf.Size()))
|
||||
{
|
||||
SetLastError(attr.ErrorCode);
|
||||
return false;
|
||||
}
|
||||
|
||||
CByteBuffer data2;
|
||||
if (!FillLinkData(data2, attr.GetPath(), attr.IsSymLink()))
|
||||
if (!FillLinkData(data2, attr.GetPath(),
|
||||
!attr.IsMountPoint(), attr.IsSymLink_WSL()))
|
||||
{
|
||||
errorMessage = "Cannot reproduce reparse point";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (data2.Size() != returnedSize ||
|
||||
memcmp(data2, buf, returnedSize) != 0)
|
||||
if (data2.Size() != buf.Size() ||
|
||||
memcmp(data2, buf, buf.Size()) != 0)
|
||||
{
|
||||
errorMessage = "mismatch for reproduced reparse point";
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
static const int k_LinkType_Buttons[] =
|
||||
{
|
||||
IDR_LINK_TYPE_HARD,
|
||||
IDR_LINK_TYPE_SYM_FILE,
|
||||
IDR_LINK_TYPE_SYM_DIR,
|
||||
IDR_LINK_TYPE_JUNCTION
|
||||
IDR_LINK_TYPE_JUNCTION,
|
||||
IDR_LINK_TYPE_WSL
|
||||
};
|
||||
|
||||
void CLinkDialog::Set_LinkType_Radio(int idb)
|
||||
@@ -104,16 +108,33 @@ bool CLinkDialog::OnInit()
|
||||
if (fi.HasReparsePoint())
|
||||
{
|
||||
CReparseAttr attr;
|
||||
bool res = GetSymLink(us2fs(FilePath), attr);
|
||||
UString error;
|
||||
bool res = GetSymLink(us2fs(FilePath), attr, error);
|
||||
if (!res && error.IsEmpty())
|
||||
{
|
||||
DWORD lastError = GetLastError();
|
||||
if (lastError != 0)
|
||||
error = NError::MyFormatMessage(lastError);
|
||||
}
|
||||
|
||||
UString s = attr.PrintName;
|
||||
UString s = attr.GetPath();
|
||||
if (!attr.IsSymLink_WSL())
|
||||
if (!attr.IsOkNamePair())
|
||||
{
|
||||
s += " : ";
|
||||
s += attr.SubsName;
|
||||
s += attr.PrintName;
|
||||
}
|
||||
|
||||
if (!res)
|
||||
{
|
||||
s.Insert(0, L"ERROR: ");
|
||||
if (!error.IsEmpty())
|
||||
{
|
||||
s += " : ";
|
||||
s += error;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
SetItemText(IDT_LINK_PATH_TO_CUR, s);
|
||||
|
||||
@@ -121,11 +142,13 @@ bool CLinkDialog::OnInit()
|
||||
_pathFromCombo.SetText(FilePath);
|
||||
_pathToCombo.SetText(destPath);
|
||||
|
||||
if (res)
|
||||
// if (res)
|
||||
{
|
||||
if (attr.IsMountPoint())
|
||||
linkType = IDR_LINK_TYPE_JUNCTION;
|
||||
if (attr.IsSymLink())
|
||||
else if (attr.IsSymLink_WSL())
|
||||
linkType = IDR_LINK_TYPE_WSL;
|
||||
else if (attr.IsSymLink_Win())
|
||||
{
|
||||
linkType =
|
||||
fi.IsDir() ?
|
||||
@@ -140,6 +163,7 @@ bool CLinkDialog::OnInit()
|
||||
}
|
||||
else
|
||||
{
|
||||
// no ReparsePoint
|
||||
_pathFromCombo.SetText(AnotherPath);
|
||||
_pathToCombo.SetText(FilePath);
|
||||
if (fi.IsDir())
|
||||
@@ -258,15 +282,18 @@ void CLinkDialog::OnButton_Link()
|
||||
}
|
||||
|
||||
NFind::CFileInfo info1, info2;
|
||||
bool finded1 = info1.Find(us2fs(from));
|
||||
bool finded2 = info2.Find(us2fs(to));
|
||||
const bool finded1 = info1.Find(us2fs(from));
|
||||
const bool finded2 = info2.Find(us2fs(to));
|
||||
|
||||
bool isDirLink = (
|
||||
const bool isDirLink = (
|
||||
idb == IDR_LINK_TYPE_SYM_DIR ||
|
||||
idb == IDR_LINK_TYPE_JUNCTION);
|
||||
|
||||
if (finded1 && info1.IsDir() != isDirLink ||
|
||||
finded2 && info2.IsDir() != isDirLink)
|
||||
const bool isWSL = (idb == IDR_LINK_TYPE_WSL);
|
||||
|
||||
if (!isWSL)
|
||||
if ((finded1 && info1.IsDir() != isDirLink) ||
|
||||
(finded2 && info2.IsDir() != isDirLink))
|
||||
{
|
||||
ShowError(L"Incorrect link type");
|
||||
return;
|
||||
@@ -282,25 +309,41 @@ void CLinkDialog::OnButton_Link()
|
||||
}
|
||||
else
|
||||
{
|
||||
bool isSymLink = (idb != IDR_LINK_TYPE_JUNCTION);
|
||||
if (finded1 && !info1.IsDir() && !info1.HasReparsePoint() && info1.Size != 0)
|
||||
{
|
||||
UString s ("WARNING: reparse point will hide the data of existing file");
|
||||
s.Add_LF();
|
||||
s += from;
|
||||
ShowError(s);
|
||||
return;
|
||||
}
|
||||
|
||||
const bool isSymLink = (idb != IDR_LINK_TYPE_JUNCTION);
|
||||
|
||||
CByteBuffer data;
|
||||
if (!FillLinkData(data, to, isSymLink))
|
||||
if (!FillLinkData(data, to, isSymLink, isWSL))
|
||||
{
|
||||
ShowError(L"Incorrect link");
|
||||
return;
|
||||
}
|
||||
|
||||
CReparseAttr attr;
|
||||
DWORD errorCode = 0;
|
||||
if (!attr.Parse(data, data.Size(), errorCode))
|
||||
if (!attr.Parse(data, data.Size()))
|
||||
{
|
||||
ShowError(L"Internal conversion error");
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (!NIO::SetReparseData(us2fs(from), isDirLink, data, (DWORD)data.Size()))
|
||||
|
||||
bool res;
|
||||
if (to.IsEmpty())
|
||||
{
|
||||
// res = NIO::SetReparseData(us2fs(from), isDirLink, NULL, 0);
|
||||
res = NIO::DeleteReparseData(us2fs(from));
|
||||
}
|
||||
else
|
||||
res = NIO::SetReparseData(us2fs(from), isDirLink, data, (DWORD)data.Size());
|
||||
|
||||
if (!res)
|
||||
{
|
||||
ShowLastErrorMessage();
|
||||
return;
|
||||
@@ -350,5 +393,7 @@ void CApp::Link()
|
||||
if (dlg.Create(srcPanel.GetParent()) != IDOK)
|
||||
return;
|
||||
|
||||
// fix it: we should refresh panel with changed link
|
||||
|
||||
RefreshTitleAlways();
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
#include "../../GuiCommon.rc"
|
||||
|
||||
#define xc 288
|
||||
#define yc 200
|
||||
#define yc 214
|
||||
|
||||
#undef xRadioSize
|
||||
#define xRadioSize xc - m - 2
|
||||
@@ -20,7 +20,7 @@ BEGIN
|
||||
|
||||
LTEXT "", IDT_LINK_PATH_TO_CUR, m, 78, xc, 8
|
||||
|
||||
GROUPBOX "Link Type", IDG_LINK_TYPE, m, 104, xc, 76
|
||||
GROUPBOX "Link Type", IDG_LINK_TYPE, m, 104, xc, 90
|
||||
|
||||
CONTROL "Hard Link", IDR_LINK_TYPE_HARD, "Button", BS_AUTORADIOBUTTON | WS_GROUP,
|
||||
m + m, 120, xRadioSize, 10
|
||||
@@ -30,6 +30,8 @@ BEGIN
|
||||
m + m, 148, xRadioSize, 10
|
||||
CONTROL "Directory Junction", IDR_LINK_TYPE_JUNCTION, "Button", BS_AUTORADIOBUTTON,
|
||||
m + m, 162, xRadioSize, 10
|
||||
CONTROL "WSL", IDR_LINK_TYPE_WSL, "Button", BS_AUTORADIOBUTTON,
|
||||
m + m, 176, xRadioSize, 10
|
||||
|
||||
DEFPUSHBUTTON "Link", IDB_LINK_LINK, bx2, by, bxs, bys
|
||||
PUSHBUTTON "Cancel", IDCANCEL, bx1, by, bxs, bys
|
||||
|
||||
@@ -10,6 +10,7 @@
|
||||
#define IDR_LINK_TYPE_SYM_FILE 7712
|
||||
#define IDR_LINK_TYPE_SYM_DIR 7713
|
||||
#define IDR_LINK_TYPE_JUNCTION 7714
|
||||
#define IDR_LINK_TYPE_WSL 7715
|
||||
|
||||
|
||||
#define IDC_LINK_PATH_FROM 100
|
||||
|
||||
@@ -152,7 +152,7 @@ bool CMenuPage::OnInit()
|
||||
);
|
||||
|
||||
|
||||
if (!NFile::NFind::DoesFileExist(path))
|
||||
if (!NFile::NFind::DoesFileExist_Raw(path))
|
||||
{
|
||||
path.Empty();
|
||||
EnableItem(dll.ctrl, false);
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user