line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Parallel::SubArray; |
2
|
|
|
|
|
|
|
require v5.8.6; |
3
|
|
|
|
|
|
|
our $VERSION = 0.6; |
4
|
15
|
|
|
15
|
|
989565
|
use strict; |
|
15
|
|
|
|
|
45
|
|
|
15
|
|
|
|
|
660
|
|
5
|
15
|
|
|
15
|
|
19065
|
use Storable qw(store_fd fd_retrieve); |
|
15
|
|
|
|
|
79680
|
|
|
15
|
|
|
|
|
1500
|
|
6
|
15
|
|
|
15
|
|
150
|
use Exporter 'import'; |
|
15
|
|
|
|
|
135
|
|
|
15
|
|
|
|
|
10905
|
|
7
|
|
|
|
|
|
|
our @EXPORT_OK = qw(par); |
8
|
|
|
|
|
|
|
|
9
|
|
|
|
|
|
|
sub par { |
10
|
21
|
|
|
21
|
1
|
867
|
my( $timeout ) = @_; |
11
|
|
|
|
|
|
|
sub { |
12
|
29
|
|
|
29
|
|
225717
|
my @subs = @{ shift(@_) }; |
|
29
|
|
|
|
|
159
|
|
13
|
29
|
|
|
|
|
46
|
my %rets; |
14
|
29
|
|
|
|
|
47
|
my $c = 0; |
15
|
29
|
|
|
|
|
104
|
for my $sub ( @subs ) { |
16
|
105
|
|
|
|
|
183
|
$c++; |
17
|
105
|
|
|
|
|
142
|
my( $parent_w, $child_r ); |
18
|
105
|
|
|
|
|
6732
|
pipe( $child_r, $parent_w ); |
19
|
105
|
|
|
|
|
4129
|
select((select($parent_w ), $| = 1)[0]); |
20
|
105
|
100
|
|
|
|
218992
|
if( my $pid = fork ) { |
21
|
87
|
|
|
|
|
4641
|
close $parent_w; |
22
|
87
|
|
|
|
|
10541
|
$rets{ $pid } = { fd => $child_r, |
23
|
|
|
|
|
|
|
ord => $c |
24
|
|
|
|
|
|
|
}; |
25
|
|
|
|
|
|
|
} else { |
26
|
18
|
50
|
|
|
|
1679
|
die "Cannot fork: $!" unless defined $pid; |
27
|
18
|
|
|
|
|
1200
|
close $child_r; |
28
|
|
|
|
|
|
|
my $exit = sub { |
29
|
14
|
|
|
|
|
138
|
my( $save_val, $exit_val ) = @_; |
30
|
14
|
|
|
|
|
726
|
store_fd $save_val, $parent_w; |
31
|
14
|
|
|
|
|
5257
|
close $parent_w; |
32
|
14
|
|
|
|
|
9114
|
exit $exit_val; |
33
|
18
|
|
|
|
|
3204
|
}; |
34
|
18
|
|
|
|
|
5690
|
local $SIG{ALRM} = sub { $exit->( ['TIMEOUT'], 1 ) }; |
|
2
|
|
|
|
|
6000236
|
|
35
|
18
|
|
100
|
|
|
1753
|
alarm( $timeout || 0 ); |
36
|
18
|
|
|
|
|
471
|
my $ret = eval{ $sub->() }; |
|
18
|
|
|
|
|
958
|
|
37
|
12
|
|
|
|
|
8002486
|
my $err = $@; |
38
|
12
|
|
|
|
|
228
|
alarm( 0 ); |
39
|
12
|
100
|
|
|
|
317
|
$exit->( [$err], 1 ) if $err; |
40
|
10
|
|
|
|
|
258
|
$exit->( $ret , 0 ); |
41
|
|
|
|
|
|
|
} |
42
|
|
|
|
|
|
|
} |
43
|
11
|
|
|
|
|
308
|
while(1) { |
44
|
60
|
|
|
|
|
33412740
|
my $pid = wait(); |
45
|
60
|
|
|
|
|
61792
|
my $err = $?; |
46
|
60
|
100
|
66
|
|
|
1649
|
last if( $pid == -1 or not @subs ); |
47
|
49
|
50
|
|
|
|
482
|
next if not exists $rets{ $pid }; |
48
|
49
|
100
|
|
|
|
343
|
if( $err ) { |
49
|
18
|
|
|
|
|
502
|
$rets{ $pid }->{err} = fd_retrieve( $rets{ $pid }->{fd} )->[0]; |
50
|
|
|
|
|
|
|
} else { |
51
|
31
|
|
|
|
|
818
|
$rets{ $pid }->{val} = fd_retrieve( $rets{ $pid }->{fd} ); |
52
|
|
|
|
|
|
|
} |
53
|
49
|
|
|
|
|
5279
|
close $rets{ $pid }->{fd}; |
54
|
49
|
|
|
|
|
218
|
pop @subs; |
55
|
|
|
|
|
|
|
} |
56
|
|
|
|
|
|
|
my $r = sub { |
57
|
12
|
|
|
|
|
101
|
my( $key ) = @_; |
58
|
|
|
|
|
|
|
# can be optimized |
59
|
54
|
|
|
|
|
427
|
[ map { $rets{$_}->{ $key } } |
|
62
|
|
|
|
|
276
|
|
60
|
12
|
|
|
|
|
312
|
sort { $rets{$a}->{ord} <=> $rets{$b}->{ord} } |
61
|
|
|
|
|
|
|
keys %rets |
62
|
|
|
|
|
|
|
]; |
63
|
11
|
|
|
|
|
217
|
}; |
64
|
11
|
100
|
|
|
|
178
|
return wantarray ? ( $r->('val'), $r->('err') ) : $r->('val'); |
65
|
|
|
|
|
|
|
} |
66
|
21
|
|
|
|
|
663
|
} |
67
|
|
|
|
|
|
|
|
68
|
|
|
|
|
|
|
1; |
69
|
|
|
|
|
|
|
__END__ |