ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/AnyEvent-Fork-RPC/RPC/Sync.pm
Revision: 1.22
Committed: Sun Sep 15 20:18:14 2019 UTC (6 years, 9 months ago) by root
Branch: MAIN
CVS Tags: HEAD
Changes since 1.21: +3 -0 lines
Log Message:
2.0

File Contents

# Content
1 package AnyEvent::Fork::RPC::Sync;
2
3 use common::sense; # actually required to avoid spurious warnings...
4
5 our $VERSION = 2; # protocol version
6
7 # declare only
8 sub AnyEvent::Fork::RPC::event;
9
10 # always successful
11 sub AnyEvent::Fork::RPC::flush { 1 }
12
13 sub do_exit { exit } # workaround for perl 5.14 and below
14
15 # the goal here is to keep this simple, small and efficient
16 sub run {
17 my %kv = splice @_, pop;
18
19 my $rfh = shift;
20 my $wfh = fileno $rfh ? $rfh : *STDOUT;
21
22 my $function = delete $kv{function};
23 my $serialiser = delete $kv{serialiser};
24 my $rlen = delete $kv{rlen};
25
26 $0 =~ s/^(\d+).*$/$1 $function/s;
27
28 {
29 package main;
30 my $init = delete $kv{init};
31 &$init if length $init;
32 $function = \&$function; # resolve function early for extra speed
33 }
34
35 %kv = (); # save some very small amount of memory
36
37 my ($f, $t) = eval $serialiser; die $@ if $@;
38
39 my $write = sub {
40 my $got = syswrite $wfh, $_[0];
41
42 while ($got < length $_[0]) {
43 my $len = syswrite $wfh, $_[0], 1<<30, $got;
44
45 defined $len
46 or die "AnyEvent::Fork::RPC::Sync: write error ($!), parent gone?";
47
48 $got += $len;
49 }
50 };
51
52 *AnyEvent::Fork::RPC::event = sub {
53 $write->(pack "NN/a*", 0, &$f);
54 };
55
56 my $rbuf;
57
58 while (sysread $rfh, $rbuf, $rlen - length $rbuf, length $rbuf) {
59 $rlen = $rlen * 2 + 16 if $rlen - 128 < length $rbuf;
60
61 while () {
62 last if 4 > length $rbuf;
63 my $len = unpack "N", $rbuf;
64 last if 4 + $len > length $rbuf;
65
66 $write->(pack "NN/a*", 1, $f->($function->($t->(substr $rbuf, 4, $len))));
67
68 substr $rbuf, 0, 4 + $len, "";
69 }
70 }
71
72 shutdown $wfh, 1;
73 exit; # work around broken win32 perls
74 }
75
76 1
77