C#套接字读取缓冲区错误,多个客户端连接到服务器 [英] C# socket read buffer error with multiple clients connecting to servers

查看:87
本文介绍了C#套接字读取缓冲区错误,多个客户端连接到服务器的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我编写了一个Windows C#应用程序,最多可以创建16个线程。每个线程都为远程设备创建一个套接字。每个线程发送命令以读取设备状态。 (每300毫秒)当我创建一个或两个线程来读取状态时,这是可以的。但是当我创建10个线程来读取设备状态时,我将在套接字接收缓冲区中得到错误的数据。



请参阅以下内容获取我的套接字驱动程序代码:



I write an Windows C# application which can create up to 16 threads. Each thread creates a socket for a remote device. Each thread send commands to read the device status. (every 300 ms) It is OK when I create one or two threads to read the status. But when I create 10 threads to read device status, I will get wrong data in the socket receive buffer.

Please refer to the following for my socket driver code:

class SocketClient {

    private IPAddress ipAddress;
    private IPEndPoint remoteEP;
    private Socket mSocket;
    private SocketAsyncEventArgs e = new SocketAsyncEventArgs();
    private System.Timers.Timer timer_connection;
    private static byte[] response = new byte[1024];
    private Boolean waittingConnectDone;
    private Boolean boolConnected;
    public SocketClient() {
    }

    private byte[] acknowledge = null;

    public Boolean Connect(String IP, int Port) {
        Boolean bRet = true;
        ipAddress = IPAddress.Parse(IP);
        remoteEP = new IPEndPoint(ipAddress, Port);
        mSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
        //mSocket.ReceiveTimeout = GlobalVar.ethernet_timeout;
        mSocket.ReceiveTimeout = 500;

        try {
            waittingConnectDone = false;
            e.RemoteEndPoint = remoteEP;
            e.UserToken = mSocket;
            e.Completed += new EventHandler<socketasynceventargs>(e_Completed);
            mSocket.ConnectAsync(e);

            if (timer_connection != null) {
                timer_connection.Dispose();
            } else {
                timer_connection = new System.Timers.Timer();
            }
            timer_connection.Interval = 2000;
            timer_connection.Elapsed += new ElapsedEventHandler(timer_connection_Tick);
            timer_connection.Start();
            while (true) {
                if (waittingConnectDone)
                    break;
                Application.DoEvents();
            }
            bRet = boolConnected;

            //sender.Connect(remoteEP);
        } catch {
            Debug.WriteLine("### Ethernet ### Connection Error!");
            bRet = false;
        }
        return bRet;
    }

    private void e_Completed(object sender, SocketAsyncEventArgs e) {
        boolConnected = true;
        waittingConnectDone = true;
    }

    private void timer_connection_Tick(object sender, EventArgs e) {
        if (!mSocket.Connected) {
            timer_connection.Stop();
            boolConnected = false;
            waittingConnectDone = true;
        }
    }

    public void Disconnect() {
        try {
            mSocket.Shutdown(SocketShutdown.Both);
            mSocket.Close();
        } catch {
        }
    }





每个线程使用以下代码来读取设备状态:





Each Thread use following code to read the device status:

private byte[] acknowledge = null;
private static byte[] response = new byte[1024];

public byte[] sendCommand(byte[] Cmp_TxData) {
    try {
        bytesSent = mSocket.Send(Cmp_TxData);
        bytesRec = mSocket.Receive(response);

        acknowledge = new byte[bytesRec];
        Array.Copy(response, 0, acknowledge, 0, bytesRec);
    }
    catch
    {
        acknowledge = null;
    }

    return acknowledge;
}



缓冲区数据错误如下:


And the buffer data error is something like following:

TX --> 00-03-01-F4-00-03-44-14 
RX <-- 00-00-00-00-00-00-00-00-00-00-00





有时候我读了正确的数据,但有时数据都是0!



有吗我的套接字驱动程序有什么问题吗?



真的很感谢你的帮助。



Sometimes I read correct data, but sometimes the data are all 0!

Is there anything wrong with my socket driver?

Really appreciate your help.

推荐答案

private static byte[] response = new byte[1024];



这意味着所有线程只有一个缓冲区。缓冲区应该在线程内本地创建,而不是作为静态实体。您也可以在发送之后直接拨打接收,但不检查是否收到任何数据,或者是否仍有传输的一些数据,请参阅 https://msdn.microsoft.com/en -us / library / 8s4y8aff(v = vs.110).aspx [ ^ ]。


That means only one buffer for all threads. The buffer should be created locally within the thread, not as a static entity. You also call Receive straight after Send, but you do not check whether you received any data, or whether there is still some data being transmitted, see https://msdn.microsoft.com/en-us/library/8s4y8aff(v=vs.110).aspx[^].


这篇关于C#套接字读取缓冲区错误,多个客户端连接到服务器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