当使用Winsock读取所有信息时,结束“recv()”循环

我在winsockrecv()循环中遇到问题。 我试图在iResult == 0时终止循环,但是,循环仅在套接字closures时结束。 它似乎挂在最后recv()哪里iResult将等于0.所以任何想法如何有效地终止循环? 我的最终目标(无论是否iResult == 0,也许我是这样做的错误方式)是当所有发送的信息被读取时停止循环。 这是循环。

do { iResult = recv(socket, recvbuf, BUFLEN-1, 0); if(iResult > 0){ // Null byte :) // Remove that garbage >:( recvbuf[iResult] = '\0'; printf("Recvbuf: %s\n\n\niResult: %d\n",recvbuf,iResult); continue; // working properly } else if(iResult == 0) // Connection closed properly break; else { printf("ERROR! %ld",WSAGetLastError()); break; } } while(iResult > 0); 

就像我说的,我收到所有的数据,我只是不能退出循环。 下一步是将数据写回到服务器,但是直到ping超时才挂起。 套接字是SOCK_STREAM,BUFLEN被定义为0x200

谢谢

Solutions Collecting From Web of "当使用Winsock读取所有信息时,结束“recv()”循环"

默认情况下,而不是返回0, 如果没有数据要接收 recv 块 :

如果在套接字上没有可用的数据,则recv调用会根据为WSARecv定义的阻塞规则阻塞并等待数据到达,并且MSG_PARTIAL标志未设置,除非该套接字是非阻塞的。 在这种情况下,将返回错误代码设置为WSAEWOULDBLOCK的SOCKET_ERROR值。 select,WSAAsyncSelect或WSAEventSelect函数可用于确定更多数据何时到达。

您可以使用ioctlsocket将套接字置于非阻塞模式:

 u_long iMode = 1; ioctlsocket(socket, FIONBIO, &iMode); 

编辑 :这是我在较早的rev,然后删除(请参阅评论)setsockopt建议:

如果没有可用的数据,可以使用带SO_RCVTIMEO选项的setsockopt函数将套接字设置为recv超时。

当你设计一个TCP通信机制时,你必须定义消息边界。 (通常\ r \ n)。 tcp本身并不知道边界; 你必须自己做这个。 recv()调用可能不总是在消息边界上返回。 一个send()可能在另一端被拆分成多个recv()。