-1

I have a doubt about fork process. I have a code which is

int main(int c, char **v){
  fork();
  fork() && fork() || fork();
  printf("Hello\t");
}

According to me the output of the above code will be 24 = 16 times "Hello", because each fork creates two copy of its own so the overall becomes 2*2*2*2 which are 16 times "Hello". But it's not correct it is giving me output as 10 times Hello. What is happening here?

user2736738
  • 30,591
  • 5
  • 42
  • 56
Ajay Kumar
  • 115
  • 5
  • 10
  • 3
    What do the [`fork`](http://man7.org/linux/man-pages/man2/fork.2.html) function return in the parent process? What does it return in the child process? And how do [short-circuit evaluation](https://en.wikipedia.org/wiki/Short-circuit_evaluation) work? When you can answer that you know what will happen. Knowing [operator precedence](http://en.cppreference.com/w/c/language/operator_precedence) would also be helpful. – Some programmer dude Jan 07 '18 at 10:48
  • 3
    And some nitpicking: The `fork` function only creates two copies if you count the original parent process as a "copy". – Some programmer dude Jan 07 '18 at 10:49
  • It means either homework, a quiz, a '-F' mark or a pink slip. – Martin James Jan 07 '18 at 10:56

1 Answers1

8

It's a brain teaser that tests your understanding of fork and how logical operators work in C. In particular their short circuit evaluation. It works based on these principles:

  • || will not evaluate the second expression if the first evaluates to a truthy value (not 0).

  • && will not evaluate the second expression if the first evaluates to a falsy value (0).

  • && has greater precedence than ||. So the "tricky" expression is equivalent to the fully parenthesized ((fork() && fork()) || fork());

  • fork returns 0 to the child process, and something other than 0 to the parent process. It returns -1 on failure, but evidently success is assumed in the problem.

With that in mind, we can trace process creation as follows:

  1. The original process calls fork unconditionally. Thus resulting in 2 processes.

  2. Each process from #1 calls the first fork in the logical expression. Each child thus created has a 0 returned, so it doesn't call the fork after the &&. The total number of processes is now 4.

  3. The two processes from #1 do call the fork after the &&. They create another 2 processes. Bringing us up to a total of 6. The parents satisfy the left sub-expression of the || so they won't call fork anymore. The newly created children processes do not satisfy the || yet. So they will call the last fork.

  4. The two children created in #2 and the two created in #3 call the last fork after the ||. They spawn 4 more processes in total. Bringing the count up to 10.

StoryTeller - Unslander Monica
  • 165,132
  • 21
  • 377
  • 458