Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to get return value from child process to parent?

I'm supposed to return the sum of first 12 terms of Fibonacci series from child process to parent one but instead having 377, parent gets 30976.

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

int main(int argc, char *argv[])
{
    pid_t childpid;
    int i, fib_sum=0, fib1=1, fib2=1, temp, status;

    childpid=fork();

    if(childpid!=0)
    {
        wait(&status);
        fprintf(stderr, "%d\n", status);
    }
    else
    {
        for(i=1; i<=12; i++)
        {
            temp=fib1;
            fib_sum=fib1+fib2;
            fib1=fib_sum;
            fib2=temp;
        }
        fprintf(stderr, "%d\n", fib_sum);
        return fib_sum;
    }
}

What am I doing wrong?

like image 285
Alopex Avatar asked Mar 30 '18 20:03

Alopex


People also ask

How do you find the return value of a child process?

To obtain the return value from another program run as a child process your code must fork. The child fork (pid zero) contains the execl() function to “execute and leave” another program. The parent fork contains the wait() function, which suspends execution until the child process completes its task.

How do you send data from child process to parent process?

Write a C program in which the child process takes an input array and send it to the parent process using pipe() and fork() and then print it in the parent process.

What is the return value of fork () for a parent process?

fork() returns 0 in the child process and positive integer in the parent process.

What happens when a child process returns?

Child process increments val prints it and returns. Once it returns parent process resumes and executes further by incrementing var , printing its value and then returning from it from the main() .


2 Answers

I'm supposed to return the sum of first 12 terms of Fibonacci series from child process to parent one but instead having 377, parent gets 30976.

Process exit status is limited in value, therefore it is not the best way to communicate a value between child and parent.

One of the solution is to pass the calculated value using pipes.

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

int main(int argc, char *argv[])
{
    pid_t childpid;
    int i, fib_sum=0, fib1=1, fib2=1, temp, status;

    int fd[2];
    int val = 0;

    // create pipe descriptors
    pipe(fd);

    childpid = fork();
    if(childpid != 0)  // parent
    {
        close(fd[1]);
        // read the data (blocking operation)
        read(fd[0], &val, sizeof(val));

        printf("Parent received value: %d\n", val);
        // close the read-descriptor
        close(fd[0]);
    }
    else  // child
    {
        // writing only, no need for read-descriptor:
        close(fd[0]);

        for(i=1; i<=12; i++)
        {
            temp = fib1;
            fib_sum = fib1+fib2;
            fib1 = fib_sum;
            fib2 = temp;
        }

        // send the value on the write-descriptor:
        write(fd[1], &fib_sum, sizeof(fib_sum)); 
        printf("Child send value: %d\n", fib_sum);

        // close the write descriptor:
        close(fd[1]);

        return fib_sum;
    }
}

Test:

Child send value: 377                                                                                                                         
Parent received value: 377
like image 175
sg7 Avatar answered Sep 19 '22 20:09

sg7


If you can't use pipes, which would be the optimal solution here, you could save the result to a file that the parent would read from. Pass the name of the file to save the result to from parent to child. In your child process, you would do:

int main(int argc, char *argv[])
{
    int fib_sum=0;
    if (argc <= 1)
    {
        print_usage();
        return 1;
    }
    //... calculate fib_sum
    FILE *f = fopen(argv[1], "w");
    if (f == NULL)
    {
        printf("Error opening file!\n");
        return 1;
    }
    fprintf(f, "%d", fib_sum);
    return 0;
}

Then in your parent process:

int n = 0;
FILE* f;
//... spawn child and wait
FILE *f = fopen(file_name, "r");
fscanf(f, "%d", &n);
like image 36
mnistic Avatar answered Sep 19 '22 20:09

mnistic