in reply to Re^3: Cannot catch ALRM signal for timeout
in thread Cannot catch ALRM signal for timeout

but it still does not work

What doesn't work?

The timeout works fine. I changed

my $scheme_pid = open (WORKER, "worker_program < $input |")
to
my $scheme_pid = open (WORKER, "-|", $^X, '-e', '$|=1; for (1..100) { +print "%d\n", $_*$t; sleep(2) }')

and the timeout triggered. The log file contained only "0".

You'll need to fix the return 1, though. That will only return out of the eval, not out of the sub.

Replies are listed 'Best First'.
Re^5: Cannot catch ALRM signal for timeout
by Magice (Novice) on Dec 08, 2009 at 22:28 UTC
    It still stuck, not alarmed for some reasons. My code right now has become:
    sub process_scheme{ my ($output_file) = @_; open (OUTPUT_FILE, ">", $output_file) || die "cannot open log file +"; my $scheme_pid = open (SCHEME, "./t.pl | ") || die "cannot pipe sc +heme"; my $str = ""; MAIN: while (1) { eval{ local $SIG{ALRM} = sub { die "alarm\n" }; # NB: \n require +d alarm 5;#$allow_time; if (eof(SCHEME)){ close OUTPUT_FILE; close SCHEME; last MAIN; } $str = <SCHEME>; alarm 0; }; if ($@) { close OUTPUT_FILE; kill $scheme_pid; close SCHEME; return -$current_player; } # process the line print OUTPUT_FILE $str; } return 1; }
    where the t.pl is
    while(1){};
    The script gets stuck, waiting forever, not stopping/returning anything
      kill $scheme_pid;

      You probably meant something like

      kill INT => $scheme_pid;

      As you have it, kill would try to send the signal number $scheme_pid to no processes — so nothing happens, effectively...

      As a result, your code hangs in the implicit wait behind close SCHEME, because the child process is still alive.

      what makes you think it's stuck? Are you sure it's really stuck and that you're not suffering from buffering? Add
      OUTPUT_FILE->autoflush(1);
      after the open. You'll need
      use IO::Handle qw( );
      at the top.