如何知道send()或sendmsg()成功传递消息?

时间:2014-02-03 01:04:58

标签: c sockets send sendto

我使用TCP套接字建立一个简单的客户端和服务器程序进行通信。服务器等待客户端连接并回复它是否从客户端接收消息。下面是代码在服务器和客户端中的实现方式:

服务器端的代码:

 listen(sockfd,5);

 clilen = sizeof(cli_addr);
 newsockfd = accept(sockfd, (struct sockaddr *) &cli_addr, &clilen);

 if (newsockfd < 0)
      error("ERROR on accept");
 bzero(buffer,256);

 n = read(newsockfd,buffer,255);

 if (n < 0)
     error("ERROR reading from socket");

 printf("Here is the message: %s\n",buffer);

 n = write(newsockfd,"I got your message",18);

 if (n < 0)
     error("ERROR writing to socket");

客户端代码:

if (connect(sockfd,(struct sockaddr *)&serv_addr,sizeof(serv_addr)) < 0)
    error("ERROR connecting");
printf("Please enter the message: ");
bzero(buffer,256);
fgets(buffer,255,stdin);
n = write(sockfd,buffer,strlen(buffer));
if (n < 0)
     error("ERROR writing to socket");
else
    printf("sucess. n = %d", n);

bzero(buffer,256);
n = read(sockfd,buffer,255);
if (n < 0)
     error("ERROR reading from socket");

现在,假设我启动服务器然后启动客户端,客户端成功连接到服务器。然后我关闭服务器并尝试从客户端发送消息,write()操作不返回任何错误。我期望这里是一个错误,因为服务器实际上没有收到任何数据包(它被关闭)。

所以我的问题是:有没有办法知道write()(或send()sendto()sendmsg())是否成功将消息传递给服务器?< / p>

2 个答案:

答案 0 :(得分:4)

没有。写或发只是说话,他们不等待反馈(例如TCP的情况下的ACK)。但是,如果您收到某种反馈,您只能确定邮件已成功发送。它甚至没有帮助尝试另一个发送,因为它可能在前一个消息尚未在客户端时执行。它也没有帮助recv和希望错误,因为您收到的数据可能在您发送消息之前由对等方发送。唯一可靠的方法是在应用程序协议中放置某种显式握手,并等待对您的消息的匹配响应。

答案 1 :(得分:1)

它不起作用。只要消息适合发送缓冲区,write()就会返回成功。知道该消息是由服务器接收和处理的唯一方法是接收解析“我收到你的消息”。

write()返回-1,然后已知连接已关闭或无效,但不要依赖它来检测所有可能的错误。