Problem to understand how it works theses processes











up vote
0
down vote

favorite












Good evening,



I'm programming and testing some things about processes in C with fork() and waitpid() system calls. I understand the behavior with the global variable, but I don't understand why when the second process is finished and back in the first process the variable "i" has the same value as the second process.



And also why when the program go back to the root process, the variable "i" has the value 2.



Here is the code :



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>

int total = 0;
int main(int argc, char **argv) {
int i, pid;

for(i = 1; i < 3; ++i) {
pid = fork();

if(pid == 0) {
total = total + i;
printf("n");
printf("Child process %dn", getpid());
printf("Parent process %dn", getppid());
printf("i = %dn", i);
} else {
waitpid(pid, NULL, 0);
}
}
printf("Child process (end) %dn", getpid());
printf("Parent process (end) %dn", getppid());
printf("total = %dn", total);
printf("i = %dn", i);
exit(0);
}


And here is the result of the execution



Child process 9191
Parent process 9190
i = 1

Child process 9192
Parent process 9191
i = 2

Child process (end) 9192
Parent process (end) 9191
total = 3
i = 3

Child process (end) 9191
Parent process (end) 9190
total = 1
i = 3

Child process 9193
Parent process 9190
i = 2

Child process (end) 9193
Parent process (end) 9190
total = 2
i = 3

Child process (end) 9190
Parent process (end) 2876
total = 0
i = 3


I have a suggestion : it is that the function waitpid() take the resources to the child process, but it cannot explain the value of the variable "i" in the root process.



I hope that I was clear about my problems and sorry for my little bad english.



Thank you for your answers.










share|improve this question


















  • 4




    When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
    – John Bollinger
    Nov 9 at 21:47












  • You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
    – John Bollinger
    Nov 9 at 21:48






  • 1




    it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
    – Osiris
    Nov 9 at 21:52












  • OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
    – user3629249
    Nov 10 at 0:23










  • regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
    – user3629249
    Nov 10 at 0:26















up vote
0
down vote

favorite












Good evening,



I'm programming and testing some things about processes in C with fork() and waitpid() system calls. I understand the behavior with the global variable, but I don't understand why when the second process is finished and back in the first process the variable "i" has the same value as the second process.



And also why when the program go back to the root process, the variable "i" has the value 2.



Here is the code :



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>

int total = 0;
int main(int argc, char **argv) {
int i, pid;

for(i = 1; i < 3; ++i) {
pid = fork();

if(pid == 0) {
total = total + i;
printf("n");
printf("Child process %dn", getpid());
printf("Parent process %dn", getppid());
printf("i = %dn", i);
} else {
waitpid(pid, NULL, 0);
}
}
printf("Child process (end) %dn", getpid());
printf("Parent process (end) %dn", getppid());
printf("total = %dn", total);
printf("i = %dn", i);
exit(0);
}


And here is the result of the execution



Child process 9191
Parent process 9190
i = 1

Child process 9192
Parent process 9191
i = 2

Child process (end) 9192
Parent process (end) 9191
total = 3
i = 3

Child process (end) 9191
Parent process (end) 9190
total = 1
i = 3

Child process 9193
Parent process 9190
i = 2

Child process (end) 9193
Parent process (end) 9190
total = 2
i = 3

Child process (end) 9190
Parent process (end) 2876
total = 0
i = 3


I have a suggestion : it is that the function waitpid() take the resources to the child process, but it cannot explain the value of the variable "i" in the root process.



I hope that I was clear about my problems and sorry for my little bad english.



Thank you for your answers.










share|improve this question


















  • 4




    When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
    – John Bollinger
    Nov 9 at 21:47












  • You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
    – John Bollinger
    Nov 9 at 21:48






  • 1




    it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
    – Osiris
    Nov 9 at 21:52












  • OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
    – user3629249
    Nov 10 at 0:23










  • regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
    – user3629249
    Nov 10 at 0:26













up vote
0
down vote

favorite









up vote
0
down vote

favorite











Good evening,



I'm programming and testing some things about processes in C with fork() and waitpid() system calls. I understand the behavior with the global variable, but I don't understand why when the second process is finished and back in the first process the variable "i" has the same value as the second process.



And also why when the program go back to the root process, the variable "i" has the value 2.



Here is the code :



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>

int total = 0;
int main(int argc, char **argv) {
int i, pid;

for(i = 1; i < 3; ++i) {
pid = fork();

if(pid == 0) {
total = total + i;
printf("n");
printf("Child process %dn", getpid());
printf("Parent process %dn", getppid());
printf("i = %dn", i);
} else {
waitpid(pid, NULL, 0);
}
}
printf("Child process (end) %dn", getpid());
printf("Parent process (end) %dn", getppid());
printf("total = %dn", total);
printf("i = %dn", i);
exit(0);
}


