[Chicago-talk] Do I need a fork for this?

Dan Rench drench+chipm at gmail.com
Sun Jan 11 15:48:34 PST 2009

Since nobody's biting...

On Fri, Jan 9, 2009 at 3:05 PM, Richard Reina <richard at rushlogistics.com> wrote:
>  What kind of return
>> values do you expect from list_compiler()?
> An array reference and a hash reference
> ($TR_array, $cr_hash) = list_compiler();

Here's one way to do it:

use Storable qw(store_fd fd_retrieve);

sub bg_run {
   my $subref = shift;

   my $pid = open(H, '-|');

   if (! defined $pid) {
       die "Can't fork: $!";

   if ($pid) { # parent (reader)
       return sub { return fd_retrieve(\*H) }; # get return value from child
   else { # child (writer)
       my $r = $subref->(@_); # run the subroutine
       store_fd($r, *STDOUT); # send return value to the parent
       exit 0;

my $get_result = bg_run(sub { return [ list_compiler() ] });

# bg_run() just started a background process to run list_compiler()
# $get_result is a reference to a sub that, um, gets the results.

# Some dummy user input:
print 'Enter something while we wait: ';
my $in = <STDIN>; chomp $in;
print "You entered '$in'.\n";

# If list_compiler() is already done, $get_result->() will
# return immediately. Otherwise we wait until the result comes in:

my ($TR_array, $cr_hash) = @{$get_result->()}};

If you can change list_compiler() to return an array ref instead of
the 2-element list, the bg_run() call could go like this instead:

my $get_result = bg_run(\&list_compiler);

If list_compliler() needs arguments:

my $get_result = bg_run(\&list_compiler, $arg1, $arg2, ...);

There's a lot more you could do with this. You could add something to
detect when list_compliler() is still working to let the user know
your program isn't hanging, it's just waiting an a result.

More information about the Chicago-talk mailing list