gpt4 book ai didi

c - 在 C 中为套接字编写 send_all 和 recv_all 函数

转载 作者:太空宇宙 更新时间:2023-11-04 08:45:25 25 4
gpt4 key购买 nike

我是一个新的 C 程序员,所以你必须原谅我缺乏知识。我正在尝试在 Windows 机器上使用 C 中的套接字在客户端和服务器之间来回发送数据。我将 cygwin 的工具与 codeblocks IDE 一起使用。简单的发送和接收不起作用,所以经过一番搜索后,我的印象是我的问题是我需要一个 send_all 和 recv_all 函数。我已经编写了以下两个函数,但接收似乎总是陷入无限循环。我不太确定为什么。

void send_all(int socket, void *buffer, int length) {
size_t i = 0;
for (i = 0; i < length; i += send(socket, buffer, length - i, 0)){
printf("Completed: %d bytes \r", i);
}
printf("Send Completed: %d bytes \n", length);
}

void recv_all(int sockfd, void *buffer, int length){
size_t i = 0;
for (i = 0; i < length; i+= recv(sockfd, buffer + i, length - i, 0)){
printf("Completed: %d bytes \r", i);
}
printf("Receive Completed: %d bytes \n", length);
}

我想知道是不是因为接收方不知道发送方发送了多少字节。感谢所有建议,但请保持建设性。谢谢。

最佳答案

recv() 实际上返回一个 signed 值(int 在 Winsock 中,ssize_t 在 POSIX 中)。如果发生读取错误,或者如果套接字处于非阻塞模式且没有数据可用,则其返回值可以是负数。如果套接字被优雅地关闭,它的返回值为零(这会导致代码中的无限循环)。

在将返回值添加到字节计数器之前,您需要检查返回值,以检测这两种情况。

如果您的套接字处于阻塞模式(默认),您的代码将无限期阻塞,直到收到所需的数据量,或者发生错误(一旦您添加代码来检查)。鉴于您的函数名称,这似乎是您想要的行为。如果是这样,您的一般方法是合理的。

ssize_t bytesRead = 0;

while (bytesRead < length)
{
ssize_t rv = recv(/* ... */);

if (rv == 0)
{
printf("Socket closed gracefully before enough data received\n");
break;
}

else if (rv < 0)
{
// if your socket is non-blocking, check for EAGAIN which
// would mean no data is currently available; in this case you
// could do something like call select() on the socket to
// go to sleep until more data comes in

printf("Read error occurred before enough data received\n");
break;
}

bytesRead += rv;
}

关于c - 在 C 中为套接字编写 send_all 和 recv_all 函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21861279/

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