Your first question -
what being in the child/father process technically means
The fork()
creates a child process by duplicating the calling process.
The process that invoked fork()
is the parent process and the newly created process is the child process.
So fork()
splits a process in two, and returns 0 to the child process and the PID of the child process to the parent process, or -1 if the fork failed.
The child process and the parent process run in separate memory spaces. At the time of fork() both memory spaces have the same content.
There is concept called Copy on Write, its good to have knowledge about it-
Copy on Write is an optimization where the page tables are set up so that the parent and child process start off sharing all of the same memory, and only the pages that are written to by either process are copied when needed.
If the process does not modify any memory and immediately executes a new process, replacing the address space entirely. Thus, it would be wasteful to copy all of the process's memory during a fork, and instead the copy-on-write technique is used.
For example, in your program you have immediately calling execlp
after fork
:
if(fork()==0){
//processus fils
//executer la commande
execlp(ligne, ligne, NULL);
Your second question -
I couldn't see the use of waitpid, what will happen if I didn't use it?
To explain this, I have modified your program and added statement to print parent and child process pid's and commented out this statement-
waitpid(-1,NULL,0);
Output of program is -
parent process pid : 22325
-->ls
child process pid : 22326
< here the output of ls command >
Now, if we see the output of ps
command with grep'ed parent process id -
# ps -eaf | grep 22325
root 22325 21555 0 10:39 pts/4 00:00:00 ./a.out
root 22326 22325 0 10:39 pts/4 00:00:00 [ls] <defunct>
root 22339 21644 0 10:39 pts/5 00:00:00 grep 22325
Here, in the output the first column is UID, second is PID and third id PPID (parent pid).
You can see the child process (pid - 22326) is marked as < defunct >.
A "defunct" process (also referred to as "zombie" process) is a process which has finished execution, it will have an exit status to report to its parent process. Because of this last little bit of information, the process will remain in the operating system’s process table as a zombie process, indicating that it is not to be scheduled for further execution, but that it cannot be completely removed (and its process ID cannot be reused) until it has been determined that the exit status is no longer needed.
And here comes the use of waitpid()
-
The wait()
and waitpid()
functions shall obtain status information pertaining to one of the caller's child processes.
waitpid()
suspends the calling process until the system gets status information on the child. If the system already has status information on an appropriate child when waitpid()
is called, waitpid()
returns immediately. waitpid()
is also ended if the calling process receives a signal whose action is either to execute a signal handler or to end the process.
For other details on waitpid()
like syntax (status, options) and return value you can check its man page.
If I uncomment the waitpid()
in your program and compile and run it, the output -
parent process id : 23069
-->ls
child process id : 23070
<here the output of ls command>
Now, if we see the output of ps command with grep'ed parent process id -
# ps -eaf | grep 23069
root 23069 21555 0 10:51 pts/4 00:00:00 ./a.out
root 23108 21644 0 10:51 pts/5 00:00:00 grep 23069
There is no zombie process. The child process which runs ls
command has been finished and the parent process read its exit status.
Hope this answer your both the questions.