Linux recv() 接收部分消息的套接字编程问题

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/10250666/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-06 05:54:50  来源:igfitidea点击:

Socket programming issue with recv() receiving partial messages

clinux

提问by Don Wool

I have a socket that is receiving streaming stock tick data. However, I seem to get a lot of truncated messages, or what appears to be truncated messages. Here is how I am receiving data:

我有一个正在接收流式股票报价数据的套接字。但是,我似乎收到了很多被截断的消息,或者似乎是被截断的消息。这是我接收数据的方式:

if((numbytes = recv(sockfd, buf, MAXDATASIZE-1, 0)) == -1) {
    perror("recv()");
    exit(1);
}
else {
    buf[numbytes] = '
// Read the response (sum total bytes read in tot_bytes)
for(tot_bytes=0; ; tot_bytes += iolen)
{  
    wait_on_socket(sockfd, 1, 60000L);
    res = curl_easy_recv(curl, buf + tot_bytes, sizeof_buf - tot_bytes, &iolen);

    if(CURLE_OK != res) {
        // printf( "## %d", res );
        break;
    }
}
'; // Process data }

Can recv()receive just a partial message of what was sent?

可以recv()只接收发送内容的部分消息吗?

My feeling is I might need another loop around the recv()call that receives until a complete message is sent. I know that a libcurl implementation I have (not possible to use libcurl here I would think) has an outer loop:

我的感觉是我可能需要围绕recv()接收的呼叫进行另一个循环,直到发送完整的消息。我知道我拥有的 libcurl 实现(我认为在这里不可能使用 libcurl)有一个外循环:

numbytes =  recv(sockfd, buf, MAXDATASIZE-1, MSG_WAITALL);

Do I need an recv()loop similar to the libcurl example (that verifiably works)?

我是否需要recv()类似于 libcurl 示例的循环(可验证有效)?

采纳答案by RichieHindle

You're right, you need a loop. recvonly retrieves the data that's currently available; once any data has been read, it doesn't wait for more to appear before it returns.

你是对的,你需要一个循环。 recv只检索当前可用的数据;一旦读取了任何数据,它就不会在返回之前等待更多数据出现。

The manual pagesays "The receive calls normally return any data available, up to the requested amount, rather than waiting for receipt of the full amount requested."

手册页说:“在接听电话正常返回的任何数据可用,直到请求的数量,而不是等待接收请求全额的。”

回答by young

can recv() receive just a partial message of what was sent?

recv() 可以只接收发送的部分消息吗?

Yes, indeed, if you use TCP. I think this can help you. Handling partial return from recv() TCP in C

是的,确实,如果您使用 TCP。我认为这可以帮助你。 在 C 中处理从 recv() TCP 的部分返回

回答by chrisaycock

TCP does not respect message boundaries. That means that recv()is not guaranteed to get the entire message, exactly as you hypothesize. And that is indeed why you need a loop around your recv(). (That's also why upper-layer protocols like HTTP either close the socket, or prepend a length indicator, so the recipient knows exactly when to stop reading from the socket.)

TCP 不尊重消息边界。这意味着recv()不能保证完全按照您的假设获得完整的消息。这确实是为什么你需要在你的recv(). (这也是为什么像 HTTP 这样的上层协议要么关闭套接字,要么在前面加上一个长度指示符,以便接收者确切地知道何时停止从套接字读取。)

回答by Anshuman

We can also pass the flag to recvto wait until all the message has arrived. It works when you know the number of bytes to receive. You can pass the command like this.

我们也可以将标志传递recv给等待所有消息到达。当您知道要接收的字节数时,它会起作用。您可以像这样传递命令。

##代码##