简体   繁体   中英

Stuck on wait() after fork()

I have looked on some topics about this, but could not solve it -

I am forking twice, but when waiting for the last proc it get stuck on wait(), if i remove the wait() it moves on, but obviously it does not wait:

here is the relevant code:

  /*Fork #1*/
  if((pid=fork())==0)
  {
    if(command -> inputRedirect != NULL)
    {
      fclose(stdin);
      fopen(command -> inputRedirect,"r");
    }
    fclose(stdout);
    dup(pipefd[1]);
    close(pipefd[1]);
    i=execvp(command->arguments[0],command->arguments);
  }
  if(i == -1)
  {
    perror("Error");
    return 1;
  }
  printf("\nParent: %d , Child: %d\n",getpid(),pid);

  command = command->next;
  /*Fork #2*/
  if((pid=fork())==0)
  {

    fclose(stdin);
    dup(pipefd[0]);
    close(pipefd[0]);

    if(command -> outputRedirect != NULL)
    {
      fclose(stdout);
      fopen(command ->outputRedirect,"w");
    }

    i=execvp(command->arguments[0],command->arguments);
    _exit(0);
  }

  if(i == -1)
  {
    perror("Error");
    return 1;
  }

  if(command->blocking == 1)
  {
    int test=0;
    printf("\nParent: %d , Child: %d\n",getpid(),pid);
    printf("\ntest1\n");
    while((test=wait(NULL)) != pid)
    {
      printf("\n %d \n ", test);
    }
    printf("\ntest2\n");
  }
  return 0;
}

i added some tests to see some PID outputs and whats going on inside, it waits for the first chil process to finish, and print the right ID, but on the second one it just blocks.

I do however see on screen that the second process finished (from the process output).

Any help on the topic would be most welcome.

thank you.

It is an error for a process to call wait() when it has no uncollected children ( wait() will return -1 and set errno to ECHILD in that case), so the fact that wait() hangs indicates that there is a child process that has not been collected. Once that child process in fact has terminated -- including if it had already terminated before the wait() call -- the parent process becomes eligible for scheduling and should return promptly from wait() . That the wait() call hangs for you is therefore a pretty good indication that one of the two child processes in fact has not exited.

As I wrote in comments, the child's output is not necessarily a reliable indication of whether it has exited. The child will become a zombie when it exits, until it is collected, and you can check for that in the process table.

Your file descriptor handling looks a bit weird, and it is possible that that is the source of your problem. In the first place, if you want to duplicate your pipe FDs onto the children's standard streams, then you should use dup2() so as to specify explicitly, instead of close() + dup() . More likely to be your actual problem, though, is the parent process's failure to close its copies of the pipe's FDs. If the second child is waiting for EOF on its standard input (from the pipe), then the parent's failure to close its copy of the writing end of that pipe will prevent the child from terminating.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM