【问题标题】:C# TcpClient ReadAsync reading a large messageC# TcpClient ReadAsync 读取大消息
【发布时间】:2013-02-28 20:13:33
【问题描述】:

我有一个 C# TcpClient 来异步读取数据。简化代码如下:

public async Task StartReading(CancellationToken token)
{
    // To fit the largest package
    const int BufferSize = 524288;

    while(true)
    {
         var buffer = new byte[BufferSize];
         int bytesRead = await this.networkStream.ReadAsync(buffer, 0, BufferSize);
                                          .WithWaitCancellation(token);            

            if (bytesRead > 0)
            {
                 Console.Read(string.Fromat("{0} bytes received."));

                 // Run processing at background process
                 Task.Run(() => ProcessData(buffer, bytesRead));
            }
            else
            {
                // If received 0 bytes then a tcp connection is terminated
                break;
            }
    }
}

收到的包可能包含一条或多条以 STX 开头并以 ETX 结尾的消息,不发送包长度。此 Feed 由第 3 方提供,不会更改。

在测试过程中,服务器似乎以 8192 个块发送数据,因此一条消息可能被分成两个后续块并且无法处理。
这是一个日志:
已收到 8192 个字节
已处理 89 条消息 / 1 条失败
已收到 8192 个字节
已处理 89 条消息 / 2 条失败
已收到 8192 个字节
已处理 89 条消息 / 2 条失败
已收到 2349 个字节
已处理 34 条消息/1 条失败

同步读取也无济于事。我该如何管理它?

【问题讨论】:

    标签: c# asynchronous tcpclient


    【解决方案1】:

    从根本上说,TCP 是一个基于流的 协议。您试图将其视为基于数据包的 协议。不要那样做。

    数据提供了自己的分隔符 - 所以使用它。如果没有完全接收到消息,请记住这些字节,然后在收到消息的其余部分时处理它们。 (请记住,在下一次读取调用中也可能不会完全接收到消息......)

    【讨论】:

      猜你喜欢
      • 2013-02-22
      • 1970-01-01
      • 2016-03-19
      • 1970-01-01
      • 1970-01-01
      • 2016-04-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多