1Sys::SigAction(3) User Contributed Perl Documentation Sys::SigAction(3)
2
3
4
6 Sys::SigAction - Perl extension for Consistent Signal Handling
7
9 #do something non-interupt able
10 use Sys::SigAction qw( set_sig_handler );
11 {
12 my $h = set_sig_handler( 'INT' ,'mysubname' ,{ flags => SA_RESTART } );
13 ... do stuff non-interupt able
14 } #signal handler is reset when $h goes out of scope
15
16 or
17
18 #timeout a system call:
19 use Sys::SigAction qw( set_sig_handler );
20 eval {
21 my $h = set_sig_handler( 'ALRM' ,\&mysubname ,{ mask=>[ 'ALRM' ] ,safe=>1 } );
22 alarm(2)
23 ... do something you want to timeout
24 alarm(0);
25 }; #signal handler is reset when $h goes out of scope
26 alarm(0);
27 if ( $@ ) ...
28
29 or
30
31 use Sys::SigAction;
32 my $alarm = 0;
33 eval {
34 my $h = Sys::SigAction::set_sig_handler( 'ALRM' ,sub { $alarm = 1; } );
35 alarm(2)
36 ... do something you want to timeout
37 alarm(0);
38 };
39 alarm(0);
40 if ( $@ or $alarm ) ...
41
42 or
43
44 use Sys::SigAction;
45 my $alarm = 0;
46 Sys::SigAction::set_sig_handler( 'TERM' ,sub { "DUMMY" } );
47 #code from here on uses new handler.... (old handler is forgotten)
48
49 or
50
51 use Sys::SigAction qw( timeout_call );
52 if ( timeout_call( 5 ,sub { $retval = DoSomething( @args ); } )
53 {
54 print "DoSomething() timed out\n" ;
55 }
56
58 This module implements "set_sig_handler()", which sets up a signal han‐
59 dler and (optionally) returns an object which causes the signal handler
60 to be reset to the previous value, when it goes out of scope.
61
62 Also implemented is "timeout_call()" which takes a timeout value and a
63 code reference, and executes the code reference wrapped with an alarm
64 timeout.
65
66 Finally, two convenience routines are defined which allow one to get
67 the signal name from the number -- "sig_name()", and get the signal
68 number from the name -- "sig_number()".
69
71 Prior to version 5.8.0 perl implemented 'unsafe' signal handling. The
72 reason it is consider unsafe, is that there is a risk that a signal
73 will arrive, and be handled while perl is changing internal data struc‐
74 tures. This can result in all kinds of subtle and not so subtle prob‐
75 lems. For this reason it has always been recommended that one do as
76 little as possible in a signal handler, and only variables that already
77 exist be manipulated.
78
79 Perl 5.8.0 and later versions implements 'safe' signal handling on
80 platforms which support the POSIX sigaction() function. This is accom‐
81 plished by having perl note that a signal has arrived, but deferring
82 the execution of the signal handler until such time as it is safe to do
83 so. Unfortunately these changes can break some existing scripts, if
84 they depended on a system routine being interupted by the signal's
85 arrival. The perl 5.8.0 implementation was modified further in version
86 5.8.2.
87
88 From the perl 5.8.2 perlvar man page:
89
90 The default delivery policy of signals changed in Perl 5.8.0
91 from immediate (also known as "unsafe") to deferred, also
92 known as "safe signals".
93
94 The implementation of this changed the "sa_flags" with which the signal
95 handler is installed by perl, and it causes some system routines (like
96 connect()) to return EINTR, instead of another error when the signal
97 arrives. The problem comes when the code that made the system call
98 sees the EINTR code and decides it's going to call it again before
99 returning. Perl doesn't do this but some libraries do, including for
100 instance, the Oracle OCI library.
101
102 Thus the 'deferred signal' approach (as implemented by default in perl
103 5.8 and later) results in some system calls being retried prior to the
104 signal handler being called by perl. This breaks timeout logic for
105 DBD-Oracle which works with earlier versions of perl. This can be par‐
106 ticularly vexing, the host on which a database resides is not avail‐
107 able: "DBI->connect()" hangs for minutes before returning an error
108 (and cannot even be interupted with control-C, even when the intended
109 timeout is only seconds). This is because SIGINT appears to be
110 deferred as well. The result is that it is impossible to implement
111 open timeouts with code that looks like this in perl 5.8.0 and later:
112
113 eval {
114 local $SIG{ALRM} = sub { die "timeout" };
115 alarm 2;
116 $sth = DBI->connect(...);
117 alarm 0;
118 };
119 alarm 0;
120 die if $@;
121
122 The solution, if your system has the POSIX sigaction() function, is to
123 use perl's "POSIX::sigaction()" to install the signal handler. With
124 "sigaction()", one gets control over both the signal mask, and the
125 "sa_flags" that are used to install the handler. Further, with perl
126 5.8.2 and later, a 'safe' switch is provided which can be used to ask
127 for safe(r) signal handling.
128
129 Using sigaction() ensures that the system call won't be resumed after
130 it's interrupted, so long as die is called within the signal handler.
131 This is no longer the case when one uses $SIG{name} to set signal han‐
132 dlers in perls >= 5.8.0.
133
134 The usage of sigaction() is not well documented however, and in perl
135 versions less than 5.8.0, it does not work at all. (But that's OK,
136 because just setting $SIG does work in that case.) Using sigaction()
137 requires approximately 4 or 5 lines of code where previously one only
138 had to set a code reference into the %SIG hash.
139
140 Unfortunately, at least with perl 5.8.0, the result is that doing this
141 effectively reverts to the 'unsafe' signals behavior. It is not clear
142 whether this would be the case in perl 5.8.2, since the safe flag can
143 be used to ask for safe signal handling. I suspect this separates the
144 logic which uses the "sa_flags" to install the handler, and whether
145 deferred signal handling is used.
146
147 The reader should also note, that the behavior of the 'safe' attribute
148 is not consistent with what this author expected. Specifically, it
149 appears to disable signal masking. This can be examined further in the
150 t/safe.t and the t/mask.t regression tests. Never-the-less,
151 Sys::SigAction provides an easy mechanism for the user to recover the
152 pre-5.8.0 behavior for signal handling, and the mask attribute clearly
153 works. (see t/mask.t) If one is looking for specific safe signal han‐
154 dling behavior that is considered broken, and the breakage can be
155 demonstrated, then a patch to t/safe.t would be most welcome.
156
157 This module wraps up the POSIX:: routines and objects necessary to call
158 sigaction() in a way that is as efficient from a coding perspective as
159 just setting a localized $SIG{SIGNAL} with a code reference. Further,
160 the user has control over the "sa_flags" passed to sigaction(). By
161 default, if no additional args are passed to sigaction(), then the sig‐
162 nal handler will be called when a signal (such as SIGALRM) is deliv‐
163 ered.
164
165 Since sigaction() is not fully functional in perl versions less than
166 5.8, this module implements equivalent behavior using the standard %SIG
167 array. The version checking and implementation of the 'right' code is
168 handled by this module, so the user does not have to write perl version
169 dependent code. The attrs hashref argument to set_sig_handler() is
170 silently ignored, in perl versions less than 5.8. This module has been
171 tested with perls as old as 5.005 on solaris.
172
173 It is hoped that with the use of this module, your signal handling
174 behavior can be coded in a way that does not change from one perl ver‐
175 sion to the next, and that sigaction() will be easier for you to use.
176
178 set_sig_handler()
179
180 $sig ,$handler ,$attrs
181
182 Install a new signal handler and (if not called in a void context)
183 returning a Sys::SigAction object containing the old signal handler,
184 which will be restored on object destruction.
185
186 $sig is a signal name (without the 'SIG') or number.
187
188 $handler is either the name (string) of a signal handler
189 function or a subroutine CODE reference.
190
191 $attrs if defined is a hash reference containing the
192 following keys:
193
194 flags => the flags the passed sigaction
195
196 ex: SA_RESTART (defined in your signal.h)
197
198 mask => the array reference: signals you
199 do not want delivered while the signal
200 handler is executing
201
202 ex: [ SIGINT SIGUSR1 ] or
203 ex: [ qw( INT USR1 ]
204
205 safe => A boolean value requesting 'safe' signal
206 handling (only in 5.8.2 and greater)
207 earlier versions will issue a warning if
208 you use this
209
210 timeout_call()
211
212 $timeout ,$coderef
213
214 Given a code reference, and a timeout value (in seconds), timeout()
215 will (in an eval) setup a signal handler for SIGALRM (which will die),
216 set an alarm clock, and execute the code reference.
217
218 If the alarm goes off the code will be interupted. The alarm is can‐
219 celed if the code returns before the alarm is fired. The routine
220 returns true if the code being executed timed out. (was interrupted).
221 Exceptions thrown by the code executed are propagated out.
222
223 The original signal handler is restored, prior to returning to the
224 caller.
225
226 sig_name()
227
228 Return the signal name (string) from a signal number.
229
230 ex:
231
232 sig_name( SIGINT ) returns 'INT'
233
234 sig_number()
235
236 Return the signal number (integer) from a signal name (minus the SIG
237 part).
238
239 ex:
240
241 sig_number( 'INT' ) returns the integer value of SIGINT;
242
244 Lincoln A. Baxter <lab@lincolnbaxter.com.make.me.VALID>
245
247 Copyright (c) 2004 Lincoln A. Baxter
248 All rights reserved.
249
250 You may distribute under the terms of either the GNU General Public
251 License or the Artistic License, as specified in the Perl README file,
252 with the exception that it cannot be placed on a CD-ROM or similar media
253 for commercial distribution without the prior approval of the author.
254
256 perldoc perlvar
257 perldoc POSIX
258
259 The dbd-oracle-timeout.pod file included with this module. This
260 includes a DBD-Oracle test script, which illustrates the use of this
261 module with the DBI with the DBD-Oracle driver.
262
263
264
265perl v5.8.8 2006-10-24 Sys::SigAction(3)