Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Process.Kill() doesn't seem to kill the process

Tags:

I am having trouble using Process.Kill(). I think I must be misunderstanding how it works. This is my test function. I start a long-running process (ping -t) and then kill it five seconds later.

I can see the ping process show up, but the process is still there after my program finishes. I have to kill it manually.

Console.WriteLine("Total number of ping processes is {0}", Process.GetProcessesByName("ping").Length);  ProcessStartInfo startInfo = new ProcessStartInfo("cmd.exe"); Process process = new Process();  startInfo.CreateNoWindow = true; startInfo.UseShellExecute = false; startInfo.Arguments = "/c ping -t 8.8.8.8";  Console.WriteLine("Staring ping process"); process.StartInfo = startInfo; process.Start(); Thread.Sleep(5000);  Console.WriteLine("Total number of ping processes is {0}", Process.GetProcessesByName("ping").Length); Thread.Sleep(5000);  Console.WriteLine("Killing ping process"); process.Kill(); Thread.Sleep(5000);  Console.WriteLine("Total number of ping processes is {0}", Process.GetProcessesByName("ping").Length); 

What am I doing wrong here?

like image 214
Kris Harper Avatar asked May 15 '15 00:05

Kris Harper


People also ask

Does kill actually kill the process?

Description. The kill command sends a signal (by default, the SIGTERM signal) to a running process. This default action normally stops processes.

Does killing a process kill all threads?

When you kill process, everything that process owns, including threads is also killed. The Terminated property is irrelevant. The system just kills everything.


2 Answers

You started cmd.exe, then cmd.exe starts child process ping.exe. To kill ping.exe you can kill all process hierarchy. For example with WMI(add System.Management reference):

private static void KillProcessAndChildrens(int pid) {     ManagementObjectSearcher processSearcher = new ManagementObjectSearcher       ("Select * From Win32_Process Where ParentProcessID=" + pid);     ManagementObjectCollection processCollection = processSearcher.Get();      try     {         Process proc = Process.GetProcessById(pid);         if (!proc.HasExited) proc.Kill();     }     catch (ArgumentException)     {         // Process already exited.     }      if (processCollection != null)     {         foreach (ManagementObject mo in processCollection)         {             KillProcessAndChildrens(Convert.ToInt32(mo["ProcessID"])); //kill child processes(also kills childrens of childrens etc.)         }     } } 
like image 108
SulNR Avatar answered Nov 04 '22 00:11

SulNR


This is a patch for the @SulNR answer since its answer leak child processes of child processes.

private static void KillProcessAndChildrens(int pid) {     ManagementObjectSearcher processSearcher = new ManagementObjectSearcher       ("Select * From Win32_Process Where ParentProcessID=" + pid);     ManagementObjectCollection processCollection = processSearcher.Get();      // We must kill child processes first!     if (processCollection != null)     {         foreach (ManagementObject mo in processCollection)         {             KillProcessAndChildrens(Convert.ToInt32(mo["ProcessID"])); //kill child processes(also kills childrens of childrens etc.)         }     }      // Then kill parents.     try     {         Process proc = Process.GetProcessById(pid);         if (!proc.HasExited) proc.Kill();     }     catch (ArgumentException)     {         // Process already exited.     } } 
like image 24
Julio Avatar answered Nov 03 '22 23:11

Julio