i'm writing a program that recieves a command name and arguments and optionally the string "bg" at the end , if the "bg" string is passed my program should execute the command with its arguments in background if not in foreground, here's my code:
#include<sys/types.h>
#include<sys/wait.h>
#include<unistd.h>
#include<stdio.h>
#include<errno.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char* argv[])
{
pid_t pid;
int state;
if( (pid=fork())<0) {
perror("\nError in fork");
exit(-1);
}
else if(pid==0) {
if(strcmp(argv[argc-1], "bg") == 0 ){
strcpy(argv[argc-1],"&");
if( (execvp(argv[1], argv)<0)) {
perror("\nError in first execvp");
exit(-1);
}
}
else{
if( (execvp(argv[1], argv+1)<0)) {
perror("\nError en second el execvp");
exit(-1);
}
}
}
wait(&state);
printf("\nMy child %d terminated with state %d\n",pid,state);
exit(0);
}
input example:
./myprogram ls -lai bg // in this case my program should execute "ls -lai" in background
./myprogram ls -lai // in this case it should execute command normally in foreground
my code works when the bg argument is not passed but when passed i tried to substitute it with "&" but it didn't work, help is appreciated guys.
The difference between backgrounding a program - or not - lies in waiting for it to finish, or don't wait. So you don't really have to use two different execvp's. But, you need to remove the trailing bg from the arguments. Appending the & won't do anything - the & is a metacharacter for the shell, which tells the shell not to wait for the program that's being executed.
So, what you should do is:
if the last argument is "bg" : decrease argc by one, set the argument that had the bg to null
fork and execvp what's in argv
if the last argument was "bg", do NOT call wait(); else call wait.