找出Windows服务的运行进程名称.NET 1.1

时间:2009-02-19 14:53:32

标签: c# windows-services process .net-1.1

我们正在使用写得很糟糕的Windows服务,当我们尝试从代码中阻止它时,它会挂起。因此,我们需要找到与该服务相关的进程并将其终止。 有什么建议吗?

6 个答案:

答案 0 :(得分:12)

您可以使用System.Management.MangementObjectSearcher获取服务的进程ID,并使用System.Diagnostics.Process获取相应的Process实例并将其删除。

以下程序中的KillService()方法显示了如何执行此操作:

using System;
using System.ComponentModel;
using System.Diagnostics;
using System.Management;

namespace KillProcessApp {
    class Program {
        static void Main(string[] args) {
            KillService("YourServiceName");
        }

        static void KillService(string serviceName) {
            string query = string.Format(
                "SELECT ProcessId FROM Win32_Service WHERE Name='{0}'", 
                serviceName);
            ManagementObjectSearcher searcher = 
                new ManagementObjectSearcher(query);
            foreach (ManagementObject obj in searcher.Get()) {
                uint processId = (uint) obj["ProcessId"];
                Process process = null;
                try
                {
                    process = Process.GetProcessById((int)processId);
                }
                catch (ArgumentException)
                {
                    // Thrown if the process specified by processId
                    // is no longer running.
                }
                try
                {
                    if (process != null) 
                    {
                        process.Kill();
                    }
                }
                catch (Win32Exception)
                {
                    // Thrown if process is already terminating,
                    // the process is a Win16 exe or the process
                    // could not be terminated.
                }
                catch (InvalidOperationException)
                {
                    // Thrown if the process has already terminated.
                }
            }
        }
    }
}

答案 1 :(得分:5)

WMI具有以下信息:Win32_Service类。

这样的WQL查询
SELECT ProcessId FROM Win32_Service WHERE Name='MyServiceName'

使用System.Management应该可以解决问题。

快速查看:taskllist.exe /svc以及命令行中的其他工具。

答案 2 :(得分:4)

您可以使用

tasklist /svc /fi "SERVICES eq YourServiceName"

查找进程名称和ID,以及同一进程是否托管其他服务。

答案 3 :(得分:1)

要完全回答我的问题 - 如何查找与某项服务相关的流程:

ManagementObjectSearcher searcher = new ManagementObjectSearcher
  ("SELECT * FROM Win32_Service WHERE DisplayName = '" + serviceName + "'");

foreach( ManagementObject result in searcher.Get() )
{
  if (result["DisplayName"].ToString().ToLower().Equals(serviceName.ToLower()))
  {
    int iPID = Convert.ToInt32( result["ProcessId"] );
    KillProcessByID(iPID, 1000); //some method that will kill Process for given PID and timeout. this should be trivial
  }
}

}

答案 4 :(得分:0)

Microsoft / SysInternals有一个名为PsKill的命令行工具,允许您按名称终止进程。此工具还允许您终止其他服务器上的进程。 Windows SysInternals

  

用法:pskill [-t] [\ computer [-u username [-p password]]]<进程ID |名称>
    -t杀死进程及其后代     -u指定登录到远程计算机的可选用户名     -p指定用户名的可选密码。如果省略此项,系统将提示您输入隐藏密码。

答案 5 :(得分:0)

我想这是一个两步过程 - 如果它始终是相同的服务,您可以使用其他答案中建议的方法轻松找到过程名称。

然后,我在.NET 1.1 Web服务器上的类中有以下代码:

Process[] runningProcs = 
          Process.GetProcessesByName("ProcessName");

foreach (Process runningProc in runningProcs)
{
    // NOTE: Kill only works for local processes
    runningProc.Kill();
}

Kill method可以抛出一些你应该考虑捕获的异常 - 尤其是Win32Exception,如果进程无法被杀死则抛出。

请注意,WaitForExit methodHasExited property也存在于1.1世界中,但在杀戮1.1的文档页面中未提及。