简体   繁体   English

多个客户端的异步TCP服务器

[英]Async TCP Server for multiple Clients

I've got an TCP Server that listens asynchronously for incoming connections. 我有一个TCP服务器,它异步侦听传入的连接。 Everything works fine if just one client is connected. 如果仅连接一个客户端,则一切正常。 But if there are two or more connections, the Server doesn't get the first message. 但是,如果有两个或多个连接,则服务器不会收到第一条消息。 When i debug the ReceiveCallback function i can see that the Server gets the length of the message but not the data. 当我调试ReceiveCallback函数时,我可以看到服务器获取的是消息的长度,而不是数据的长度。 Ie if I connect two clients and try to send the first message: "hello", the server gets: received = 5; 即如果我连接两个客户端并尝试发送第一条消息:“ hello”,则服务器将收到:received = 5; buffer= /0/0/0/0/0, so nothing is displayed. 缓冲区= / 0/0/0/0/0,因此什么也不显示。 In the second message of the same client, the server gets the data. 在同一客户端的第二条消息中,服务器获取数据。

that's how my server looks like: 这就是我的服务器的样子:

        private void StartServer()
    {
        try
        {
            serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            serverSocket.Bind(new IPEndPoint(IPAddress.Any, 3333));
            serverSocket.Listen(100);
            serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);   

        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
    }


     private void AcceptCallback(IAsyncResult ar)
    {
        try
        {
            Socket clientSocket = serverSocket.EndAccept(ar); 
            clientSocketList.Add(clientSocket);
            AppendToTextBox("ClientConnected");
            clientSocket.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(ReceiveCallback), clientSocket);
            serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);

        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
    }


        private void ReceiveCallback(IAsyncResult ar)
    {
        try
        {
            int received = 0;
            Socket current = (Socket)ar.AsyncState;
            received = current.EndReceive(ar);
            byte[] data = new byte[received];

            if (received == 0)
            {
                return;
            }

            Array.Copy(buffer, data, received);
            string text = Encoding.ASCII.GetString(data);

            AppendToTextBox(text);
            buffer = null;
            Array.Resize(ref buffer, current.ReceiveBufferSize);

            current.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(ReceiveCallback), current);
        }
        catch (Exception ex)
        {
            MessageBox.Show(ex.Message, Application.ProductName, MessageBoxButtons.OK, MessageBoxIcon.Error);
        }
    }

See the example at http://msdn.microsoft.com/en-us/library/dxkwh6zw.aspx 请参阅以下示例: http://msdn.microsoft.com/zh-cn/library/dxkwh6zw.aspx

You want to change your code so that it allocates a new buffer each time you call BeginReceive : 您想要更改代码,以便每次调用BeginReceive时它都分配一个新的缓冲区:

        Socket clientSocket = serverSocket.EndAccept(ar); 
        clientSocketList.Add(clientSocket);
        AppendToTextBox("ClientConnected");
        var buffer = new byte[BUFFER_LENGTH];  // <---
        clientSocket.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(ReceiveCallback), clientSocket);
        serverSocket.BeginAccept(new AsyncCallback(AcceptCallback), null);

You must have one buffer per client. 每个客户端必须有一个缓冲区。 Otherwise, one client can overwrite the buffer used by the other client. 否则,一个客户端可以覆盖另一客户端使用的缓冲区。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM