1

I am figuring out how threads with fork work and here is the code that I have tried to make some sense of. (Pardon the errors in the code)

#include <stdio.h>
#include <pthread.h>
#include <unistd.h>
#include <sys/wait.h>
void* f(int threadnum) {
    int i;
    i = fork();

    if (i == 0) {   // child process
        printf("(%d) child says hello\n", threadnum);
    } else {
        printf("(%d) parent[%d] says hello\n", threadnum, i);
        wait(NULL);
        int new = fork();
        if (new != 0){
            printf("(%d) parent[%d] says hello to grandchild\n", threadnum, new);
            wait(NULL);
        } else 
            printf("(%d) grandchild says hello\n", threadnum);
    }
}

 int main () 
{
    pthread_t pid[2]; 
    for (int i = 0; i < 2; i++) {
        pthread_create(&pid[i], NULL, f, (void *)i);
        printf("Thread created with id [%li]\n", pid[i]);
    }
    for (int i = 0; i < 2; i++){
        pthread_join(pid[i], NULL);
    }
    return 0;
}

And this is the output that i have gotten:

Thread created with id [663664384]
Thread created with id [655271680]
(1) parent[5690] says hello
(0) parent[5691] says hello
(1) child says hello
(1) parent[5692] says hello to grandchild
(0) child says hello
(1) grandchild says hello
(0) parent[5693] says hello to grandchild
(0) grandchild says hello

I don't see much difference as to how threads work differently from having to fork the calling of f() twice. If a single thread executes exit(), how about the whole process? If a single thread calls exec(), how about the other threads?

Kode.Error404
  • 573
  • 5
  • 24
  • Related to (possibly a duplicate of) https://stackoverflow.com/questions/6056903/multithreaded-fork – Jeremy Friesner Nov 18 '19 at 04:17
  • Your code invokes undefined behaviour by not returning a valid value from the thread function. Ensure you have `return 0;` on every exit path from the thread function (unless you have a useful value to return). – Jonathan Leffler Nov 18 '19 at 06:58
  • Note that the 'grandchild' process is actually a second sibling to the first forked process; it has the same parent process. – Jonathan Leffler Nov 18 '19 at 07:00
  • If your program used mutexes, for example, and the sole thread in a forked process needed to use a mutex locked by a different thread in the pre-forked process, then the process is deadlocked — there is no way to release that locked mutex. This is one of the many reasons you have to be careful. Your code isn't using mutexes; that makes it simpler. – Jonathan Leffler Nov 18 '19 at 07:12

1 Answers1

2

You will not see much difference in the behavior with your current code. A major difference between a thread and a process is in the memory layout.

A child thread uses the same virtual memory as the parent, whereas a child process has it's own copy of VM. Hence you can see the difference in the behavior of thread and fork by calling exit() from various places in your code.

If you call exit() from the place where parent says hello (Essentially, from the new thread)process will exit immediately since it's using the same VM. Whereas if the exit() is called from child says hello (Meaning from the new process), rest of the print statements will continue, since the child has it's own memory space.

Rohit Walavalkar
  • 790
  • 9
  • 28