… | |
… | |
71 | |
71 | |
72 | use Errno (); |
72 | use Errno (); |
73 | use Fcntl (); |
73 | use Fcntl (); |
74 | use POSIX (); |
74 | use POSIX (); |
75 | |
75 | |
76 | our $VERSION = '2.1'; |
76 | our $VERSION = '2.3'; |
77 | |
77 | |
78 | our $FD_MAX = eval { POSIX::sysconf (&POSIX::_SC_OPEN_MAX) - 1 } || 1023; |
78 | our $FD_MAX = eval { POSIX::sysconf (&POSIX::_SC_OPEN_MAX) - 1 } || 1023; |
79 | |
79 | |
80 | # this is the forked server code, could/should be bundled as it's own file |
80 | # this is the forked server code, could/should be bundled as it's own file |
81 | |
81 | |
… | |
… | |
108 | |
108 | |
109 | [1, $DBH->{$attr_name}] |
109 | [1, $DBH->{$attr_name}] |
110 | } |
110 | } |
111 | |
111 | |
112 | sub req_begin_work { |
112 | sub req_begin_work { |
113 | [1, $DBH->begin_work or die [$DBI::errstr]] |
113 | [1, $DBH->begin_work || die [$DBI::errstr]] |
114 | } |
114 | } |
115 | |
115 | |
116 | sub req_commit { |
116 | sub req_commit { |
117 | [1, $DBH->commit or die [$DBI::errstr]] |
117 | [1, $DBH->commit || die [$DBI::errstr]] |
118 | } |
118 | } |
119 | |
119 | |
120 | sub req_rollback { |
120 | sub req_rollback { |
121 | [1, $DBH->rollback or die [$DBI::errstr]] |
121 | [1, $DBH->rollback || die [$DBI::errstr]] |
122 | } |
122 | } |
123 | |
123 | |
124 | sub req_func { |
124 | sub req_func { |
125 | my (undef, $arg_string, $function) = @{+shift}; |
125 | my (undef, $arg_string, $function) = @{+shift}; |
126 | my @args = eval $arg_string; |
126 | my @args = eval $arg_string; |
… | |
… | |
304 | Scalar::Util::weaken (my $self = $self); |
304 | Scalar::Util::weaken (my $self = $self); |
305 | |
305 | |
306 | $self->{rw} = AE::io $client, 0, sub { |
306 | $self->{rw} = AE::io $client, 0, sub { |
307 | return unless $self; |
307 | return unless $self; |
308 | |
308 | |
309 | $self->{last_activity} = AE::now; |
|
|
310 | |
|
|
311 | my $len = sysread $client, $rbuf, 65536, length $rbuf; |
309 | my $len = sysread $client, $rbuf, 65536, length $rbuf; |
312 | |
310 | |
313 | if ($len > 0) { |
311 | if ($len > 0) { |
314 | # we received data, so reset the timer |
312 | # we received data, so reset the timer |
|
|
313 | $self->{last_activity} = AE::now; |
315 | |
314 | |
316 | while () { |
315 | while () { |
317 | my $len = unpack "L", $rbuf; |
316 | my $len = unpack "L", $rbuf; |
318 | |
317 | |
319 | # full response available? |
318 | # full response available? |
… | |
… | |
335 | $self->_error ($res->[1], @$req, $res->[2]) # error, request record, is_fatal |
334 | $self->_error ($res->[1], @$req, $res->[2]) # error, request record, is_fatal |
336 | if $self; # cb() could have deleted it |
335 | if $self; # cb() could have deleted it |
337 | } |
336 | } |
338 | |
337 | |
339 | # no more queued requests, so become idle |
338 | # no more queued requests, so become idle |
|
|
339 | if ($self && !@{ $self->{queue} }) { |
340 | undef $self->{last_activity} |
340 | undef $self->{last_activity}; |
341 | if $self && !@{ $self->{queue} }; |
341 | $self->{tw_cb}->(); |
|
|
342 | } |
342 | } |
343 | } |
343 | |
344 | |
344 | } elsif (defined $len) { |
345 | } elsif (defined $len) { |
345 | # todo, caller? |
346 | # todo, caller? |
346 | $self->_error ("unexpected eof", @caller, 1); |
347 | $self->_error ("unexpected eof", @caller, 1); |
… | |
… | |
432 | |
433 | |
433 | sub kill_child { |
434 | sub kill_child { |
434 | my $self = shift; |
435 | my $self = shift; |
435 | |
436 | |
436 | if (my $pid = delete $self->{child_pid}) { |
437 | if (my $pid = delete $self->{child_pid}) { |
|
|
438 | # kill and reap process |
|
|
439 | my $kid_watcher; $kid_watcher = AE::child $pid, sub { |
|
|
440 | undef $kid_watcher; |
|
|
441 | }; |
437 | kill TERM => $pid; |
442 | kill TERM => $pid; |
438 | } |
443 | } |
|
|
444 | |
439 | close delete $self->{fh}; |
445 | close delete $self->{fh}; |
440 | } |
446 | } |
441 | |
447 | |
442 | sub DESTROY { |
448 | sub DESTROY { |
443 | shift->kill_child; |
449 | shift->kill_child; |