Dilletante
Dilletante

Reputation: 1891

In the following program how many processes will be spawned

int main()
{
fork();
fork() && fork() || fork();
fork();

printf("forked\n");
return 0;
}

When we call fork function , the parent gets a non-zero pid while the child gets a 0 in return Based on this Logic, in the second statement we will have to apply the principle of shortcircuiting(afaik).... After the 1st call there will be 2 process,

After the second line, 8 processes,[A parent gets forked two times in (fork() && fork()), and the second child also gets twice due to the "fork()||fork()"]

And finally 16(According to my reasoning)

Please let me know if this is correct or some other logic is involved

Upvotes: 2

Views: 734

Answers (2)

TOC
TOC

Reputation: 4446

To calculate the number of process after (fork() && fork() || fork()), just remember that :

  • In (&&) logical operator : the right side is evaluated only when the left side is NON ZERO

  • In (||) logical operator : the right side is evaluated only when the left side is ZERO

And with operators precedence we wan write this like so:

(fork() && fork()) || fork()

Remember also that fork return NON ZERO to the parent and ZERO to the child

To simplify the explanation, we rename :

fork() && fork() operation A

and the last fork() Operation B, so the precedent line is equivalent to:

(fork() && fork()) || fork() => A || B

First line (fork) :

---> 2 process (Father and Child1)

Second line:

  • A operation:

the first fork =>

Father will give a child => Father(PID of Child2) and Child2(ZERO) Child1 will give a child => Child1(PID of Child3) and Child3(ZERO)

We have 4 Process : Father (PID of Child2), Child2(ZERO), Child1(PID of Child3) and Child3(ZERO)

The (&& fork()) will be executed only for last operations that returns NON ZERO => Father and Child1

Father wille give a child => Father(PID of Child4) and Child4(ZERO) Child1 will give a child => Child1(PID of Child5) and Child5(ZERO)

Let's summurize:

We have 6 process :

Father(PID of Child4), Child4(ZERO), Child1(PID of Child5), Child5(ZERO), Child2(ZERO) and Child3(ZERO)

  • B Operation:

Is only executed for last commands that returns ZERO => process that returns ZERO from A Operation, Concerned Process are:

Child4(ZERO), Child5(ZERO), Child2(ZERO) and Child3(ZERO)

When forking this 4 process we end with 4 new process => Total number of process after second line = 10

Third Line : It's just a simple fork

=> The total number of process is = 20

To demonstrate that: use this (fork_quiz.c)

#include <unistd.h>
#include <stdio.h>

int main(int argc, char **argv)
{
        fork();
        fork() && fork() || fork();
        fork();

        sleep(10);

        return 0;
}

And compile it:

gcc -Wall fork_quiz.c -o fork_quiz

And run it like so :

toc@UnixServer:~$ ./fork_quiz & (sleep 1; ps -o "%P%p%c")
[1] 15455
 PPID   PID COMMAND
15046 15047 bash
15047 15455 fork_quiz
15047 15456 bash
15455 15457 fork_quiz
15455 15458 fork_quiz
15455 15459 fork_quiz
15455 15460 fork_quiz
15457 15462 fork_quiz
15457 15463 fork_quiz
15457 15464 fork_quiz
15458 15465 fork_quiz
15458 15466 fork_quiz
15459 15467 fork_quiz
15459 15468 fork_quiz
15465 15469 fork_quiz
15467 15470 fork_quiz
15463 15471 fork_quiz
15463 15472 fork_quiz
15462 15473 fork_quiz
15462 15474 fork_quiz
15473 15475 fork_quiz
15471 15476 fork_quiz
15456 15477 ps

Upvotes: 7

Vladimir
Vladimir

Reputation: 10493

Let's rewrite the program a bit to count spawned processes:

#include <stdio.h>

int my_fork(const char *c) {
    int r = fork();
    if (!r) {
        fprintf(stderr, "process spawned at %s\n", c);
    }
    return r;
}

int main()
{
my_fork("a");
my_fork("b") && my_fork("c") || my_fork("d");
my_fork("e");

return 0;
}

Upon launch you will see 19 lines process spawned so 19 processes were spawned as a result of fork() invokation:

~$ ./test
process spawned at a
process spawned at c
process spawned at c
process spawned at e
process spawned at e
process spawned at b
process spawned at d
process spawned at d
process spawned at e
process spawned at e
process spawned at e
process spawned at d
process spawned at e
process spawned at e
process spawned at b
process spawned at e
process spawned at d
process spawned at e
process spawned at e

UPD: Number of processes can be easily calculated having in mind that there is short-circuit boolean evaluation in C.

Upvotes: 1

Related Questions