gpt4 book ai didi

windows - 当请求的缓冲区大小大于可用数据量时,为什么 recv 会失败?

转载 作者:可可西里 更新时间:2023-11-01 02:33:03 25 4
gpt4 key购买 nike

TCP 传输栈的底层是许多缓冲区限制,有时它们的作者记录了这些限制。在 WinXP SP3 上,我遇到了其中之一,我想,但无法弄清楚原因。

我已经实现了一个简单的客户端来从服务器获取数据(由一位同事用 Java 编写)。该协议(protocol)是将数据的长度(按网络顺序)写入四个字节,然后写入数据。服务器以 1024 字节 block 的形式将数据写入 TCP 流。客户端正确接收数据缓冲区的长度,分配内存并在循环中重复调用recv以获取所有数据:

unsigned int TCP_BlockSize = 4096;
unsigned int len;
int result;

...code to request len...
unsigned char *buf = new unsigned char[len];

if( len > TCP_BlockSize)
{
Uint32 currentLen = 0;
result = 0;
Uint32 failCount = 0;
while( currentLen < len && result >= 0)
{
result = recv( sock, buf + currentLen, TCP_BlockSize );
if( result > 0 )
{
currentLen = currentLen + result;
}
else
{
break;
}
}
}

如果我将 TCP_BlockSize 设置为 4095 或更低,一切都很好,我可以接收数兆字节的传输。当我尝试 4096 大小的接收 block 时,对剩余数据的最后一个请求,即 len - currentLen < TCP_BlockSize,总是失败,返回值为 -1,并且 errno = 0。我尝试了一些实验,比如修剪大小传输的数据以及 815054 和 834246 字节之间的某处,对于 4096 字节的接收 block ,一切都会蓬勃发展。

另一个细节:服务器在发送最后一个字节后关闭套接字。这就引出了一个问题,为什么不返回剩余的数据?在流为空 关闭之前不从 recv 返回 -1 感觉像是一个缺陷,因为当流不为空 并且 关闭接收时它是不明确的 - 1 从 recv。

那么如何获取最后的数据呢?

最佳答案

尝试类似...

to_rcv = (len - currentlen < TCP_BlockSize) ? len - currentlen : TCP_BlockSize;
result = recv( sock, buf + currentLen, to_rcv);

这样最终的 recv 将只询问所需的数量,否则它会询问 TCP_BlockSize。

关于windows - 当请求的缓冲区大小大于可用数据量时,为什么 recv 会失败?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/441361/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com