产卵过程持有套接字端口。如何防止它这样做?

时间:2012-10-19 13:25:22

标签: c# sockets

为了简单起见,我正在编写一个调用“APPLICATION A”的程序,它打开了一个到本地主机上的端口8881的套接字连接;之后它使用代码打击产生了一个exe应用程序调用“APPLICATION B”:

        try
        {
            XmSam.Log("Spawning (" + process + ")");

            ProcessEx proc = new ProcessEx();

            proc.StartInfo.FileName = AppDomain.CurrentDomain.BaseDirectory + process + ".exe";
            proc.StartInfo.Arguments = parameters;
            proc.StartInfo.UseShellExecute = false;
            proc.Start();

            Program.Processes.Add(proc);

            XmSam.Log("Spawned " + proc.ProcessName);
        }
        catch (Exception ex)
        {
            XmSam.Log(ex);
        }

当我关闭APPLICATION A时(通过停止应用程序或在窗口任务管理器中终止其进程),APPLICATION B仍然运行,这很好。但是,当我再次启动APPLICATION A时,我得到了例外:

2012-10-18 16:21:23 - Only one usage of each socket address (protocol/network address/port) is normally permitted
2012-10-18 16:21:23 -    at System.Net.Sockets.Socket.DoBind(EndPoint endPointSnapshot, SocketAddress socketAddress)

当APPLICATION A试图打开套接字到端口8881时发生了这个错误。如果我杀死APPLICATION B,这个错误就会消失。我不认为这是因为APPLICATION B代码,因为它没有任何代码如下面的代码所示:

    [STAThread]
    static void Main()
    {
        while (true)
        {
        }
    }

我试着在Process类下查看MSDN,但我没有看到任何相关内容。我假设当你生成一个进程时,该进程独立于调用应用程序,但显然情况并非如此。你知道任何让我在不调用调用应用程序的情况下生成进程的设置吗?

我知道另一种方法是在APPLICATION A中使用代码来杀死APPLICATION B,但这不是理想的解决方案,特别是在APPLICATION A意外崩溃的情况下。

谢谢。

2 个答案:

答案 0 :(得分:0)

应该确保应用程序A在关闭时关闭套接字。我认为Application.ApplicationExit Event是一个很好的地方,或者当你完成套接字时。

答案 1 :(得分:0)

经过多次挖掘后,我找到了答案。我觉得这很棒article

其中,该问题的主要解释如下:

  

System.Diagnostics.Process.Start使子进程从父进程继承句柄。这意味着,无论您生成什么进程(例如Internet Explorer),该进程都会获取您的进程拥有的所有句柄!因此,即使你在进程中释放句柄,如果你生成的进程仍在运行,你的句柄也不会被释放,因为子进程可能正在使用它们。

因此,考虑到这一点,我所要做的就是将UseShellExecute标志更新为true。

proc.StartInfo.UseShellExecute = true;