1

我在 .NET C# 中遇到问题,多线程套接字应用程序。

随机一段时间后,连接被接受而不执行回调函数并且不会开始接受。

监听器和回调函数的代码如下所示。

    public void StartListening()
    {
        // Data buffer for incoming data.
        byte[] bytes = new Byte[1024];

        // Establish the local endpoint for the socket.
        // The DNS name of the computer
        // running the listener is "host.contoso.com".
        IPEndPoint localEndPoint = new IPEndPoint(IPAddress.Any, listenPort);//Listen on all available network interfaces

        // Create a TCP/IP socket.
        Socket listener = new Socket(AddressFamily.InterNetwork,
            SocketType.Stream, ProtocolType.Tcp);

        // Bind the socket to the local endpoint and listen for incoming connections.
        bool signal = true;
        try
        {
            listener.Bind(localEndPoint);       
            listener.Listen(listenPort);

            while (startlisten)
            {
                // Set the event to nonsignaled state.
                allDone.Reset();
                if (signal)
                {
                    // Start an asynchronous socket to listen for connections.
                    string s = string.Format("Server Socket: Waiting for a connection at Port:{0}", listenPort);
                    DisplayMsg(s);
                    listener.BeginAccept(
                        new AsyncCallback(AcceptCallback),
                        listener);
                }
                // Wait until a connection is made before continuing.
                signal = allDone.WaitOne(100);
            }
            listener.Close();
        }
        catch (Exception e)
        {
            if (e is System.Net.Sockets.SocketException)
            {
                SocketException socex = (e as SocketException);

                throw new Exception(socex.Message);
            }
            else
            {
                throw new Exception(e.Message);
            }
        }
    }

    public void AcceptCallback(IAsyncResult ar)
    {
        // Signal the main thread to continue.

        try
        {
            if (startlisten)
            {
                // Get the socket that handles the client request.
                Socket listener = (Socket)ar.AsyncState;

                TCPClient tcp = frm.GetClientObj();
                tcp.socketForServer = listener.EndAccept(ar);

                DisplayErrorMsg("Connection Request From: " + tcp.socketForServer.RemoteEndPoint.ToString());

                tcp.Connected = true;
                tcp.ReceiveData();

                // Create the state object.
                //                StateObject state = new StateObject();
                //                state.workSocket = handler;
                //                handler.BeginReceive(state.buffer, 0, StateObject.BufferSize, 0,
                //                    new AsyncCallback(ReadCallback), state);
            }
        }
        catch (Exception e)
        {
            if (e is System.Net.Sockets.SocketException)
            {
                SocketException socex = (e as SocketException);

                DisplayErrorMsg(socex.Message);
            }
            else
            {
                DisplayErrorMsg(e.Message);
            }
        }
        allDone.Set();

    }
4

2 回答 2

1

如果您在 EndAccept 之前关闭侦听套接字,则会发生这种情况

“要取消对 BeginAccept 方法的挂起调用,请关闭 Socket。当在异步操作进行时调用 Close 方法时,将调用提供给 BeginAccept 方法的回调。对 EndAccept 方法的后续调用将抛出 ObjectDisposedException表示操作已被取消。”

http://msdn.microsoft.com/en-us/library/5bb431f9.aspx

于 2013-07-26T13:27:47.420 回答
0

我找到了答案,它与allDone事件有关,应该在 if 循环中发出信号。

if (signal)
{
    allDone.Reset();
    // Start an asynchronous socket to listen for connections.
    string s = string.Format("Server Socket: Waiting for a connection at Port:{0}", listenPort);
    DisplayMsg(s);
    listener.BeginAccept(new AsyncCallback(AcceptCallback), listener);
}

// Wait until a connection is made before continuing.
signal = allDone.WaitOne(100);
于 2016-07-13T13:53:52.277 回答