Solved

Kill Task like Task Mgr

Posted on 2015-01-14
5
144 Views
Last Modified: 2015-02-01
I want my Uninstall.exe (running with admin rights) to Terminate my Application that was installed and is running with Std User Rights.
Whereas this works in OS above win XP it fails on Win XP.

function Tform_Main.KillTask(ExeFileName: string): integer;
const
  PROCESS_TERMINATE=$0001;
var
  ContinueLoop: BOOL;
  FSnapshotHandle,ProcessHandl: THandle;
  FProcessEntry32: TProcessEntry32;
begin
  result := 0;
  FSnapshotHandle := CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
  FProcessEntry32.dwSize := Sizeof(FProcessEntry32);
  ContinueLoop := Process32First(FSnapshotHandle, FProcessEntry32);
  while integer(ContinueLoop) <> 0 do
  begin
    if ((UpperCase(ExtractFileName(FProcessEntry32.szExeFile)) = UpperCase(ExeFileName)) or
       (UpperCase(FProcessEntry32.szExeFile) = UpperCase(ExeFileName))) then
    begin
      ProcessHandl:=OpenProcess(PROCESS_TERMINATE,BOOL(0),FProcessEntry32.th32ProcessID) ;
      Result := Integer(TerminateProcess(ProcessHandl, 0));
      CloseHandle(ProcessHandl);
    end;
    ContinueLoop := Process32Next(FSnapshotHandle, FProcessEntry32);
  end;
  CloseHandle(FSnapshotHandle);
end;

Open in new window

0
Comment
Question by:Allan_Fernandes
  • 3
  • 2
5 Comments
 
LVL 26

Expert Comment

by:Sinisa Vuk
ID: 40549914
- first you must find process id using EnumProcesses and compare started process module name with your exe file:

function FindExeProcess(sExe: String): Cardinal;
var
  PIDArray: array [0..1023] of DWORD;
  cb: DWORD;
  i, ProcCount: Integer;
  hMod: HMODULE;
  hProcess: THandle;
  ModuleName: array [0..300] of Char;
begin
  Result := 0;
  sExe := UpperCase(sExe);
  EnumProcesses(@PIDArray, SizeOf(PIDArray), cb); //get all process list
  ProcCount := cb div SizeOf(DWORD);
  
  for i := 0 to ProcCount - 1 do
  begin
    hProcess := OpenProcess(PROCESS_QUERY_INFORMATION or PROCESS_VM_READ, False, PIDArray[i]);
    if (hProcess <> 0) then
    begin
      EnumProcessModules(hProcess, @hMod, SizeOf(hMod), cb);
      GetModuleFilenameEx(hProcess, hMod, ModuleName, SizeOf(ModuleName));
      if UpperCase(ModuleName) = sExe then
      begin
        Result := PIDArray[i];
      end;
      CloseHandle(hProcess);
      if Result > 0 then Break; //found it
    end;
  end;
end;

Open in new window


... and kill process by process id:
procedure KillProcess(hProcessID: Cardinal);
Var
  hProcess : THandle;
  ovExitCode : LongWord;
begin
  try
    if hProcessID<>0 then
    begin
      hProcess:=OpenProcess(PROCESS_TERMINATE, True, hProcessID);
      if hProcess<>0 then
      begin
        GetExitCodeProcess(hProcess, ovExitCode);
        TerminateProcess(hProcess, ovExitCode);
        CloseHandle(hProcess);
      end;
    end;
  except
  end;
end;

procedure TForm1.Button6Click(Sender: TObject);
var
  hPid: Cardinal;
begin
  hPid := FindExeProcess('C:\Program Files (x86)\Foxit Software\Foxit Reader\Foxit Reader.exe');
  if hPid > 0 then
    KillProcess(hPid);
end;

Open in new window

0
 

Author Comment

by:Allan_Fernandes
ID: 40553031
The code you have given works only within the User
0
 
LVL 26

Expert Comment

by:Sinisa Vuk
ID: 40553405
check if function FindExeProcess get valid Pid (>0) for different user. Is running exe 64 bit? or 32bit?
try change:
const
  PROCESS_QUERY_LIMITED_INFORMATION = $1000;
