Цитата R.i.m.s.k.y.:
значение параметра HungAppTimeout »
|
вероятнее всего это 5000 миллисекунд = 5 секунд, ваш Кэп.
==========================================================
El Sanchez, Ты можешь пожалуйста научить свою функцию так чтоб она ещё и путь к файлу сравнивала как у меня, ну короче чтоб при необходимости только определённые процессы завершать.
(а то получается грохнули одного Васю, другого, а фамилию не спросили)
Я боюсь это делать, тк когда свою функцию ваял мне показали 2 раза синий экран, и сейчс ещё раз когда твою функцию дополнял
Цитата El Sanchez:
TerminateProcess стоит применять в крайнем случае, когда другие способы завершения процесса не помогают »
|
не знал, но ради интереса поискал другие более гуманные способы, других не нашёл. Ну кроме закрытия окна программы:
Цитата El Sanchez:
Нужно послать окну программы сообщение WM_CLOSE »
|
гуманных не нашёл, но наткнулся на более зверский:
http://www.delphisources.ru/forum/sh...ad.php?t=21276
хотя там тоже TerminateProcess, но уже для системных процессов, путём поднятия привилегий текущему процессу, как я понимаю
пртировал, не тестил (боюсь)
читать дальше »
Код:

[Setup]
AppName=My Program
AppVerName=My Program v.1.2
DefaultDirName={pf}\My Program
[noparse][code][/npparse]
#ifdef UNICODE
#define A "W"
#else
#define A "A"
#endif
const
TOKEN_ADJUST_PRIVILEGES = $32;
TOKEN_QUERY = $8;
SE_PRIVILEGE_ENABLED = $2;
ERROR_SUCCESS = 0;
TH32CS_SNAPPROCESS = $2;
INVALID_HANDLE_VALUE = -1;
WM_CLOSE = $10;
WAIT_OBJECT_0 = $0;
TA_FAILED = 0;
SYNCHRONIZE = $100000;
PROCESS_TERMINATE = $1;
MAX_PATH = 260;
type
_ULARGE_INTEGER = record
LowPart: DWORD;
HighPart: DWORD;
end;
_LUID_AND_ATTRIBUTES = record
Luid: _ULARGE_INTEGER;
Attributes: DWORD;
end;
_TOKEN_PRIVILEGES = record
PrivilegeCount: DWORD;
Privileges: array[0..0] of _LUID_AND_ATTRIBUTES;
end;
TPROCESSENTRY32 = record
dwSize, cntUsage, th32ProcessID: DWORD;
th32DefaultHeapID: Longint;
th32ModuleID, cntThreads, th32ParentProcessID: DWORD;
pcPriClassBase: Longint;
dwFlags: DWORD;
szExeFile: array [0..MAX_PATH-1] of Char;
end;
function CreateToolhelp32Snapshot(dwFlags, th32ProcessID: DWORD): THandle; external 'CreateToolhelp32Snapshot@kernel32.dll stdcall';
function Process32First(hSnapshot: THandle; var lppe: TPROCESSENTRY32): Boolean; external 'Process32First@kernel32.dll stdcall';
function Process32Next(hSnapshot: THandle; var lppe: TPROCESSENTRY32): Boolean; external 'Process32Next@kernel32.dll stdcall';
function OpenProcessToken(ProcessHandle: THandle; DesiredAccess: DWORD; var TokenHandle: THandle): BOOL; external 'OpenProcessToken@advapi32.dll stdcall';
function GetCurrentProcess: THandle; external 'GetCurrentProcess@kernel32.dll stdcall';
function LookupPrivilegeValue(lpSystemName, lpName: String; var lpLuid: _ULARGE_INTEGER): BOOL; external 'LookupPrivilegeValue{#A}@advapi32.dll stdcall';
function AdjustTokenPrivileges(TokenHandle: THandle; DisableAllPrivileges: BOOL; const NewState: _TOKEN_PRIVILEGES; BufferLength: DWORD; var PreviousState: _TOKEN_PRIVILEGES; var ReturnLength: DWORD): BOOL; external 'AdjustTokenPrivileges@advapi32.dll stdcall';
function TerminateProcess(hProcess: THandle; uExitCode: UINT): BOOL; external 'TerminateProcess@kernel32.dll stdcall';
function OpenProcess(dwDesiredAccess: DWORD; bInheritHandle: BOOL; dwProcessId: DWORD): THandle; external 'OpenProcess@kernel32.dll stdcall';
function CloseHandle(hObject: THandle): BOOL; external 'CloseHandle@kernel32.dll stdcall';
function GetLastError: DWORD; external 'GetLastError@kernel32.dll stdcall';
function GetWindowThreadProcessId(hWnd: HWND; var lpdwProcessId: DWORD): DWORD; external 'GetWindowThreadProcessId@user32.dll stdcall';
function EnumWindows(lpEnumFunc, lParam: Longint): BOOL; external 'EnumWindows@user32.dll stdcall';
function WaitForSingleObject(hHandle: THandle; dwMilliseconds: DWORD): DWORD; external 'WaitForSingleObject@kernel32.dll stdcall';
function CharArrayToString(aChar: array of Char): String;
begin
Result := '';
while aChar[Length(Result)] <> #0 do Insert(aChar[Length(Result)], Result, Length(Result)+1);
end;
function EnumWindowsProc(hwnd: HWND; lParam: Longint): BOOL;
var
dwID: DWORD;
begin
GetWindowThreadProcessId(hwnd, dwID) ;
if dwID = lParam then PostMessage(hwnd, WM_CLOSE, 0, 0);
Result := True;
end;
function ProcessTerminate(const ProcessName: String; dwTimeout: DWORD):Boolean;
var
hToken: THandle;
SeDebugNameValue: _ULARGE_INTEGER;
tkp: _TOKEN_PRIVILEGES;
ReturnLength: Cardinal;
hProcess: THandle;
pe32: TPROCESSENTRY32;
hProcessSnap: THandle;
begin
Result := False;
// Добавляем привилегию SeDebugPrivilege
// Для начала получаем токен нашего процесса
if not OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES or TOKEN_QUERY, hToken) then Exit;
// Получаем LUID привилегии
if not LookupPrivilegeValue('', 'SeDebugPrivilege', SeDebugNameValue) then
begin
CloseHandle(hToken);
Exit;
end;
tkp.PrivilegeCount := 1;
tkp.Privileges[0].Luid := SeDebugNameValue;
tkp.Privileges[0].Attributes := SE_PRIVILEGE_ENABLED;
// Добавляем привилегию к нашему процессу
AdjustTokenPrivileges(hToken, False, tkp, SizeOf(tkp), tkp, ReturnLength);
if GetLastError() <> ERROR_SUCCESS then exit;
// Завершаем процесс. Если у нас есть SeDebugPrivilege, то мы можем
// завершить и системный процесс
// Получаем дескриптор процесса для его завершения
hProcessSnap := CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
if hProcessSnap = INVALID_HANDLE_VALUE then Exit;
try
pe32.dwSize := SizeOf(pe32);
if not Process32First(hProcessSnap, pe32) then Exit;
while Process32Next(hProcessSnap, pe32) do
begin
if CompareText(CharArrayToString(pe32.szExeFile), ProcessName) = 0 then
begin
hProcess := OpenProcess(SYNCHRONIZE or PROCESS_TERMINATE, False, pe32.th32ProcessID);
if hProcess = TA_FAILED then Exit;
try
Result := WaitForSingleObject(hProcess, dwTimeout) = WAIT_OBJECT_0;
if not Result then Result := TerminateProcess(hProcess, 0);
finally
CloseHandle(hProcess);
end;
end;
end;
finally
CloseHandle(hProcessSnap);
end;
// Удаляем привилегию
tkp.Privileges[0].Attributes := 0;
AdjustTokenPrivileges(hToken, FALSE, tkp, SizeOf(tkp), tkp, ReturnLength);
if GetLastError() <> ERROR_SUCCESS then Exit;
Result := True;
end;
procedure InitializeWizard();
begin
ProcessTerminate('calc.exe', 5000);
end;
PS: Халфе 2 в полноэкранном режиме на сообщение PostMessage(hwnd, WM_CLOSE, 0, 0); пофиг, (поставлю dwTimeout в 2 раза меньше)
но в оконном режиме, закрытие окна работает на ура