c - 为什么最后一个 read() 需要很长时间才能返回

标签 c network-programming

我编写了一个简单的程序,使用 unix 套接字从服务器下载 html 文件。

我使用 write() 发送“Get/index.html Host:*”消息,然后使用 while 循环来 read() 回复。一切都很顺利,但最后一个 read() 将返回 0 需要很长时间才能返回。有没有办法纠正代码,这样我就不需要等待这个特殊的时间了?或者这是怎么发生的?

    sprintf(cmdstr,"%s %s %s\r\nHOST:%s\r\n\r\n",METHOD,place,VERSION,host);
    cmdlen = strlen(cmdstr);
    if (write(sockfd,cmdstr,cmdlen) != cmdlen) {
       perror("write cmd error");
       return ;
    }

    while ((n = read(sockfd,read_data,BUFSIZE)) > 0) {
        read_data[n] = 0;
        p = read_data;

        if (filep == NULL) {
            if (filep = fopen(filename,"w")) == NULL) {
                perror("fopen ");
                return;
            }
            p = strstr(read_data,"\r\n\r\n");
            p += 4;
        }
        fputs(p,filep);
    }

    printf ("%s download completed.\n",filename);

最佳答案

如果没有准备好数据,recv将阻塞或失败(取决于它是阻塞还是非阻塞)。
recv当套接字的另一端关闭连接时,返回零。决不以其他方式。

对于 HTTP/1.1(当今几乎所有现有服务器),这种情况通常不会发生,至少不会立即发生,因为默认情况下连接预计会保持事件状态。

发送Connection: close向服务器发出信号,表明您不希望出现此行为。然后它应该尽快断开连接(当然是在向您发送所有内容之后)。

或者,您可以尝试调用 shutdown(sockfd, SHUT_WR); ,它执行连接的半关闭,并且服务器可能(希望应该)做出适当的 react 。

或者,最后,您只能阅读内容长度告诉您的内容,然后断开连接,但这对服务器来说是一种反社会行为,并且并非完全没有风险。

关于c - 为什么最后一个 read() 需要很长时间才能返回,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10025309/

相关文章:

c - 在 C 中使用函数和动态内存分配进行线性搜索

c++ - 具有多个文件的 LOG4CPP

c - 在 C 中通过 TCP 发送和接收整数值

c++ - 如何向路由器预连接发送消息

java - 从java程序向greasemonkey应用程序发送数据?

sockets - VMCI套接字,Berkeley套接字和winsock有什么区别?

c - C 中 Ackermann 函数的替代实现

c - 合并多个 .so 共享库

c - 我如何在不实际使用 c 中的 union 的情况下建立一个 union ?

c - 如何在C HTTP客户端程序中向文件写入HTTP请求