And here is the result of the execution



Child process 9191
Parent process 9190
i = 1

Child process 9192
Parent process 9191
i = 2

Child process (end) 9192
Parent process (end) 9191
total = 3
i = 3

Child process (end) 9191
Parent process (end) 9190
total = 1
i = 3

Child process 9193
Parent process 9190
i = 2

Child process (end) 9193
Parent process (end) 9190
total = 2
i = 3

Child process (end) 9190
Parent process (end) 2876
total = 0
i = 3


I have a suggestion : it is that the function waitpid() take the resources to the child process, but it cannot explain the value of the variable "i" in the root process.



I hope that I was clear about my problems and sorry for my little bad english.



Thank you for your answers.










share|improve this question













Good evening,



I'm programming and testing some things about processes in C with fork() and waitpid() system calls. I understand the behavior with the global variable, but I don't understand why when the second process is finished and back in the first process the variable "i" has the same value as the second process.



And also why when the program go back to the root process, the variable "i" has the value 2.



Here is the code :



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>

int total = 0;
int main(int argc, char **argv) {
int i, pid;

for(i = 1; i < 3; ++i) {
pid = fork();

if(pid == 0) {
total = total + i;
printf("n");
printf("Child process %dn", getpid());
printf("Parent process %dn", getppid());
printf("i = %dn", i);
} else {
waitpid(pid, NULL, 0);
}
}
printf("Child process (end) %dn", getpid());
printf("Parent process (end) %dn", getppid());
printf("total = %dn", total);
printf("i = %dn", i);
exit(0);
}


And here is the result of the execution



Child process 9191
Parent process 9190
i = 1

Child process 9192
Parent process 9191
i = 2

Child process (end) 9192
Parent process (end) 9191
total = 3
i = 3

Child process (end) 9191
Parent process (end) 9190
total = 1
i = 3

Child process 9193
Parent process 9190
i = 2

Child process (end) 9193
Parent process (end) 9190
total = 2
i = 3

Child process (end) 9190
Parent process (end) 2876
total = 0
i = 3


I have a suggestion : it is that the function waitpid() take the resources to the child process, but it cannot explain the value of the variable "i" in the root process.



I hope that I was clear about my problems and sorry for my little bad english.



Thank you for your answers.







c linux fork waitpid






share|improve this question













share|improve this question











share|improve this question




share|improve this question










asked Nov 9 at 21:30









ZeRedDiamond

204




204








  • 4




    When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
    – John Bollinger
    Nov 9 at 21:47












  • You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
    – John Bollinger
    Nov 9 at 21:48






  • 1




    it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
    – Osiris
    Nov 9 at 21:52












  • OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
    – user3629249
    Nov 10 at 0:23










  • regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
    – user3629249
    Nov 10 at 0:26














  • 4




    When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
    – John Bollinger
    Nov 9 at 21:47












  • You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
    – John Bollinger
    Nov 9 at 21:48






  • 1




    it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
    – Osiris
    Nov 9 at 21:52












  • OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
    – user3629249
    Nov 10 at 0:23










  • regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
    – user3629249
    Nov 10 at 0:26








4




4




When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
– John Bollinger
Nov 9 at 21:47






