I'm trying to determine whether an execution failed by checking the result of waitpid(). However, even when I run a command that I know fails and writes the issue to stderr, the check below never registers. What could possibly be wrong with this code?
Thanks for any help.
pid_t pid; // the child process that the execution runs inside of.
int ret; // exit status of child process.
child = fork();
if (pid == -1)
{
// issue with forking
}
else if (pid == 0)
{
execvp(thingToRun, ThingToRunArray); // thingToRun is the program name, ThingToRunArray is
// programName + input params to it + NULL.
exit(-1);
}
else // We're in the parent process.
{
if (waitpid(pid, &ret, 0) == -1)
{
// Log an error.
}
if (!WIFEXITED(ret)) // If there was an error with the child process.
{
}
}
It is a blocking call that will wait till any of the child processes terminates. There are other options as well. Using the waitpid function you could wait for a specific child to terminate using its PID or you can have a non-blocking way to check if there is any child-processes that has already terminated.
The WNOHANG flag (set in the options argument) will make the call to waitpid() non-blocking. You'll have to call it periodically to check if the child is finished yet. Or you could setup SIGCHLD to take care of the children.
Specifies the child processes the caller wants to wait for: If pid is greater than 0, waitpid() waits for termination of the specific child whose process ID is equal to pid. If pid is equal to zero, waitpid() waits for termination of any child whose process group ID is equal to that of the caller.
Syntax of waitpid() : pid_t waitpid(pid_t pid, int *status, int options); The value of pid can be: < -1: Wait for any child process whose process group ID is equal to the absolute value of pid .
waitpid
only returns -1 if an error occurs with waitpid
. That is, if you give it an incorrect pid, or it is interrupted, etc. If the child has a failing exit status, waitpid will succeed (return the pid) and set ret
to reflect the status of the child.
To determine the status of the child, use WIFEXITED(ret)
and WEXITSTATUS(ret)
. For example:
if( waitpid( pid, &ret, 0 ) == -1 ) {
perror( "waitpid" );
} else if( WIFEXITED( ret ) && WEXITSTATUS( ret ) != 0 ) {
; /* The child failed! */
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With