I'm executing two bash command ps
(which is valid bash command to show processes info) and abc
(Invalid bash command) using execvp()
inside a child process after creating it with by fork()
The problem is once execvp()
fails parent process is taken over by child process as we can from the output of screenshot.
I had to type exit twice to exit out of infinite while loop. What's happening? I'm correctly executing execvp()
inside a child process yet main(parent) process is taken over by child process?
Can anyone explain this behaviour & how I can fix this ? If execvp()
fails I do not want that child process to take over parent process. How to handle this?
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<sys/wait.h>
int ExecCommand(char** args)
{
int childId = fork();
if(childId<0) printf("Error creating child process\n");
if(childId==0)
{
printf("Executing (%s) whose childId:%d\n", args[0], getpid());
int status=execvp(args[0],args);
printf("Failed executing %s with status %d whose childId:%d\n\n",args[0],status,getpid());
return 1;
}
else
{
int id=wait(NULL);
printf("waiting for child: %d\n\n",id);
}
}
int main()
{
char out[5]="exit\0";
while(1)
{
printf("From Main(): pid:%d ppid:%d\n",getpid(), getppid());
printf("Enter 'exit' to exit or Just hit Enter to execute below 2 commands:");
char input[25]={'\0'};
scanf("$[^\n]",&input[0]);
getchar();//to remove \n from stdin
strncpy(out,input,4);
if(strcmp(out,"exit\0")==0)
{
exit(0);
}
char *cmd1[2] = {"ps", NULL}; //valid bash command
char *cmd2[2] = {"abc", NULL}; //invalid bash command
char** commands[2]={cmd1, cmd2};
for(int i=0;i<2;i )
{
ExecCommand(commands[i]);
}
}
return 0;
}
Output:
CodePudding user response:
The problem is that if execvp
fails, you return to the main
function in your child process. That leads to both the original (parent) and child process will continue in the loop.
If execvp
fails you should probably call exit
to exit the child process.
Also note that in the parent process the ExecCommand
function doesn't return anything at all. If you compiler doesn't complain about that you need to enable more warnings when building.