...
hProcess := OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, False, PIDArray[i]);
...

Open in new window

0
 

Author Comment

by:Allan_Fernandes
ID: 40554996
Sorry that does not help either.
0
 
LVL 26

Accepted Solution

by:
Sinisa Vuk earned 500 total points
ID: 40556625
Ok. You can try WMI.
Ref: WMI and Win32_Process class

function FindExeProcess2(sExe: String): Cardinal;
const
  wbemFlagForwardOnly = $00000020;
var
  FSWbemLocator, FWMIService, FWbemObjectSet, FWbemObject: OLEVariant;
  oEnum : IEnumvariant;
  iValue : LongWord;
  PathStr, ModuleName: String;
begin;
  Result := 0;
  sExe := UpperCase(sExe);
  
  FSWbemLocator := CreateOleObject('WbemScripting.SWbemLocator');
  FWMIService := FSWbemLocator.ConnectServer('localhost', 'root\CIMV2', '', '');
  FWbemObjectSet:= FWMIService.ExecQuery('SELECT * FROM Win32_Process','WQL',wbemFlagForwardOnly);
  oEnum := IUnknown(FWbemObjectSet._NewEnum) as IEnumVariant;
  while oEnum.Next(1, FWbemObject, iValue) = 0 do
  begin
    PathStr := '';
    if not VarIsNull(FWbemObject.ExecutablePath) then
      PathStr := FWbemObject.ExecutablePath;
    ModuleName := IncludeTrailingPathDelimiter(PathStr) + FWbemObject.Name;

    if UpperCase(ModuleName) = sExe then
    begin
      Result := FWbemObject.ProcessId; //keep pid
    end;
    FWbemObject:=Unassigned;
    if Result > 0 then Break;
  end;
end;

procedure KillProcess2(hProcessID: Cardinal);
const
  wbemFlagForwardOnly = $00000020;
var
  FSWbemLocator, FWMIService, FWbemObjectSet, FWbemObject: OLEVariant;
  oEnum : IEnumvariant;
  iValue : LongWord;
  PathStr, ModuleName: String;
begin;
  FSWbemLocator := CreateOleObject('WbemScripting.SWbemLocator');
  FWMIService := FSWbemLocator.ConnectServer('localhost', 'root\CIMV2', '', '');
  FWbemObjectSet:= FWMIService.ExecQuery('SELECT * FROM Win32_Process','WQL',wbemFlagForwardOnly);
  oEnum := IUnknown(FWbemObjectSet._NewEnum) as IEnumVariant;
  while oEnum.Next(1, FWbemObject, iValue) = 0 do
  begin
    if FWbemObject.ProcessId = hProcessID then
    begin
      FWbemObject.Terminate();
      FWbemObject:=Unassigned;
      Break;
    end;
  end;
end;

Open in new window


this works for me - as admin user
more useful samples here:
https://theroadtodelphi.wordpress.com/page/12
0

Featured Post

Gigs: Get Your Project Delivered by an Expert

Select from freelancers specializing in everything from database administration to programming, who have proven themselves as experts in their field. Hire the best, collaborate easily, pay securely and get projects done right.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
domain controllers numbers 4 72
list all GPO's per container/OU 3 68
Delphi: sending SMS on android platform 1 17
Windows Password recovery 7 34
The use of stolen credentials is a hot commodity this year allowing threat actors to move laterally within the network in order to avoid breach detection.
This is an article about Leadership and accepting and adapting to new challenges. It focuses mostly on upgrading to Windows 10.
With the advent of Windows 10, Microsoft is pushing a Get Windows 10 icon into the notification area (system tray) of qualifying computers. There are many reasons for wanting to remove this icon. This two-part Experts Exchange video Micro Tutorial s…
Windows 10 is mostly good. However the one thing that annoys me is how many clicks you have to do to dial a VPN connection. You have to go to settings from the start menu, (2 clicks), Network and Internet (1 click), Click VPN (another click) then fi…

813 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

11 Experts available now in Live!

Get 1:1 Help Now