2

Is there any way to prevent creation of zombie processes while I am using fork() and exec() to run an application in background? The parent should not wait() for the child to complete. Also I cannot use sigaction() and sigaction.sa_handler because it affects all child processes which I don't want. I want something that will reap that particular child only, or that will prevent from spawning any zombie. Please help.

JatiA
  • 73
  • 1
  • 4
  • 12
  • As I noted in a comment to mah on Hoenir's answer, IMO it's usually an error to start a background task for which you have no way of determining its result (output/success/failure) or when it completes, but my answer addresses how to do it anyway in case you have a legitimate use for such a construct. – R.. GitHub STOP HELPING ICE Dec 08 '14 at 16:05

4 Answers4

3

If you want to create a "detached" process that you don't have to wait for, the best way is to fork twice so that it's a "grandchild" process. Immediately waitpid on the direct child process, which should call _exit immediately after forking again (so this waitpid does not block forward progress in the parent). The grandchild process will be orphaned so it gets inherited by the init process and you never have to deal with it again.

Alternatively you can install a signal handler for SIGCHLD with SA_NOCLDWAIT. However this is a really bad idea in general since its effects are global. It will badly break any library code you use that needs to be able to wait for child processes, including standard library functions like popen, possibly wordexp, possibly grantpt, etc.

R.. GitHub STOP HELPING ICE
  • 208,859
  • 35
  • 376
  • 711
1

To prevent of zombie processes you need to tell the parent to wait for the child, until the child's terminates the process.
You need to use the waitpid() function that is included in the library 'sys/wait.h'

Down here you have an example code that you can use the waitpid() function.

 #include <unistd.h>
    #include <sys/types.h>
    #include <errno.h>
    #include <stdio.h>
    #include <sys/wait.h>
    #include <stdlib.h>


int main()
{
    pid_t child_pid;
    int status;
    int local = 0;
    /* now create new process */
    child_pid = fork();

    if (child_pid >= 0) /* fork succeeded */
    {
        if (child_pid == 0) /* fork() returns 0 for the child process */
        {
            printf("child process!\n");

            // Increment the local and global variables

            printf("child PID =  %d, parent pid = %d\n", getpid(), getppid());



         }
         else /* parent process */
         {
             printf("parent process!\n");
             printf("parent PID =  %d, child pid = %d\n", getpid(), child_pid);
             wait(&status); /* wait for child to exit, and store child's exit status */
       }

     //code ..
  • 1
    Simply waiting for a child to terminate often defeats the reason for forking to another process so without some addition (such as was posted in @R's answer), simply saying "call `wait()`" doesn't seem particularly helpful. – mah Dec 08 '14 at 15:53
  • @mah: In fairness, if you're forking a process to do some job, you should probably care about the result of that job, and therefore have some asynchronous method to determine that it was completed (e.g. a pipe that reads EOF in your event loop) which in turn tells you when to `waitpid` for the child. I think it's almost-always wrong to make a truely detached process, but my answer addressed how to do that correctly anyway in case OP really needs to. – R.. GitHub STOP HELPING ICE Dec 08 '14 at 16:03
1

@R: In fairness, there ARE usercases where one might fork a job, and where there is absolutely no need to react on the result of the spawned child. Any call of a wait() function may eventually block the parent if there is no answer, may it? This might crash an airplane...

1

You can register a signal handler mechanism to prevent the child process to get zombie,

this Link will be helpful to resolution of your problem.

Hoi_A
  • 472
  • 1
  • 10
  • 20
Parthiv Shah
  • 350
  • 3
  • 17
  • (+1) but always include a short description of the solution, just in case the link won't be available in the future. – Omnibyte Apr 06 '19 at 08:37