| Newsgroups |
perl.poe |
| Message-ID |
<[email protected]> |
Hello,
Ah, Let me fix a few bugs/typos in your code then it'll work as
intended!
1. You do not need to run waitpid() yourself, POE::Kernel does it
for you :) To be precise, the sig_child event is delivered *after*
POE::Kernel has run waitpid. Maybe the
docs need to be updated to make this very clear?
2. In *any* signal handler ( other than sig_child, ha! ) you need to
let POE::Kernel know that it's OK to continue execution. This means
you need to run POE::Kernel->sig_handled() in your sig handler (
event "down" ) or POE will commence shutdown operations. Again, the
POE::Kernel docs about signals
are a lengthy read, but I believe it explains everything? In your
case, since you didn't do it the kernel shut down *before* it had a
chance to fire the sig_child event.
3. In event "sig_child" you have a minor typo: $_[ARG1] not [ARG1]
heh :)
4. Finally, in order to gracefully terminate the program you need to
delete the wheel in the "sig_child" event so the reference counts for
your session
will go down and POE::Kernel will commence shutdown. This is
explained somewhat in the POE::Wheel::Run docs. ( also in POE::Wheel too )
Here's a patch against your code that DWYMTD ( does what you meant
to do :) Yeah, coding stuff in POE takes a while to get your head around
because
there is a lot of things that interact. I know that the docs are HUGE
and doesn't necessarily explain everything. That's why dhoss++ and
rcaputo++ are working
on a new tutorial/book for POE. However, if you have ideas on how to
make the docs clearer - please let us know! Have fun hacking Perl/POE :)
~Apocalypse
apoc@blackhole:~$ diff -urbd testsigchld_mike.pl testsigchld_myver.pl
--- testsigchld_mike.pl 2010-04-21 10:06:53.000000000 -0700
+++ testsigchld_myver.pl 2010-04-21 10:09:20.000000000 -0700
@@ -24,10 +24,11 @@
down => sub {
warn "killing process";
$_[HEAP]->{wheel}->kill();
+ $_[KERNEL]->sig_handled();
},
sig_child => sub {
- warn("waitpid for " . [ARG1]);
- waitpid $_[ARG1], 0;
+ warn("child pid exited: " . $_[ARG1]);
+ delete $_[HEAP]->{wheel};
},
});
Mike Schilli wrote:
> I must be missing something obvious, as I'm getting
>
> in start at ./wheel line 14.
> starting ... at ./wheel line 27.
> killing process at ./wheel line 30.
> 7353: !!! Child process PID:7354 reaped:
> 7353: !!! Your program may not be using sig_child() to reap
> processes.
> 7353: !!! In extreme cases, your program can force a system reboot
> 7353: !!! if this resource leakage is not corrected.
>
> although the code catches the sig_child:
>
> use strict;
> use warnings;
> use POE;
> use POE::Wheel::Run;
>
> my $session = POE::Session->create(
> inline_states => {
> _start => sub {
> warn "in start";
> $_[HEAP]->{wheel} =
> POE::Wheel::Run->new(
> Program => "sleep",
> ProgramArgs => [60],
> CloseEvent => "closing",
> ErrorEvent => "closing",
> StderrEvent => "ignore",
> );
>
> $poe_kernel->sig_child($_[HEAP]->{wheel}->PID,
> "sig_child");
> $poe_kernel->sig( "INT" => "down" );
> warn "starting ...";
> },
> down => sub {
> warn "killing process";
> $_[HEAP]->{wheel}->kill();
> },
> sig_child => sub {
> warn("waitpid for " . [ARG1]);
> waitpid $_[ARG1], 0;
> },
> });
>
> $poe_kernel->run();
>
> Looks like the 'sig_child' handler is never run ... suggestions?
>
> -- Mike
>
> Mike Schilli
> [email protected]