由 Process Start 启动的进程的进程 ID

Process ID of process Started by Process Start

我正在尝试通过进程启动时保存的进程 ID 终止进程。但是当我试图从后面的代码中终止进程时,我正在捕获的进程 ID 不存在。

下面是启动进程并捕获进程 ID 的代码。

private List<int> pids = new List<int>();
public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            pids.Clear();
            Process myprocess= new Process();

            myprocess.StartInfo.FileName = Environment.ExpandEnvironmentVariables(@"%SystemRoot%\system32\cmdkey.exe");
            myprocess.StartInfo.Arguments = "C:\rdp\RemoteIn.rdp";
            myprocess.Start();
            pids.Add(myprocess.Id);          
        }

        private void terminateAll()
        {
            //foreach (var p in pids) p.Kill();

            foreach (var i in pids)
            {
                Process p = Process.GetProcessById(i);
                p.Kill();

            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            terminateAll();
        }

当我单击按钮终止进程时,它显示以下错误。

有什么办法可以解决这个问题。

使用 Palani Kumar 代码后,我遇到以下异常。

表格看起来像这样

我不知道为什么你在按钮点击事件中被声明为 List<int> 并清除列表 (pids.Clear();)。无论如何,下面的内容也适用于创建多个进程。

编辑: 到目前为止与 Amrit 讨论过。 Windows 8 为连接相同域的 mstsc 创建子进程。所以我稍微修改了我的代码。

    private void button1_Click(object sender, EventArgs e)
    {
        //pids.Clear();
        Process myprocess = new Process();

        myprocess.StartInfo.FileName = Environment.ExpandEnvironmentVariables(@"%SystemRoot%\syswow64\mstsc.exe");
        myprocess.StartInfo.Arguments = "C:\rdp\RemoteIn.rdp";
        myprocess.Start();
        Thread.Sleep(100);
        /* Edit */
        Process proc = Process.GetProcessesByName("mstsc").FirstOrDefault(x => !pids.Any(y => y == x.Id));
        if(proc != null)
        {
           pids.Add(proc.Id);
        }
    }

    private void terminateAll()
    {
        foreach (var i in pids)
        {
            try
            {
                Process p = Process.GetProcessById(i);
                p.Kill();
            }
            catch (Exception ex)
            {
                //throw exception if we close the mstsc manually
            }
        }
    }

我不确定你为什么持有

private List<int> pids = new List<int>();

而不是直接使用Process的列表

private List<Process> processes = new List<Process>();

了解 Process 对象具有安全描述符这一点很重要。每个人都可以看到进程的存在,有人可以打开进程阅读信息或等待进程结束。开杀需要更多权限。 CreateProcess 返回的进程句柄具有完全权限。因此,持有用于创建流程的 Process 对象可为您带来这样的优势。

我建议您在调用 Kill() 方法之前另外测试 Process 对象的 HasExited 属性。如果进程将被用户关闭,可以考虑额外使用 OnExited(参见 here)来删除该进程。在从 processes 列表中删除之前,您应该以任何方式调用 Process 对象的 Close() 方法,并考虑使用 CloseMainWindow() 而不是 Kill() 方法。您应该只测试这两种方法(CloseMainWindow()Kill())并选择最适合您的方法。