Returning data from forked processes
I wrapped all the solutions I found along the way (some other problems like user exiting + piping-buffers) into ruby parallel gem. Now it is as easy as:
results = Parallel.map([1,2,3],:in_processes=>4) do |i|
execute_something(i)
end
or
results = Parallel.map([1,2,3],:in_threads=>4) do |i|
execute_something(i)
end
return value from child process c
You're attempting to read status
via the WIFEXITED
function, but you never give it a value. Attempting to read an uninitialized value invokes undefined behavior.
You need to call the wait
function, which tells the parent to wait for a child to finish and receive its return code:
wait(&status);
if (WIFEXITED(status)){
int returned = WEXITSTATUS(status);
printf("exited normally with status %d\n",returned);
}
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.
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
How is it possible for fork() to return two values?
If you read, build, and run the following program you should get a better idea of what is going on.
#include <stdio.h>
#include <unistd.h>
int main(void) {
pid_t fk;
printf("\tbefore fork my pid = %lu\n", (unsigned long)getpid() );
fflush(stdout); /* This may keep the above print
statement from outputing twice. */
fk = fork(); /* The OS kernel makes a copy of the current process here */
printf("fork returned %lu and now my pid = %lu\n",
(unsigned long)fk, (unsigned long)getpid() );
return 0;
}
The reason that the fflush(stdout)
is needed is that since the process is duplicated by fork that means that the buffering done for stdout by stdio is duplicated as well. The "\n" at the end of that first print statement may make it go ahead and flush stdout, but this isn't guaranteed.
How to get return value from CHILD PROCESS?
What you are looking for is wait() or waitpid().
Related Topics
Get Sidekiq to Execute a Job Immediately
How to Write Rake Task to Import Data to Rails App
Converting from Xml Name-Values into Simple Hash
How to Declare a String with Both Single and Double Quotes in Yaml
Why Can't I Use an Integer as a Key Using the New Ruby 1.9.2 Hash Syntax
Ruby on Rails Display Half a Star for a Decimal Rating, E.G. 4.5
Breaking Up Long Strings on Multiple Lines in Ruby Without Stripping Newlines
Directly Accessing an Instance Variable VS. Using an Accessor Method
Rails Unable to Convert Unpermitted Parameters to Hash
How to Format This International Phone Number in Rails
Finding If a Sentence Contains a Specific Phrase in Ruby
In Ruby Why Does Nil.Id Return 4
How to Escape #{ from String Interpolation
Can't Install Gems Because "Undefined Method 'Invoke_With_Build_Args' for Nil:Nilclass"