%SIG contiene las rutinas de manipulación de las señales.
Las claves del hash son los nombres de las señales. Así, $SIG{INT}$
contendrá el nombre de la subrutina que se ejecuta cuando se produce una interrupción
de teclado (el usuario pulsó CTRL-C).
Supongamos que tenemos un programa que crea ciertos ficheros temporales
durante su ejecución, los cuales son borrados al final de la misma.
Si el usuario pulsa CTRL-C, nuestro programa será interrumpido y los ficheros
temporales quedarán como restos de la ejecución inacabada. El problema se
resuelve usando un manejador de la señal de interrupción:
lhp@nereida:~/Lperl/src$ cat -n signal.pl
1 #!/usr/bin/perl -w
2 use strict;
3 use File::Temp qw{tempdir};
4 use Time::HiRes qw(usleep);
5 use IO::File;
6 use IO::Tee;
7 use constant W => 0.7e6;
8
9 my $n = shift || 1;
10 my $temp_dir;
11
12 sub clean_files {
13 unlink glob "$temp_dir/*";
14 rmdir $temp_dir;
15 }
16
17 sub int_handler {
18 &clean_files;
19 die "\nPrograma interrumpido por el usuario\n";
20 }
21
22 $temp_dir = tempdir('/tmp/pruebaXXXXX');
23 local $SIG{INT} = \&int_handler;
24
25 my $fn = "$temp_dir/file.txt";
26 my $F = IO::File->new(">$fn");
27 $F->autoflush(1);
28 my $tee = IO::Tee->new(\*STDOUT, $F);
29
30 my @files;
31 for(my $i=0; $i<$n; $i++) {
32 print $tee "Printing $i in $fn. size ".(-s $fn)."\n";
33 usleep(W); # sleep W microseconds
34 }
35 close($F);
36
37 &clean_files;
La línea clave aquí es:
local $SIG{INT} = \&int_handler
que establece el manejador.
Veamos un ejemplo de ejecución:
lhp@nereida:~/Lperl/src$ signal.pl 1000 Printing 0 in /tmp/pruebahCKNU/file.txt. size 0 Printing 1 in /tmp/pruebahCKNU/file.txt. size 48 Printing 2 in /tmp/pruebahCKNU/file.txt. size 97 ^C Programa interrumpido por el usuario lhp@nereida:~/Lperl/src$ ls -l /tmp/pruebahCKNU/file.txt ls: /tmp/pruebahCKNU/file.txt: No existe el fichero o el directorio
Casiano Rodríguez León
