Hello,

I encountered a problem which is best represented as Perl code:

#!/usr/bin/perl use warnings FATAL => qw( all ); use strict; $SIG{ALRM} = sub { print "SIGARLM: main handler\n" }; sub f { local $SIG{ALRM} = sub { print "SIGALRM\n" }; # line 9 } if (fork) { # parent f while 1; } else { # child sleep 1; print "child starting\n"; 1 while kill ALRM => getppid; }

When I run this code, the parent process dies within seconds of the child entering the loop. It looks like the default handler gets occasionally executed (the really default one, terminating the process). I have also seen things like:

Unable to create sub named "" at testdrive/signal.pl line 9.
and (in a less stripped-down chunk of code throwing exceptions instead of printing stuff) just about every possible error message and several impossible ones.

I tested this on Debian and Ubuntu systems, both brand new and several years old, with perls 5.8.4, 5.8.8 and 5.10.0. Setting the signal mask manually (via sigprocmask) doesn't help either. Setting the handler without using local also doesn't change anything. I couldn't reproduce it under strace, due to changes in timing or weird things that strace does to signal handlers, I don't really know.

Any ideas?

Thanks,
Grzegorz Nosek

UPDATE:

Yes, the code is silly. My point is atomicity of setting signal handlers, not the most efficient way of catching SIGALRM :)

UPDATE 2:

local $SIG{FOO} = \&bar; is unsafe (the signal handler gets reset to SIG_DFL for a short moment, possibly crashing the process). I haven't been able to wrap it in sigprocmask safely in any way.

Setting $SIG{FOO} without local is apparently safe.

UPDATE 3:

A signal handler may sometimes leak out of an eval block even when it seems impossible from looking at Perl code. A simple workaround is to yield the CPU to allow signal delivery (Time::HiRes and sleep 1.01e-6 seems sufficient, although sleep 1e-6 is not). I guess it's nasty enough for a workaround.

UPDATE 4:

My real-world code still doesn't work though...


In reply to Setting signal handlers considered unsafe? by gnosek

Title:
Use:  <p> text here (a paragraph) </p>
and:  <code> code here </code>
to format your post, it's "PerlMonks-approved HTML":



  • Posts are HTML formatted. Put <p> </p> tags around your paragraphs. Put <code> </code> tags around your code and data!
  • Titles consisting of a single word are discouraged, and in most cases are disallowed outright.
  • Read Where should I post X? if you're not absolutely sure you're posting in the right place.
  • Please read these before you post! —
  • Posts may use any of the Perl Monks Approved HTML tags:
    a, abbr, b, big, blockquote, br, caption, center, col, colgroup, dd, del, details, div, dl, dt, em, font, h1, h2, h3, h4, h5, h6, hr, i, ins, li, ol, p, pre, readmore, small, span, spoiler, strike, strong, sub, summary, sup, table, tbody, td, tfoot, th, thead, tr, tt, u, ul, wbr
  • You may need to use entities for some characters, as follows. (Exception: Within code tags, you can put the characters literally.)
            For:     Use:
    & &amp;
    < &lt;
    > &gt;
    [ &#91;
    ] &#93;
  • Link using PerlMonks shortcuts! What shortcuts can I use for linking?
  • See Writeup Formatting Tips and other pages linked from there for more info.