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

github.com/kornelski/7z.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIgor Pavlov <ipavlov@users.sourceforge.net>2015-12-31 03:00:00 +0300
committerKornel LesiƄski <kornel@geekhood.net>2016-05-28 02:16:58 +0300
commit9608215ad8deb58355bae27692669fda067c4f43 (patch)
tree1227131a3f19bc36e5da4ba11791154d05cc08af /CPP/7zip/UI/FileManager/PanelItemOpen.cpp
parent5de23c1deb52b8be4c43ad9f694c64bbddd0c38a (diff)
15.1315.13
Diffstat (limited to 'CPP/7zip/UI/FileManager/PanelItemOpen.cpp')
-rw-r--r--CPP/7zip/UI/FileManager/PanelItemOpen.cpp575
1 files changed, 507 insertions, 68 deletions
diff --git a/CPP/7zip/UI/FileManager/PanelItemOpen.cpp b/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
index c37ac64f..cfbc5770 100644
--- a/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
+++ b/CPP/7zip/UI/FileManager/PanelItemOpen.cpp
@@ -6,6 +6,8 @@
#include <tlhelp32.h>
+#include "../../../Common/IntToString.h"
+
#include "../../../Common/AutoPtr.h"
#include "../../../Common/StringConvert.h"
@@ -24,6 +26,7 @@
#include "FileFolderPluginOpen.h"
#include "FormatUtils.h"
#include "LangUtils.h"
+#include "PropertyNameRes.h"
#include "RegistryUtils.h"
#include "UpdateCallback100.h"
@@ -45,6 +48,20 @@ extern bool g_IsNT;
static CFSTR kTempDirPrefix = FTEXT("7zO");
+// #define SHOW_DEBUG_INFO
+
+#ifdef SHOW_DEBUG_INFO
+ #define DEBUG_PRINT(s) OutputDebugStringA(s);
+ #define DEBUG_PRINT_W(s) OutputDebugStringW(s);
+ #define DEBUG_PRINT_NUM(s, num) { char ttt[32]; ConvertUInt32ToString(num, ttt); OutputDebugStringA(s); OutputDebugStringA(ttt); }
+#else
+ #define DEBUG_PRINT(s)
+ #define DEBUG_PRINT_W(s)
+ #define DEBUG_PRINT_NUM(s, num)
+#endif
+
+
+
#ifndef UNDER_CE
class CProcessSnapshot
@@ -76,90 +93,329 @@ public:
#endif
-typedef DWORD (WINAPI *GetProcessIdFunc)(HANDLE process);
+
+/*
+struct COpenExtProg
+{
+ const char *Ext;
+ const char *Prog;
+};
+
+static const COpenExtProg g_Progs[] =
+{
+ { "jpeg jpg png bmp gif", "Microsoft.Photos.exe" },
+ { "html htm pdf", "MicrosoftEdge.exe" },
+ // , { "rrr", "notepad.exe" }
+};
+
+static bool FindExtProg(const char *exts, const char *ext)
+{
+ unsigned len = (unsigned)strlen(ext);
+ for (;;)
+ {
+ const char *p = exts;
+ for (;; p++)
+ {
+ const char c = *p;
+ if (c == 0 || c == ' ')
+ break;
+ }
+ if (len == (unsigned)(p - exts) && IsString1PrefixedByString2(exts, ext))
+ return true;
+ if (*p == 0)
+ return false;
+ exts = p + 1;
+ }
+}
+
+class CPossibleProgs
+{
+public:
+ AStringVector ProgNames;
+
+ void SetFromExtension(const char *ext) // ext must be low case
+ {
+ ProgNames.Clear();
+ for (unsigned i = 0; i < ARRAY_SIZE(g_Progs); i++)
+ if (FindExtProg(g_Progs[i].Ext, ext))
+ {
+ ProgNames.Add(g_Progs[i].Prog);
+ }
+ }
+
+ bool IsFromList(const UString &progName) const
+ {
+ FOR_VECTOR (i, ProgNames)
+ if (progName.IsEqualTo_Ascii_NoCase(ProgNames[i]))
+ return true;
+ return false;
+ }
+};
+*/
+
+
+#ifndef UNDER_CE
+
+EXTERN_C_BEGIN
+
+/*
+GetProcessImageFileName
+ returns the path in device form, rather than drive letters:
+ \Device\HarddiskVolume1\WINDOWS\SysWOW64\notepad.exe
+
+GetModuleFileNameEx works only after Sleep(something). Why?
+ returns the path
+ C:\WINDOWS\system32\NOTEPAD.EXE
+*/
+
+/* Kernel32.dll: Win7, Win2008R2;
+ Psapi.dll: (if PSAPI_VERSION=1) on Win7 and Win2008R2;
+ Psapi.dll: XP, Win2003, Vista, 2008;
+*/
+
+typedef DWORD (WINAPI *Func_GetProcessImageFileNameW)(
+ HANDLE hProcess, LPWSTR lpFilename, DWORD nSize);
+
+typedef DWORD (WINAPI *Func_GetModuleFileNameExW)(
+ HANDLE hProcess, HMODULE hModule, LPWSTR lpFilename, DWORD nSize);
+
+typedef DWORD (WINAPI *Func_GetProcessId)(HANDLE process);
+
+EXTERN_C_END
+
+
+static HMODULE g_Psapi_dll_module;
+
+/*
+static void My_GetProcessFileName_2(HANDLE hProcess, UString &path)
+{
+ path.Empty();
+ const unsigned maxPath = 1024;
+ WCHAR temp[maxPath + 1];
+
+ const char *func_name = "GetModuleFileNameExW";
+ Func_GetModuleFileNameExW my_func = (Func_GetModuleFileNameExW)
+ ::GetProcAddress(::GetModuleHandleA("kernel32.dll"), func_name);
+ if (!my_func)
+ {
+ if (!g_Psapi_dll_module)
+ g_Psapi_dll_module = LoadLibraryW(L"Psapi.dll");
+ if (g_Psapi_dll_module)
+ my_func = (Func_GetModuleFileNameExW)::GetProcAddress(g_Psapi_dll_module, func_name);
+ }
+ if (my_func)
+ {
+ // DWORD num = GetModuleFileNameEx(hProcess, NULL, temp, maxPath);
+ DWORD num = my_func(hProcess, NULL, temp, maxPath);
+ if (num != 0)
+ path = temp;
+ }
+ // FreeLibrary(lib);
+}
+*/
+
+static void My_GetProcessFileName(HANDLE hProcess, UString &path)
+{
+ path.Empty();
+ const unsigned maxPath = 1024;
+ WCHAR temp[maxPath + 1];
+
+ const char *func_name = "GetProcessImageFileNameW";
+ Func_GetProcessImageFileNameW my_func = (Func_GetProcessImageFileNameW)
+ ::GetProcAddress(::GetModuleHandleA("kernel32.dll"), func_name);
+
+ if (!my_func)
+ {
+ if (!g_Psapi_dll_module)
+ g_Psapi_dll_module = LoadLibraryW(L"Psapi.dll");
+ if (g_Psapi_dll_module)
+ my_func = (Func_GetProcessImageFileNameW)::GetProcAddress(g_Psapi_dll_module, func_name);
+ }
+
+ if (my_func)
+ {
+ // DWORD num = GetProcessImageFileNameW(hProcess, temp, maxPath);
+ DWORD num = my_func(hProcess, temp, maxPath);
+ if (num != 0)
+ path = temp;
+ }
+ // FreeLibrary(lib);
+}
+
+struct CSnapshotProcess
+{
+ DWORD Id;
+ DWORD ParentId;
+ UString Name;
+};
+
+static void GetSnapshot(CObjectVector<CSnapshotProcess> &items)
+{
+ items.Clear();
+
+ CProcessSnapshot snapshot;
+ if (!snapshot.Create())
+ return;
+
+ DEBUG_PRINT("snapshot.Create() OK");
+ PROCESSENTRY32 pe;
+ CSnapshotProcess item;
+ memset(&pe, 0, sizeof(pe));
+ pe.dwSize = sizeof(pe);
+ BOOL res = snapshot.GetFirstProcess(&pe);
+ while (res)
+ {
+ item.Id = pe.th32ProcessID;
+ item.ParentId = pe.th32ParentProcessID;
+ item.Name = GetUnicodeString(pe.szExeFile);
+ items.Add(item);
+ res = snapshot.GetNextProcess(&pe);
+ }
+}
+
+#endif
+
class CChildProcesses
{
#ifndef UNDER_CE
CRecordVector<DWORD> _ids;
#endif
+
public:
+ // bool ProgsWereUsed;
CRecordVector<HANDLE> Handles;
CRecordVector<bool> NeedWait;
+ // UStringVector Names;
+
+ #ifndef UNDER_CE
+ UString Path;
+ #endif
+ // CChildProcesses(): ProgsWereUsed(false) {}
~CChildProcesses() { CloseAll(); }
void DisableWait(unsigned index) { NeedWait[index] = false; }
void CloseAll()
{
- FOR_VECTOR (i, Handles)
+ FOR_VECTOR (i, Handles)
{
HANDLE h = Handles[i];
if (h != NULL)
CloseHandle(h);
}
+
Handles.Clear();
NeedWait.Clear();
+ // Names.Clear();
+
+ #ifndef UNDER_CE
+ // Path.Empty();
+ _ids.Clear();
+ #endif
}
- void AddProcess(HANDLE h)
+ void SetMainProcess(HANDLE h)
{
#ifndef UNDER_CE
- GetProcessIdFunc func = (GetProcessIdFunc)::GetProcAddress(::GetModuleHandleA("kernel32.dll"), "GetProcessId");
+
+ Func_GetProcessId func = (Func_GetProcessId)::GetProcAddress(::GetModuleHandleA("kernel32.dll"), "GetProcessId");
if (func)
- _ids.AddToUniqueSorted(func(h));
+ {
+ DWORD id = func(h);
+ if (id != 0)
+ _ids.AddToUniqueSorted(id);
+ }
+
+ My_GetProcessFileName(h, Path);
+ DEBUG_PRINT_W(Path);
+
#endif
+
Handles.Add(h);
NeedWait.Add(true);
}
- void Update()
+ #ifndef UNDER_CE
+
+ void Update(bool needFindProcessByPath /* , const CPossibleProgs &progs */)
{
- #ifndef UNDER_CE
- CRecordVector<DWORD> ids, parents;
+ /*
+ if (_ids.IsEmpty())
+ return;
+ */
+
+ CObjectVector<CSnapshotProcess> sps;
+ GetSnapshot(sps);
+
+ const int separ = Path.ReverseFind_PathSepar();
+ const UString mainName = Path.Ptr(separ + 1);
+ if (mainName.IsEmpty())
+ needFindProcessByPath = false;
+
+ const DWORD currentProcessId = GetCurrentProcessId();
+
+ for (;;)
{
- CProcessSnapshot snapshot;
- if (snapshot.Create())
+ bool wasAdded = false;
+
+ FOR_VECTOR (i, sps)
{
- PROCESSENTRY32 pe;
- memset(&pe, 0, sizeof(pe));
- pe.dwSize = sizeof(pe);
- BOOL res = snapshot.GetFirstProcess(&pe);
- while (res)
+ const CSnapshotProcess &sp = sps[i];
+ const DWORD id = sp.Id;
+
+ if (id == currentProcessId)
+ continue;
+ if (_ids.FindInSorted(id) >= 0)
+ continue;
+
+ bool isSameName = false;
+ const UString &name = sp.Name;
+
+ if (needFindProcessByPath)
+ isSameName = mainName.IsEqualTo_NoCase(name);
+
+ bool needAdd = false;
+ // bool isFromProgs = false;
+
+ if (isSameName || _ids.FindInSorted(sp.ParentId) >= 0)
+ needAdd = true;
+ /*
+ else if (progs.IsFromList(name))
{
- ids.Add(pe.th32ProcessID);
- parents.Add(pe.th32ParentProcessID);
- res = snapshot.GetNextProcess(&pe);
+ needAdd = true;
+ isFromProgs = true;
}
- }
- }
+ */
- for (;;)
- {
- unsigned i;
- for (i = 0; i < ids.Size(); i++)
- {
- DWORD id = ids[i];
- if (_ids.FindInSorted(parents[i]) >= 0 &&
- _ids.FindInSorted(id) < 0)
+ if (needAdd)
{
+ DEBUG_PRINT("----- OpenProcess -----");
+ DEBUG_PRINT_W(name);
HANDLE hProcess = OpenProcess(SYNCHRONIZE, FALSE, id);
if (hProcess)
{
- _ids.AddToUniqueSorted(id);
+ DEBUG_PRINT("----- OpenProcess OK -----");
+ // if (!isFromProgs)
+ _ids.AddToUniqueSorted(id);
Handles.Add(hProcess);
NeedWait.Add(true);
- break;
+ // Names.Add(name);
+ wasAdded = true;
+ // ProgsWereUsed = isFromProgs;
}
}
}
- if (i == ids.Size())
+
+ if (!wasAdded)
break;
}
- #endif
}
+
+ #endif
};
+
struct CTmpProcessInfo: public CTempFileInfo
{
CChildProcesses Processes;
@@ -168,9 +424,12 @@ struct CTmpProcessInfo: public CTempFileInfo
bool UsePassword;
UString Password;
- CTmpProcessInfo(): UsePassword(false) {}
+ bool ReadOnly;
+
+ CTmpProcessInfo(): UsePassword(false), ReadOnly(false) {}
};
+
class CTmpProcessInfoRelease
{
CTmpProcessInfo *_tmpProcessInfo;
@@ -600,6 +859,9 @@ static HRESULT StartApplication(const UString &dir, const UString &path, HWND wi
process.Attach(execInfo.hProcess);
}
+
+ DEBUG_PRINT_NUM("-- ShellExecuteEx -- execInfo.hInstApp = ", result)
+
if (result <= 32)
{
switch (result)
@@ -610,6 +872,8 @@ static HRESULT StartApplication(const UString &dir, const UString &path, HWND wi
// L"There is no application associated with the given file name extension",
L"7-Zip", MB_OK | MB_ICONSTOP);
}
+
+ return E_FAIL; // fixed in 15.13. Can we use it for any Windows version?
}
return S_OK;
@@ -800,6 +1064,8 @@ HRESULT CPanel::OnOpenItemChanged(UInt32 index, const wchar_t *fullFilePath,
LRESULT CPanel::OnOpenItemChanged(LPARAM lParam)
{
+ // DEBUG_PRINT_NUM("OnOpenItemChanged", GetCurrentThreadId());
+
CTmpProcessInfo &tpi = *(CTmpProcessInfo *)lParam;
if (tpi.FullPathFolderPrefix != _currentFolderPrefix)
return 0;
@@ -834,24 +1100,75 @@ LRESULT CPanel::OnOpenItemChanged(LPARAM lParam)
return 1;
}
-class CExitEventLauncher
+
+CExitEventLauncher g_ExitEventLauncher;
+
+void CExitEventLauncher::Exit(bool hardExit)
{
-public:
- NWindows::NSynchronization::CManualResetEvent _exitEvent;
- CExitEventLauncher()
+ if (_needExit)
{
- if (_exitEvent.Create(false) != S_OK)
- throw 9387173;
- };
- ~CExitEventLauncher() { _exitEvent.Set(); }
-} g_ExitEventLauncher;
+ _exitEvent.Set();
+ _needExit = false;
+ }
+
+ if (_numActiveThreads == 0)
+ return;
+
+ FOR_VECTOR (i, _threads)
+ {
+ ::CThread &th = _threads[i];
+ DWORD wait = (hardExit ? 100 : INFINITE);
+ if (Thread_WasCreated(&th))
+ {
+ DWORD waitResult = WaitForSingleObject(th, wait);
+ // Thread_Wait(&th);
+ if (waitResult == WAIT_TIMEOUT)
+ wait = 1;
+ if (!hardExit && waitResult != WAIT_OBJECT_0)
+ continue;
+ Thread_Close(&th);
+ _numActiveThreads--;
+ }
+ }
+}
+
+
static THREAD_FUNC_DECL MyThreadFunction(void *param)
{
+ DEBUG_PRINT("==== MyThreadFunction ====");
+
CMyAutoPtr<CTmpProcessInfo> tmpProcessInfoPtr((CTmpProcessInfo *)param);
CTmpProcessInfo *tpi = tmpProcessInfoPtr.get();
CChildProcesses &processes = tpi->Processes;
+ bool mainProcessWasSet = !processes.Handles.IsEmpty();
+
+ bool isComplexMode = true;
+
+ if (!processes.Handles.IsEmpty())
+ {
+
+ const DWORD startTime = GetTickCount();
+
+ /*
+ CPossibleProgs progs;
+ {
+ const UString &name = tpi->RelPath;
+ int slashPos = name.ReverseFind_PathSepar();
+ int dotPos = name.ReverseFind_Dot();
+ if (dotPos > slashPos)
+ {
+ const UString ext = name.Ptr(dotPos + 1);
+ AString extA = UnicodeStringToMultiByte(ext);
+ extA.MakeLower_Ascii();
+ progs.SetFromExtension(extA);
+ }
+ }
+ */
+
+ bool firstPass = true;
+
for (;;)
{
CRecordVector<HANDLE> handles;
@@ -859,6 +1176,8 @@ static THREAD_FUNC_DECL MyThreadFunction(void *param)
FOR_VECTOR (i, processes.Handles)
{
+ if (handles.Size() > 60)
+ break;
if (processes.NeedWait[i])
{
handles.Add(processes.Handles[i]);
@@ -866,43 +1185,150 @@ static THREAD_FUNC_DECL MyThreadFunction(void *param)
}
}
+ bool needFindProcessByPath = false;
+
if (handles.IsEmpty())
- break;
+ {
+ if (!firstPass)
+ break;
+ }
+ else
+ {
+ handles.Add(g_ExitEventLauncher._exitEvent);
+
+ DWORD waitResult = ::WaitForMultipleObjects(handles.Size(), &handles.Front(), FALSE, INFINITE);
+
+ waitResult -= WAIT_OBJECT_0;
+
+ if (waitResult >= handles.Size() - 1)
+ {
+ processes.CloseAll();
+ /*
+ if (waitResult == handles.Size() - 1)
+ {
+ // exit event
+ // we want to delete temp files, if progs were used
+ if (processes.ProgsWereUsed)
+ break;
+ }
+ */
+ return waitResult >= (DWORD)handles.Size() ? 1 : 0;
+ }
- handles.Add(g_ExitEventLauncher._exitEvent);
+ if (firstPass && indices.Size() == 1)
+ {
+ DWORD curTime = GetTickCount() - startTime;
- DWORD waitResult = ::WaitForMultipleObjects(handles.Size(), &handles.Front(), FALSE, INFINITE);
+ /*
+ if (curTime > 5 * 1000)
+ progs.ProgNames.Clear();
+ */
- if (waitResult >= (DWORD)handles.Size() - 1)
- {
- processes.CloseAll();
- return waitResult >= (DWORD)handles.Size() ? 1 : 0;
+ needFindProcessByPath = (curTime < 2 * 1000);
+
+ if (needFindProcessByPath)
+ {
+ NFind::CFileInfo newFileInfo;
+ if (newFileInfo.Find(tpi->FilePath))
+ if (tpi->WasChanged(newFileInfo))
+ needFindProcessByPath = false;
+ }
+
+ DEBUG_PRINT_NUM(" -- firstPass -- time = ", curTime)
+ }
+
+ processes.DisableWait(indices[waitResult]);
}
- processes.Update();
- processes.DisableWait(indices[waitResult]);
+
+ firstPass = false;
+
+ // Sleep(300);
+ #ifndef UNDER_CE
+ processes.Update(needFindProcessByPath /* , progs */);
+ #endif
}
- NFind::CFileInfo newFileInfo;
- if (newFileInfo.Find(tpi->FilePath))
+
+ DWORD curTime = GetTickCount() - startTime;
+
+ DEBUG_PRINT_NUM("after time = ", curTime)
+
+ processes.CloseAll();
+
+ isComplexMode = (curTime < 2 * 1000);
+
+ }
+
+ bool needCheckTimestamp = true;
+
+ for (;;)
{
- if (tpi->WasChanged(newFileInfo))
+ NFind::CFileInfo newFileInfo;
+
+ if (!newFileInfo.Find(tpi->FilePath))
+ break;
+
+ if (mainProcessWasSet)
{
- UString message = MyFormatNew(IDS_WANT_UPDATE_MODIFIED_FILE, tpi->RelPath);
- if (::MessageBoxW(g_HWND, message, L"7-Zip", MB_OKCANCEL | MB_ICONQUESTION) == IDOK)
+ if (tpi->WasChanged(newFileInfo))
{
- if (SendMessage(tpi->Window, kOpenItemChanged, 0, (LONG_PTR)tpi) != 1)
+ UString m = MyFormatNew(IDS_CANNOT_UPDATE_FILE, fs2us(tpi->FilePath));
+ if (tpi->ReadOnly)
{
- ::MessageBoxW(g_HWND, MyFormatNew(IDS_CANNOT_UPDATE_FILE,
- fs2us(tpi->FilePath)), L"7-Zip", MB_OK | MB_ICONSTOP);
+ m.Add_LF();
+ AddLangString(m, IDS_PROP_READ_ONLY);
+ m.Add_LF();
+ m += tpi->FullPathFolderPrefix;
+ ::MessageBoxW(g_HWND, m, L"7-Zip", MB_OK | MB_ICONSTOP);
return 0;
}
+ {
+ const UString message = MyFormatNew(IDS_WANT_UPDATE_MODIFIED_FILE, tpi->RelPath);
+ if (::MessageBoxW(g_HWND, message, L"7-Zip", MB_OKCANCEL | MB_ICONQUESTION) == IDOK)
+ {
+ // DEBUG_PRINT_NUM("SendMessage", GetCurrentThreadId());
+ if (SendMessage(tpi->Window, kOpenItemChanged, 0, (LONG_PTR)tpi) != 1)
+ {
+ ::MessageBoxW(g_HWND, m, L"7-Zip", MB_OK | MB_ICONSTOP);
+ return 0;
+ }
+ }
+ needCheckTimestamp = false;
+ break;
+ }
}
+
+ if (!isComplexMode)
+ break;
}
+
+ // DEBUG_PRINT("WaitForSingleObject");
+ DWORD waitResult = ::WaitForSingleObject(g_ExitEventLauncher._exitEvent, INFINITE);
+ // DEBUG_PRINT("---");
+
+ if (waitResult == WAIT_OBJECT_0)
+ break;
+
+ return 1;
}
- tpi->DeleteDirAndFile();
+
+ {
+ NFind::CFileInfo newFileInfo;
+
+ bool finded = newFileInfo.Find(tpi->FilePath);
+
+ if (!needCheckTimestamp || !finded || !tpi->WasChanged(newFileInfo))
+ {
+ DEBUG_PRINT("Delete Temp file");
+ tpi->DeleteDirAndFile();
+ }
+ }
+
return 0;
}
+
+
#if defined(_WIN32) && !defined(UNDER_CE)
static const FChar *k_ZoneId_StreamName = FTEXT(":Zone.Identifier");
#endif
@@ -1284,6 +1710,7 @@ void CPanel::OpenItemInArchive(int index, bool tryInternal, bool tryExternal, bo
tpi->NeedDelete = true;
tpi->UsePassword = usePassword;
tpi->Password = password;
+ tpi->ReadOnly = IsThereReadOnlyFolder();
if (!tpi->FileInfo.Find(tempFilePath))
return;
@@ -1291,29 +1718,41 @@ void CPanel::OpenItemInArchive(int index, bool tryInternal, bool tryExternal, bo
CTmpProcessInfoRelease tmpProcessInfoRelease(*tpi);
CProcess process;
- // HRESULT res;
+ HRESULT res;
if (editMode)
- /* res = */ StartEditApplication(fs2us(tempFilePath), useEditor, (HWND)*this, process);
+ res = StartEditApplication(fs2us(tempFilePath), useEditor, (HWND)*this, process);
else
- /* res = */ StartApplication(fs2us(tempDirNorm), fs2us(tempFilePath), (HWND)*this, process);
+ res = StartApplication(fs2us(tempDirNorm), fs2us(tempFilePath), (HWND)*this, process);
- if ((HANDLE)process == 0)
- return;
+ if ((HANDLE)process == NULL)
+ {
+ // win7 / win10 work so for some extensions (pdf, html ..);
+ DEBUG_PRINT("#### (HANDLE)process == 0");
+ // return;
+ if (res != SZ_OK)
+ return;
+ }
tpi->Window = (HWND)(*this);
tpi->FullPathFolderPrefix = _currentFolderPrefix;
tpi->FileIndex = index;
tpi->RelPath = relPath;
- tpi->Processes.AddProcess(process.Detach());
+
+ if ((HANDLE)process != 0)
+ tpi->Processes.SetMainProcess(process.Detach());
- NWindows::CThread thread;
- if (thread.Create(MyThreadFunction, tpi) != S_OK)
+ ::CThread th;
+ if (Thread_Create(&th, MyThreadFunction, tpi) != 0)
throw 271824;
+ g_ExitEventLauncher._threads.Add(th);
+ g_ExitEventLauncher._numActiveThreads++;
+
tempDirectory.DisableDeleting();
tmpProcessInfoPtr.release();
tmpProcessInfoRelease._needDelete = false;
}
+
/*
static const UINT64 kTimeLimit = UINT64(10000000) * 3600 * 24;