When you fork(), the original process and the child both continue from the point of the fork, initially with the same state (subject to some exceptions that don't matter here). In particular, in your case both continue to execute the loop, independently. If that doesn't answer the question then I'm afraid you're going to need to explain your more clearly what it is that confuses you.
– John Bollinger
Nov 9 at 21:47














You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
– John Bollinger
Nov 9 at 21:48




You might find it helpful to draw out a process tree, or to write out a table of events for each of the processes.
– John Bollinger
Nov 9 at 21:48




1




1




it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
– Osiris
Nov 9 at 21:52






it cannot explain the value of the variable "i" in the root process. You actually only print i of the root process one time at the end. In the loop you only print when fork() returns 0 and that only applies for child processes.
– Osiris
Nov 9 at 21:52














OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
– user3629249
Nov 10 at 0:23




OT: When the parameters to main() argc and argv are not going to be used, to avoid the compiler outputting warning messages about the unused variables, use the signature: int main( void )
– user3629249
Nov 10 at 0:23












regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
– user3629249
Nov 10 at 0:26




regarding: if(pid == 0) { total = total + i; printf("n"); printf("Child process %dn", getpid()); printf("Parent process %dn", getppid()); printf("i = %dn", i); } at the end of the child process, MUST have an exit( 0 ); statement, otherwise the execution of the child will continue around the loop
– user3629249
Nov 10 at 0:26












1 Answer
1






active

oldest

votes

















up vote
1
down vote



accepted










the following corrected code:




  1. cleanly compiles

  2. performs the desired functionality

  3. clearly shows that total in the parent is no changed by the child processes


and now, the proposed code:



#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/wait.h>

int total = 0;


int main( void ) // <<-- corrected statement
{
int i, pid;

for(i = 1; i < 3; ++i)
{
pid = fork();

if(pid == 0)
{
total = total + i;
printf( "n") ;
printf( "Child process %dn", getpid() );
printf( "Parent process %dn", getppid() );
printf( "i = %dn", i );
exit( 0 ); // <<-- added statement
}

else
{
waitpid( pid, NULL, 0 );
}
}

printf( "Child process (end) %dn", getpid() );
printf( "Parent process (end) %dn", getppid() );
printf( "total = %dn", total );
printf( "i = %dn", i );
exit( 0 );
}


the output of the above code is:



Child process 10378
Parent process 10377
i = 1

Child process 10379
Parent process 10377
i = 2
Child process (end) 10377
Parent process (end) 10375
total = 0
i = 3


however, the code fails to check for the error case from the function: fork() so will be open to a major failure if the call to fork() fails. I.E. the code should be (also) checking for a returned value of -1 from the call to fork() and calling



if( pid < 0 )
{
perror( "fork failed");
exit( 1 );`
}





share|improve this answer





















    Your Answer






    StackExchange.ifUsing("editor", function () {
    StackExchange.using("externalEditor", function () {
    StackExchange.using("snippets", function () {
    StackExchange.snippets.init();
    });
    });
    }, "code-snippets");

    StackExchange.ready(function() {
    var channelOptions = {
    tags: "".split(" "),
    id: "1"
    };
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function() {
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled) {
    StackExchange.using("snippets", function() {
    createEditor();
    });
    }
    else {
    createEditor();
    }
    });

    function createEditor() {
    StackExchange.prepareEditor({
    heartbeatType: 'answer',
    convertImagesToLinks: true,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: 10,
    bindNavPrevention: true,
    postfix: "",
    imageUploader: {
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    },
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    });


    }
    });














    draft saved

    draft discarded


















    StackExchange.ready(
    function () {
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53233502%2fproblem-to-understand-how-it-works-theses-processes%23new-answer', 'question_page');
    }
    );

    Post as a guest















    Required, but never shown

























    1 Answer
    1






    active

    oldest

    votes








    1 Answer
    1






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes








    up vote
    1
    down vote



    accepted










    the following corrected code:




    1. cleanly compiles

    2. performs the desired functionality

    3. clearly shows that total in the parent is no changed by the child processes


    and now, the proposed code:



    #include <stdio.h>
    #include <stdlib.h>
    #include <unistd.h>
    #include <sys/wait.h>

    int total = 0;


    int main( void ) // <<-- corrected statement
    {
    int i, pid;

    for(i = 1; i < 3; ++i)
    {
    pid = fork();

    if(pid == 0)
    {
    total = total + i;
    printf( "n") ;
    printf( "Child process %dn", getpid() );
    printf( "Parent process %dn", getppid() );
    printf( "i = %dn", i );
    exit( 0 ); // <<-- added statement
    }

    else
    {
    waitpid( pid, NULL, 0 );
    }
    }

    printf( "Child process (end) %dn", getpid() );
    printf( "Parent process (end) %dn", getppid() );
    printf( "total = %dn", total );
    printf( "i = %dn", i );
    exit( 0 );
    }


    the output of the above code is:



    Child process 10378
    Parent process 10377
    i = 1

    Child process 10379
    Parent process 10377
    i = 2
    Child process (end) 10377
    Parent process (end) 10375
    total = 0
    i = 3


    however, the code fails to check for the error case from the function: fork() so will be open to a major failure if the call to fork() fails. I.E. the code should be (also) checking for a returned value of -1 from the call to fork() and calling



    if( pid < 0 )
    {
    perror( "fork failed");
    exit( 1 );`
    }





    share|improve this answer

























      up vote
      1
      down vote



      accepted










      the following corrected code:




      1. cleanly compiles

      2. performs the desired functionality

      3. clearly shows that total in the parent is no changed by the child processes


      and now, the proposed code:



      #include <stdio.h>
      #include <stdlib.h>
      #include <unistd.h>
      #include <sys/wait.h>

      int total = 0;


      int main( void ) // <<-- corrected statement
      {
      int i, pid;

      for(i = 1; i < 3; ++i)
      {
      pid = fork();

      if(pid == 0)
      {
      total = total + i;
      printf( "n") ;
      printf( "Child process %dn", getpid() );
      printf( "Parent process %dn", getppid() );
      printf( "i = %dn", i );
      exit( 0 ); // <<-- added statement
      }

      else
      {
      waitpid( pid, NULL, 0 );
      }
      }

      printf( "Child process (end) %dn", getpid() );
      printf( "Parent process (end) %dn", getppid() );
      printf( "total = %dn", total );
      printf( "i = %dn", i );
      exit( 0 );
      }


      the output of the above code is:



      Child process 10378
      Parent process 10377
      i = 1

      Child process 10379
      Parent process 10377
      i = 2
      Child process (end) 10377
      Parent process (end) 10375
      total = 0
      i = 3


      however, the code fails to check for the error case from the function: fork() so will be open to a major failure if the call to fork() fails. I.E. the code should be (also) checking for a returned value of -1 from the call to fork() and calling



      if( pid < 0 )
      {
      perror( "fork failed");
      exit( 1 );`
      }





      share|improve this answer























        up vote
        1
        down vote



        accepted







        up vote
        1
        down vote



        accepted






        the following corrected code:




        1. cleanly compiles

        2. performs the desired functionality

        3. clearly shows that total in the parent is no changed by the child processes


        and now, the proposed code:



        #include <stdio.h>
        #include <stdlib.h>
        #include <unistd.h>
        #include <sys/wait.h>

        int total = 0;


        int main( void ) // <<-- corrected statement
        {
        int i, pid;

        for(i = 1; i < 3; ++i)
        {
        pid = fork();

        if(pid == 0)
        {
        total = total + i;
        printf( "n") ;
        printf( "Child process %dn", getpid() );
        printf( "Parent process %dn", getppid() );
        printf( "i = %dn", i );
        exit( 0 ); // <<-- added statement
        }

        else
        {
        waitpid( pid, NULL, 0 );
        }
        }

        printf( "Child process (end) %dn", getpid() );
        printf( "Parent process (end) %dn", getppid() );
        printf( "total = %dn", total );
        printf( "i = %dn", i );
        exit( 0 );
        }


        the output of the above code is:



        Child process 10378
        Parent process 10377
        i = 1

        Child process 10379
        Parent process 10377
        i = 2
        Child process (end) 10377
        Parent process (end) 10375
        total = 0
        i = 3


        however, the code fails to check for the error case from the function: fork() so will be open to a major failure if the call to fork() fails. I.E. the code should be (also) checking for a returned value of -1 from the call to fork() and calling



        if( pid < 0 )
        {
        perror( "fork failed");
        exit( 1 );`
        }





        share|improve this answer












        the following corrected code:




        1. cleanly compiles

        2. performs the desired functionality

        3. clearly shows that total in the parent is no changed by the child processes


        and now, the proposed code:



        #include <stdio.h>
        #include <stdlib.h>
        #include <unistd.h>
        #include <sys/wait.h>

        int total = 0;


        int main( void ) // <<-- corrected statement
        {
        int i, pid;

        for(i = 1; i < 3; ++i)
        {
        pid = fork();

        if(pid == 0)
        {
        total = total + i;
        printf( "n") ;
        printf( "Child process %dn", getpid() );
        printf( "Parent process %dn", getppid() );
        printf( "i = %dn", i );
        exit( 0 ); // <<-- added statement
        }

        else
        {
        waitpid( pid, NULL, 0 );
        }
        }

        printf( "Child process (end) %dn", getpid() );
        printf( "Parent process (end) %dn", getppid() );
        printf( "total = %dn", total );
        printf( "i = %dn", i );
        exit( 0 );
        }


        the output of the above code is:



        Child process 10378
        Parent process 10377
        i = 1

        Child process 10379
        Parent process 10377
        i = 2
        Child process (end) 10377
        Parent process (end) 10375
        total = 0
        i = 3


        however, the code fails to check for the error case from the function: fork() so will be open to a major failure if the call to fork() fails. I.E. the code should be (also) checking for a returned value of -1 from the call to fork() and calling



        if( pid < 0 )
        {
        perror( "fork failed");
        exit( 1 );`
        }






        share|improve this answer












        share|improve this answer



        share|improve this answer










        answered Nov 10 at 0:38









        user3629249

        10.8k1914




        10.8k1914






























            draft saved

            draft discarded




















































            Thanks for contributing an answer to Stack Overflow!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.





            Some of your past answers have not been well-received, and you're in danger of being blocked from answering.


            Please pay close attention to the following guidance:


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53233502%2fproblem-to-understand-how-it-works-theses-processes%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            Schultheiß

            Liste der Kulturdenkmale in Wilsdruff

            Android Play Services Check