I need to create 5 processes one being father of the second, grandpa of the third etc. All of them have to wait for each other to finish. I tried the approach with:
switch (pid = fork()) {
case 0:
printf("Child PID = %d\n", getpid());
printf("parent: =\%d\n", getppid());
return 0;
default:
break;
But I always get the same parent.
You need to use recursion.
For example:
void create_processes(int n) {
if(n == 0) return;
if(fork() == 0) {
int status;
// You're in the child process. Calling it recursively will have the
// child's PID as parent
create_processes(n - 1);
// Do work you need done before the child terminates
wait(&status);
// Do work you need done after the child terminates
}
}
Then call it like
create_processes(5);
Call a process myProcess that returns no type and takes an int as a parameter. Then...
void myProcess(int x)
{
if (x > 5) return;
if (x != 0)
myProcess(x - 1);
return;
};
int main()
{
int myvar = 5;
myProcess(myvar);
return 0;
}
It's done recursively.
Related
I have been trying to understand the output of this program, but still I don’t quite get it.
main()
{
int pid, i;
pid = getpid();
for (i = 0; i < 25; i++)
{
switch (fork())
{
case 0:
if (pid % 2 == 0)
{
exit(0);
break;
}
default:
if (pid % 2 != 0)
{
exit(0);
}
}
}
printf("I am the process %d and my father is the process %d\n", getpid(), getppid());
while (wait(NULL) > 0) {}
return 0;
}
When I run this, it returns:
I am the process 11110 and my father is the process 26453
However, if you were to run the above code without both "% 2", it won't return anything.
I am very confused about this. The way I thought it would work (for the code without "% 2") is, for each for iteration:
the child (pid==0) would finish its process (killing the child process) and always break from the switch (not affecting the for loop)
the father/main process will wait until the child dies
next for iteration
Is the above approach correct? If so, how would it be with "% 2"?
Without % 2 you'd get:
switch (fork())
{
case 0:
if (pid == 0)
{
exit(0);
break;
}
default:
if (pid != 0)
{
exit(0);
}
}
Since pid is not 0, the parent would exit(0) immediately after the first fork(), so you won't see a print statement.
Do I understand correctly that 2 processes are created in the code below? Since one fork () call creates one thread. There are two such calls in the code, therefore, the process is created 2?
#include <stdio.h>
#include <stdlib.h>
int main() {
int x,y;
pid_t pidl, pid2;
x = 2;
y = 3;
printf ("Single process, x=$d\n",x);
pidl = fork();
if(pidl == 0) {
printf ("New, x=%d\n",x);
exit (0);
}
if(pid1 < 0){
printf("Cannot create");
exit (1);
}
pid2=fork();
if(pid2 == 0) {
printf ("New, y=%d\n",y);
exit (0);
}
if(pid2 < 0){
printf("Cannot create");
exit (1);
}
return 0;
}
Yes. This code create two child process.
However you do not make the relation between parent and child processes by using wait function.
Therefore result of code change variously.
Child process 1 can print result before / after parent process terminated.
Child process 2 can print result before / after parent process terminated.
Maybe this variable result confuse you.
can someone help me about how to create multiple child processes which have the same parent in order to do "some" part of particular job?
for example, an external sorting algorithm which is applied with child processes; each child process sorts a part of data and finally the parent merges them..
EDIT: Maybe I should mention the forking multiple child processes with loop..
Here is how to fork 10 children and wait for them to finish:
pid_t pids[10];
int i;
int n = 10;
/* Start children. */
for (i = 0; i < n; ++i) {
if ((pids[i] = fork()) < 0) {
perror("fork");
abort();
} else if (pids[i] == 0) {
DoWorkInChild();
exit(0);
}
}
/* Wait for children to exit. */
int status;
pid_t pid;
while (n > 0) {
pid = wait(&status);
printf("Child with PID %ld exited with status 0x%x.\n", (long)pid, status);
--n; // TODO(pts): Remove pid from the pids array.
}
If you want to launch several forks, you should do it recursively. This is because you must call fork from the parent process. Otherwise, if you launch a second fork, you will duplicate both parent and first child process. Here's an example:
void forker(int nprocesses)
{
pid_t pid;
if(nprocesses > 0)
{
if ((pid = fork()) < 0)
{
perror("fork");
}
else if (pid == 0)
{
//Child stuff here
printf("Child %d end\n", nprocesses);
}
else if(pid > 0)
{
//parent
forker(nprocesses - 1);
}
}
}
I think it would be worth pointing out why threads are more appropriate here:
As you are trying to do a "part" of the job in parallel i assume that your program needs to know about the result of the computation. fork()s of a process don't share more then the initial information after fork(). Every change in one process is unknow to the other and you would need to pass the information as a message (e.g. through a pipe, see "man pipe").
Threads in a process share the same adress space and therefor are able to manipulate data and have them visible toeach other "immediatly". Also adding the benefits of being more lightweight, I'd go with pthreads().
After all: You will learn all you need to know about fork() if you use pthreads anyway.
You can do this with fork. A given parent can fork as may times as it wants. However, I agree with AviD pthreads may be more appropriate.
pid_t firstChild, secondChild;
firstChild = fork();
if(firstChild > 0)
{
// In parent
secondChild = fork();
if(secondChild > 0)
{
// In parent
}
else if(secondChild < 0)
{
// Error
}
else
{
// In secondChild
}
}
else if(firstChild < 0 )
{
// Error
}
else
{
// In firstChild
}
I am currently learning about the fork() function in c. I was playing around with the child pid's and trying to store them within an array but keep coming across errors:
void store(int pid){
int arr[10];
int i = 0;
for(i = 0; i < 10; i++){
if(arr[i] == 0){
arr[i] = pid;
printArray(arr);
break;
}
}
}
int stuff(int a){
int status = fork();
if(status == 0){
printf("PID IS %d\n", getpid());
store(getpid());
}
else {
printf("PID IS %d\n", getpid());
store(getpid());
}
return a + 1;
}
int main(int argc, char * argv[]){
int a = stuff(10);
return 0;
}
Instead, this outputs the same array with the two different PIDS in the same array index. I am not too sure what exactly is happening here and would be grateful for any explanation.
Keep it in mind that fork function is called once but returns twice. The difference in the returns is that the return value in the child
is 0, whereas the return value in the parent is the process ID of the new child. The child process and the parent process run in separate memory spaces.
That's the reason why your program outputs the same array with the two different PIDS in the same array index.
int stuff(int a){
int status = fork();
// fork will return a value of pid_t type
pid_t status = fork();
if(status == 0){
// this is in the child process, so getpid() will return the pid of the child
printf("PID IS %d\n", getpid());
store(getpid());
}
else {
// this is in then parent process, so getpid() will return the pid of the parent
printf("PID IS %d\n", getpid());
store(getpid());
}
return a + 1;
}
can someone help me about how to create multiple child processes which have the same parent in order to do "some" part of particular job?
for example, an external sorting algorithm which is applied with child processes; each child process sorts a part of data and finally the parent merges them..
EDIT: Maybe I should mention the forking multiple child processes with loop..
Here is how to fork 10 children and wait for them to finish:
pid_t pids[10];
int i;
int n = 10;
/* Start children. */
for (i = 0; i < n; ++i) {
if ((pids[i] = fork()) < 0) {
perror("fork");
abort();
} else if (pids[i] == 0) {
DoWorkInChild();
exit(0);
}
}
/* Wait for children to exit. */
int status;
pid_t pid;
while (n > 0) {
pid = wait(&status);
printf("Child with PID %ld exited with status 0x%x.\n", (long)pid, status);
--n; // TODO(pts): Remove pid from the pids array.
}
If you want to launch several forks, you should do it recursively. This is because you must call fork from the parent process. Otherwise, if you launch a second fork, you will duplicate both parent and first child process. Here's an example:
void forker(int nprocesses)
{
pid_t pid;
if(nprocesses > 0)
{
if ((pid = fork()) < 0)
{
perror("fork");
}
else if (pid == 0)
{
//Child stuff here
printf("Child %d end\n", nprocesses);
}
else if(pid > 0)
{
//parent
forker(nprocesses - 1);
}
}
}
I think it would be worth pointing out why threads are more appropriate here:
As you are trying to do a "part" of the job in parallel i assume that your program needs to know about the result of the computation. fork()s of a process don't share more then the initial information after fork(). Every change in one process is unknow to the other and you would need to pass the information as a message (e.g. through a pipe, see "man pipe").
Threads in a process share the same adress space and therefor are able to manipulate data and have them visible toeach other "immediatly". Also adding the benefits of being more lightweight, I'd go with pthreads().
After all: You will learn all you need to know about fork() if you use pthreads anyway.
You can do this with fork. A given parent can fork as may times as it wants. However, I agree with AviD pthreads may be more appropriate.
pid_t firstChild, secondChild;
firstChild = fork();
if(firstChild > 0)
{
// In parent
secondChild = fork();
if(secondChild > 0)
{
// In parent
}
else if(secondChild < 0)
{
// Error
}
else
{
// In secondChild
}
}
else if(firstChild < 0 )
{
// Error
}
else
{
// In firstChild
}