父子进程,套接字关闭

时间:2011-02-27 14:54:50

标签: sockets process parent-child

我被这个模拟服务器 - 客户端交互的代码片段所困扰,假设 sockfd 是在服务器端创建的套接字文件描述符。

我的问题是当父和它的子进程'同时'运行时,并且在子进程执行时间片期间,它关闭服务器套接字 sockfd ,然后当执行流到,例如,第二次循环,调用accpet函数,参数 sockfd 有效,它是否由子进程关闭,即从内核文件描述符表中解除分配?

while (1) {
    //accept a connection from client,get the new socket from client
                       //is the sockfd valid here,is it closed by the child in
                       //the previous loop
     newsockfd = accept(sockfd,(struct sockaddr *) &cli_addr, &clilen); 

     if (newsockfd < 0) 
         error("ERROR on accept");
     pid = fork();
     if (pid < 0)
         error("ERROR on fork");
     if (pid == 0)  {
         close(sockfd);  // can't this cause problem ??
         dostuff(newsockfd);
         exit(0);
     }
     else close(newsockfd);
 } /* end of while */

4 个答案:

答案 0 :(得分:6)

在这段代码中:

if (pid == 0)  {
     close(sockfd);  // can't this cause problem ??
     dostuff(newsockfd);
     exit(0);
 }

close()仅影响子文件sockfd文件描述符的副本。

父母的副本仍然在下次循环播放时使用。

子进程被认为是关闭不需要的继承文件描述符的良好方式。

答案 1 :(得分:0)

父级所做的任何事都不会导致子文件描述符在你的意思上被关闭。对其的操作将根据具体情况返回适当的状态,但在{2}或open之前,该子编号永远不会返回该子编号,直到子进程调用dup

答案 2 :(得分:0)

每当您调用fork()函数时,子进程都会复制当前进程。因此,在第二个循环中,子进程中的sockfd与父进程(尚未关闭)相同。所以这是有效的。

答案 3 :(得分:0)

当你关闭重复的fd时,它似乎并没有真正关闭流,直到所有关闭。我使用我创建的一个有趣的网络服务器遇到了这个问题。我在叉子上关闭了fd,但它仍保持打开状态。

我通过在fork之后关闭它来修复它。