SlideShare una empresa de Scribd logo
1 de 23
Programación de Sistemas
3.3.1 Administración de
procesos:
Comunicación entre Procesos:
Señales
MCC Enrique Ayala Franco
Introducción
 La multiprogramación necesita que los procesos se
comuniquen entre sí para poder colaborar de forma efectiva.
 Ya se han mencionado algunos mecanismos utilizando
hilos, pero también hay otras formas más primitivas de
comunicación entre procesos, por ejemplo las señales.
 El sistema utiliza señales para informar a un determinado
proceso sobre alguna condición, realizar esperas entre
procesos, etc.
 Sin embargo, las señales no son suficientes para transmitir
toda la información, por ello es necesario incorporar otros
mecanismos para compartir datos entre procesos.
2
Introducción
 El enfoque más obvio de todos es utilizar ficheros del
sistema para poder escribir y leer de ellos, pero esto es
lento, poco eficiente e inseguro, aunque muy sencillo de
hacer.
 El siguiente paso podría ser utilizar una tubería para
intercomunicar los procesos a través de él. El rendimiento
es superior respecto al enfoque anterior, pero sólo se
utilizan en casos sencillos.
 Como evolución de todo lo anterior llegó el sistema IPC
(Inter Process Communication) de System V, con sus tres
tipos de comunicación diferentes: semáforos, colas de
mensajes y segmentos de memoria compartida.
3
Introducción
 Actualmente IPC del System V ha sido reemplazado por
otro estándar, el IPC POSIX.
 Ambos implementan características avanzadas de los
sistemas de comunicación entre procesos de manera
bastante eficiente, por lo que convendría pensar en su
empleo a la hora de realizar una aplicación multiproceso
bien diseñada.
 A continuación veremos algunos conceptos y ejemplos de
manejo de señales y también el uso de tuberías y
redireccionamiento.
4
Señales en UNIX/LINUX
5
6
Objetivos
 Utilizar señales en programas para comprender su
influencia y efectos sobre los procesos.
 Conocer los tipos de señales POSIX 1b para llevar
a cabo operaciones de forma asíncrona.
7
¿Señales?
 Hay ocasiones en las que interesa manejar
sucesos asíncronos, es decir, que pueden
suceder en cualquier momento, no cuando
nosotros los comprobemos.
 La manera más sencilla de implementar esto es
mediante el uso de señales.
 La pérdida de la conexión con el terminal, una
interrupción de teclado o una condición de error
podrían desencadenar que un proceso
recibiese una señal. Una vez recibida, es tarea
del proceso atrapar o capturarla y tratarla.
 Si una señal no se captura, el proceso muere.
8
¿Señales?
 Una señal es una notificación por software para un
proceso de la ocurrencia de cierto evento.
 Cuando ocurre el evento la genera.
 La señal se deposita cuando el proceso realiza una
acción con base en ella.
 El tiempo de vida de la señal es desde que se genera
hasta que se deposita.
 La señal queda pendiente si aún no se deposita. Es
decir pueden haber colas de señales.
9
El envío de señales
 En Linux/Unix las señales tienen un nombre simbólico que inicia con
SIG. Están definidos en <signal.h>. El la tabla estan las requeridas por
POSIX. Los nombres representan enteros mayores que 0.
Símbolo Significado
SIGABRT
SIGALRM
SIGFPE
SIGHUP
SIGILL
SIGINT
SIGKILL
SIGPIPE
SIGQUIT
SIGSEGV
SIGTERM
SIGUSR1
SIGUSR2
Terminación anormal como la iniciada por abort
Señal de espera como la iniciada por alarm
Error en operación aritmética, como la división por cero
Colgado (muerte) de la terminal de control (proceso)
Instrucción de hardware no válida
Señal de atención interactiva
Terminación (no se puede atrapar o ignorar)
Escritura en un entubamiento sin lectores
Terminación interactiva
Referencia no válida de memoria
Terminación
Señal 1 definida por el usuario
Señal 2 definida por el usuario
10
El envío de señales
 Algunas señales como SIGFPE y SIGSEGV se generan al ocurrir
errores.
 Otras se generan mediante llamadas específicas, aunque un usuario
sólo puede mandar señales a procesos que posee. Se requiere el ID del
usuario real.
 Todas las señales pueden ser ignoradas o bloqueadas, a excepción de
SIGSTOP y SIGKILL, que son imposibles de ignorar.
 La señales se generan desde el shell mediante el comando kill.
Ejemplo: kill
Sintaxis:
Kill –<señal> pid
 > kill –USR1 3543
 Muchas señales tiene por omisión la terminación de procesos.
 > kill –l
 Muestra la lista de señales definidas en el núcleo del sistema
11
Señales y procesos
 Un proceso atrapa una señal si
éste ejecuta el manejador de
señal cuando se deposita una
señal.
 El programa instala el manejador
mediante una llamada sigaction
con el nombre de la función a
ejecutar.
 O un SIG_DFL o un SIG_IGN.
 SIG_DFL: realiza una acción
preestablecida.
 SIG_IGN: ignora la señal y se
desecha.
12
El envío de señales
Desde un programa en C:
//envio de señales con la llamada a kill
// ¿quién mata a quien??
#include <sys/types.h>
#include <signal.h>
#include <stdio.h>
int main (void)
{
int pid;
pid = fork();
switch (pid)
{
case 1: perror ("No se ha podido crear el hijo");
break;
case 0: printf("Soy el hijo, mi PID es %d y mi PPID es %dn",
getpid(), getppid());
// caso siniestro, el hijo mata a su padre
if( kill(getppid(), SIGTERM) == -1) // kill envía la señal al proceso.
perror("Error en kill");
break;
default: printf ("Soy el padre, mi PID es %d y el PID de mi hijo es %dn", getpid(), pid );
printf("%d",kill(pid,SIGTERM) );
// el padre mata al hijo
}
return 0;
}
13
El envío de señales
El comando raise también manda una señal al proceso en primer plano.
raise(SIGUSR1); // enviar señal a sí mismo
Otras formas de hacer esto mismo:
pthread_kill(pthread_self(), sig);
kill(getpid(), sig);
El comando stty –a informa de las características del dispositivo de
entrada estándar, incluyendo configuración de caracteres que generan
señales.
> stty –a
speed 38400 baud; rows 24; columns 77; line = 0;
intr = ^C; quit = ^; erase = ^?; kill = ^U; eof = ^D; eol = <undef>;
eol2 = <undef>; swtch = M-^?; start = ^Q; stop = ^S; susp = ^Z; rprnt = ^R;
werase = ^W; lnext = ^V; flush = ^O; min = 1; time = 0;
….
14
El envío de señales
 La función alarm hace que se envíe una señal SIGALRM al proceso que la
invoca después de un tiempo determinado en segundos.
 No se apilan, si se llama de nuevo se reinicia con el nuevo valor.
 Su efecto por default es terminar el proceso.
 Ejemplo: programa que termina en x segundos.
#include <unistd.h>
#include <signal.h>
#include <stdio.h>
int main (void)
{
alarm(5);
printf("Espero 5 segundos para terminar...n");
alarm(1);
printf("no mejor 2 segundos ...n");
for(;;){ }
printf("No creo llegar hasta aqui...n");
return 0;
}
15
Máscaras de señales
 Una máscara de señal también determina el tipo de
acción a realizar.
 La máscara contiene una lista de las señales que en
determinado tiempo están bloquedas.
 Las señales bloquedas no se desechan, esperan
hasta que el proceso las libere y entonces serán
depositadas.
 Los programas utilizan:
 sigprocmask para cambiar la máscara y bloquear señales.
 O un manejador especificando a SIG_IGN como una llamada
sigaction para ignorar señales.
16
Máscaras de señales
 Sirven para impedir, de forma temporal, que un proceso deposite la
señal, bloqueando las señales.
 La mascara de señal indica el conjunto de señales que serán
bloqueadas (no ignoradas).
 Es de tipo sigset_t.
 El proceso modifica la máscara mediante el sigprocmask de su señal.
 Funciones de bloqueo y desbloqueo de grupos de señales:
 Int sigemptyset(sigset_t *set); // ninguna señal
 Int sigfillset(sigset_t *set); // todas las señales
 Int sigaddset(sigset_t *set, int signo); // agregar una señal al grupo
 Int sigdelset(sigset_t *set, int signo); // eliminar una señal del grupo
 Int sigismember(const sigset_t *set, int signo); // 1 si es miembro del
grupo
17
Máscaras de señales
//uso de mascaras de señales
#include <signal.h>
#include <stdio.h>
int main (void)
{
sigset_t dossigs;
// inicializar mascaras
sigemptyset(&dossigs);
sigaddset(&dossigs, SIGINT);
sigaddset(&dossigs, SIGQUIT);
sigaddset(&dossigs, SIGKILL);
sigaddset(&dossigs, SIGTERM);
// aplicar mascara
if(sigprocmask(SIG_BLOCK, &dossigs, NULL))
perror("No se pudo bloquear señalesn");
alarm(25);
printf("Intenta salir de esto...n");
sleep(10);
printf("Termino de dormirn");
// desbloquear señales
if(sigprocmask(SIG_UNBLOCK, &dossigs, NULL))
perror("No se pudo desbloquear señalesn");
for(;;){
}
printf("Algo no se configuro bien...n");
return 0;
Sintaxis: Sigprocmask(int modo, const
sigset_t *set, sigset_t *pset)
El modo puede ser:
SIG_BLOCK: añade para bloquear
el conjunto de señales.
SIG_UNBLOCK: borrar una
colección se señales del bloqueo.
SIG_SETMASK: establece la
máscara de las señales que serán
bloqueadas.
18
Como atrapar señales
 Se usa la función sigaction para establecer los manejadores de señales de un
proceso.
 La información del manejador se almacena en una estructura de tipo struct
sigaction.
 La llamada al sistema tiene tres parámetros:
 Número de señal o apuntador a función.
 Apuntador a la estructura de tipo sigaction del nuevo manejador
 Apuntador a la estructura anterior
 En el llamado se llenan los valores con la información anterior de la llamada, si
se coloca un apuntador NULL, nada cambia.
 Sintaxis:
 Int sigaction(int señal, const struct sigaction *act, struct sigaction *oact);
 Struct sigaction {
void()*sa_handler) (); // SIG_DFL, SIG_IGN o apuntador a función
sigset_t sa_mask; // señales adicionales se bloquearán durante ejecución
// del manejador
int sa_flags; // banderas especiales y opciones
}
19
Como atrapar señales: ejemplo
#include <signal.h>
static void handler(int signum)
{
/* Realizar acciones para la señal entregada */
}
int main()
{
struct sigaction sa;
sa.sa_handler = handler;
sigemptyset(&sa.sa_mask);
sa.sa_flags = SA_RESTART;
/* reiniciar si se interrumpe por el manejador */
if (sigaction(SIGINT, &sa, NULL) == -1)
/* manejo de error */;
/* mas código */
}
¿Qué pasa después de ejecutar el
manejador de señal?
20
Ejemplo mas detallado
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
static void manejador1(int signum){
// acciones si se captura señal
printf("He capturado la señal ctrl-cn");
puts("Quieres continuar?: ");
char sn=getc(stdin); //leer caracter desde
stdin
//fflush(stdin); // limpiar buffer
if(sn=='n' || sn=='N')
{
printf("Proceso interrumpido por el
usuario");
exit(0);
}
else
printf("Continuar hasta que expire mi
tiempo...n");
}
int main() {
struct sigaction sa;
sa.sa_handler = manejador1;
sigemptyset(&sa.sa_mask);
sa.sa_flags = SA_RESTART;
if( sigaction(SIGINT, &sa, NULL) ==-1)
perror("Error al tratar la señaln");
printf("Para interrumpir el proceso ctrl-cn");
alarm(25);
for(;;){ // pensando...
}
printf("Continuamos con el proceson");
return 0;
}
21
Ignorar una señal
// Ignorar la señal ctrl-c
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>
#include <string.h>
char mensaje[]="Se encontro un ctrl-
cn";
static void catch_ctrl_c(int signum){
write(STDERR_FILENO,mensaje
,strlen(mensaje));
// write es seguro para llamadas
asincronas
}
int main() {
struct sigaction sa;
//sa.sa_handler = catch_ctrl_c; //
establecer nuevo manejador
sa.sa_handler = SIG_IGN; // ignorar señal
sigemptyset(&sa.sa_mask); // no mas
señales bloqueadas
sa.sa_flags = 0; // ninguna opcion
especial
if( sigaction(SIGINT, &sa, NULL) < 0)
perror("Error al tratar la señaln");
printf("Para interrumpir el proceso ctrl-
c!!!!!n");
alarm(15);
for(;;){ // pensando...
}
printf("Continuamos con el proceson");
return 0;
}
Ejemplo con signal
// ejemplo signal.c con funcion signal()
#include <stdio.h>
#include <stdlib.h>
#include <signal.h>
#include <unistd.h>
#include <errno.h>
static void manejador1(int signum){
// acciones si se captura señal
if(signum==SIGINT){
printf("He capturado la señal ctrl-cn");
puts("Quieres continuar?: ");
char sn[20];
fflush(stdin); // limpiar buffer
gets(sn); //leer caracter desde stdin
//fflush(stdin); // limpiar buffer
if(sn[0]=='n' || sn[0]=='N')
{
printf("Proceso interrumpido por el usuario");
exit(0);
}
else
{ printf("Continuar hasta que expire mi tiempo...n");
if( signal(SIGINT, manejador1) ) // necesario volver a
especificar señal a capturar
perror("Error al tratar la señaln");
}
}else
{
fprintf(stderr,"Error: esperado=%d, recibido=
%d n", SIGINT, signal);
}
}
int main() {
int n, i=1,j=0;
if( signal(SIGINT, manejador1) )
perror("Error al tratar la senialn");
printf("Para interrumpir el proceso ctrl-cn");
for(i=1;i<5000; i++){ // pensando...
for(j=0; j<35000; j++)
printf("");
}
printf("Fin de proceson");
system("pause");
return 0;
}
22
23
Ejercicio
 Hacer un comando mycat , que despliegue por
pantalla el contenido de un archivo de texto,
pasado como argumento en la línea de comandos.
El programa debe aceptar una interrupción por
software en donde se pregunte si se desea
continuar con el despliegue o terminar.
 Variantes:
 Mientras se esta desplegando se acepta la señal. Si esta
fuera del despliegue no.
 Ignorar ctrl-d y otras interrupciones.

Más contenido relacionado

La actualidad más candente

La actualidad más candente (7)

Programación en Arduino
Programación en ArduinoProgramación en Arduino
Programación en Arduino
 
Interrupciones
InterrupcionesInterrupciones
Interrupciones
 
Timer
TimerTimer
Timer
 
Concepto de semáforo, exclusión mutua y sección critica
Concepto de semáforo, exclusión mutua y sección criticaConcepto de semáforo, exclusión mutua y sección critica
Concepto de semáforo, exclusión mutua y sección critica
 
Curso basico de pic 16 f877
Curso basico de pic 16 f877Curso basico de pic 16 f877
Curso basico de pic 16 f877
 
Unidad 2 sist. oper. 1
Unidad 2 sist. oper. 1Unidad 2 sist. oper. 1
Unidad 2 sist. oper. 1
 
Sincronizacion de Procesos
Sincronizacion de ProcesosSincronizacion de Procesos
Sincronizacion de Procesos
 

Similar a Ps 10 sos_procesos_señales

Linux ud7 - gestion de procesos
Linux   ud7 - gestion de procesosLinux   ud7 - gestion de procesos
Linux ud7 - gestion de procesosJavier Muñoz
 
Ataque Informatico (Keylogger,screenshot,bavkdoor)
Ataque Informatico (Keylogger,screenshot,bavkdoor) Ataque Informatico (Keylogger,screenshot,bavkdoor)
Ataque Informatico (Keylogger,screenshot,bavkdoor) Municipio de Guayaquil
 
Ud Procesos
Ud  ProcesosUd  Procesos
Ud Procesosnaxoglez
 
Sincronizacion de procesos
Sincronizacion de procesosSincronizacion de procesos
Sincronizacion de procesoskruskaya salazar
 
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...NSM Network Security Monitoring Herramientas Software Libre de detección y pr...
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...Alejandro Valdes Jimenez
 
Telecomunicaciones - Trabajo de Investigación
Telecomunicaciones - Trabajo de InvestigaciónTelecomunicaciones - Trabajo de Investigación
Telecomunicaciones - Trabajo de InvestigaciónAgustin Peratta Knapps
 
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-criticalupita zume
 
Manual de hacking basico por taskkill#3
Manual de hacking basico por taskkill#3Manual de hacking basico por taskkill#3
Manual de hacking basico por taskkill#3Brat Stell
 
Gestión de entrada y salida y seguridad de los sistemas operativos
Gestión de entrada y salida y seguridad de los sistemas operativosGestión de entrada y salida y seguridad de los sistemas operativos
Gestión de entrada y salida y seguridad de los sistemas operativosFatima Cham
 
Seguridad Computacional y Administración de Sistemas
Seguridad Computacional y Administración de SistemasSeguridad Computacional y Administración de Sistemas
Seguridad Computacional y Administración de SistemasArturo Hoffstadt
 
Prueba programacion
Prueba programacionPrueba programacion
Prueba programacionMarti Matura
 

Similar a Ps 10 sos_procesos_señales (20)

sistemas operativos
sistemas operativossistemas operativos
sistemas operativos
 
Linux ud7 - gestion de procesos
Linux   ud7 - gestion de procesosLinux   ud7 - gestion de procesos
Linux ud7 - gestion de procesos
 
sistemas operativos
sistemas  operativos sistemas  operativos
sistemas operativos
 
Ataque Informatico (Keylogger,screenshot,bavkdoor)
Ataque Informatico (Keylogger,screenshot,bavkdoor) Ataque Informatico (Keylogger,screenshot,bavkdoor)
Ataque Informatico (Keylogger,screenshot,bavkdoor)
 
Señales en Linux
Señales en LinuxSeñales en Linux
Señales en Linux
 
Ejemplo Pdf
Ejemplo PdfEjemplo Pdf
Ejemplo Pdf
 
Ud Procesos
Ud  ProcesosUd  Procesos
Ud Procesos
 
Sincronizacion de procesos
Sincronizacion de procesosSincronizacion de procesos
Sincronizacion de procesos
 
Procesos
ProcesosProcesos
Procesos
 
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...NSM Network Security Monitoring Herramientas Software Libre de detección y pr...
NSM Network Security Monitoring Herramientas Software Libre de detección y pr...
 
27 de oct
27 de oct27 de oct
27 de oct
 
Viernes Tecnicos DTrace
Viernes Tecnicos DTraceViernes Tecnicos DTrace
Viernes Tecnicos DTrace
 
Ataques Informáticos
Ataques InformáticosAtaques Informáticos
Ataques Informáticos
 
Telecomunicaciones - Trabajo de Investigación
Telecomunicaciones - Trabajo de InvestigaciónTelecomunicaciones - Trabajo de Investigación
Telecomunicaciones - Trabajo de Investigación
 
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica
2.4 concepto-de-semaforo-exclusion-mutua-y-seccion-critica
 
Manual de hacking basico por taskkill#3
Manual de hacking basico por taskkill#3Manual de hacking basico por taskkill#3
Manual de hacking basico por taskkill#3
 
Gestión de entrada y salida y seguridad de los sistemas operativos
Gestión de entrada y salida y seguridad de los sistemas operativosGestión de entrada y salida y seguridad de los sistemas operativos
Gestión de entrada y salida y seguridad de los sistemas operativos
 
acti27 de oct
acti27 de octacti27 de oct
acti27 de oct
 
Seguridad Computacional y Administración de Sistemas
Seguridad Computacional y Administración de SistemasSeguridad Computacional y Administración de Sistemas
Seguridad Computacional y Administración de Sistemas
 
Prueba programacion
Prueba programacionPrueba programacion
Prueba programacion
 

Ps 10 sos_procesos_señales

  • 1. Programación de Sistemas 3.3.1 Administración de procesos: Comunicación entre Procesos: Señales MCC Enrique Ayala Franco
  • 2. Introducción  La multiprogramación necesita que los procesos se comuniquen entre sí para poder colaborar de forma efectiva.  Ya se han mencionado algunos mecanismos utilizando hilos, pero también hay otras formas más primitivas de comunicación entre procesos, por ejemplo las señales.  El sistema utiliza señales para informar a un determinado proceso sobre alguna condición, realizar esperas entre procesos, etc.  Sin embargo, las señales no son suficientes para transmitir toda la información, por ello es necesario incorporar otros mecanismos para compartir datos entre procesos. 2
  • 3. Introducción  El enfoque más obvio de todos es utilizar ficheros del sistema para poder escribir y leer de ellos, pero esto es lento, poco eficiente e inseguro, aunque muy sencillo de hacer.  El siguiente paso podría ser utilizar una tubería para intercomunicar los procesos a través de él. El rendimiento es superior respecto al enfoque anterior, pero sólo se utilizan en casos sencillos.  Como evolución de todo lo anterior llegó el sistema IPC (Inter Process Communication) de System V, con sus tres tipos de comunicación diferentes: semáforos, colas de mensajes y segmentos de memoria compartida. 3
  • 4. Introducción  Actualmente IPC del System V ha sido reemplazado por otro estándar, el IPC POSIX.  Ambos implementan características avanzadas de los sistemas de comunicación entre procesos de manera bastante eficiente, por lo que convendría pensar en su empleo a la hora de realizar una aplicación multiproceso bien diseñada.  A continuación veremos algunos conceptos y ejemplos de manejo de señales y también el uso de tuberías y redireccionamiento. 4
  • 6. 6 Objetivos  Utilizar señales en programas para comprender su influencia y efectos sobre los procesos.  Conocer los tipos de señales POSIX 1b para llevar a cabo operaciones de forma asíncrona.
  • 7. 7 ¿Señales?  Hay ocasiones en las que interesa manejar sucesos asíncronos, es decir, que pueden suceder en cualquier momento, no cuando nosotros los comprobemos.  La manera más sencilla de implementar esto es mediante el uso de señales.  La pérdida de la conexión con el terminal, una interrupción de teclado o una condición de error podrían desencadenar que un proceso recibiese una señal. Una vez recibida, es tarea del proceso atrapar o capturarla y tratarla.  Si una señal no se captura, el proceso muere.
  • 8. 8 ¿Señales?  Una señal es una notificación por software para un proceso de la ocurrencia de cierto evento.  Cuando ocurre el evento la genera.  La señal se deposita cuando el proceso realiza una acción con base en ella.  El tiempo de vida de la señal es desde que se genera hasta que se deposita.  La señal queda pendiente si aún no se deposita. Es decir pueden haber colas de señales.
  • 9. 9 El envío de señales  En Linux/Unix las señales tienen un nombre simbólico que inicia con SIG. Están definidos en <signal.h>. El la tabla estan las requeridas por POSIX. Los nombres representan enteros mayores que 0. Símbolo Significado SIGABRT SIGALRM SIGFPE SIGHUP SIGILL SIGINT SIGKILL SIGPIPE SIGQUIT SIGSEGV SIGTERM SIGUSR1 SIGUSR2 Terminación anormal como la iniciada por abort Señal de espera como la iniciada por alarm Error en operación aritmética, como la división por cero Colgado (muerte) de la terminal de control (proceso) Instrucción de hardware no válida Señal de atención interactiva Terminación (no se puede atrapar o ignorar) Escritura en un entubamiento sin lectores Terminación interactiva Referencia no válida de memoria Terminación Señal 1 definida por el usuario Señal 2 definida por el usuario
  • 10. 10 El envío de señales  Algunas señales como SIGFPE y SIGSEGV se generan al ocurrir errores.  Otras se generan mediante llamadas específicas, aunque un usuario sólo puede mandar señales a procesos que posee. Se requiere el ID del usuario real.  Todas las señales pueden ser ignoradas o bloqueadas, a excepción de SIGSTOP y SIGKILL, que son imposibles de ignorar.  La señales se generan desde el shell mediante el comando kill. Ejemplo: kill Sintaxis: Kill –<señal> pid  > kill –USR1 3543  Muchas señales tiene por omisión la terminación de procesos.  > kill –l  Muestra la lista de señales definidas en el núcleo del sistema
  • 11. 11 Señales y procesos  Un proceso atrapa una señal si éste ejecuta el manejador de señal cuando se deposita una señal.  El programa instala el manejador mediante una llamada sigaction con el nombre de la función a ejecutar.  O un SIG_DFL o un SIG_IGN.  SIG_DFL: realiza una acción preestablecida.  SIG_IGN: ignora la señal y se desecha.
  • 12. 12 El envío de señales Desde un programa en C: //envio de señales con la llamada a kill // ¿quién mata a quien?? #include <sys/types.h> #include <signal.h> #include <stdio.h> int main (void) { int pid; pid = fork(); switch (pid) { case 1: perror ("No se ha podido crear el hijo"); break; case 0: printf("Soy el hijo, mi PID es %d y mi PPID es %dn", getpid(), getppid()); // caso siniestro, el hijo mata a su padre if( kill(getppid(), SIGTERM) == -1) // kill envía la señal al proceso. perror("Error en kill"); break; default: printf ("Soy el padre, mi PID es %d y el PID de mi hijo es %dn", getpid(), pid ); printf("%d",kill(pid,SIGTERM) ); // el padre mata al hijo } return 0; }
  • 13. 13 El envío de señales El comando raise también manda una señal al proceso en primer plano. raise(SIGUSR1); // enviar señal a sí mismo Otras formas de hacer esto mismo: pthread_kill(pthread_self(), sig); kill(getpid(), sig); El comando stty –a informa de las características del dispositivo de entrada estándar, incluyendo configuración de caracteres que generan señales. > stty –a speed 38400 baud; rows 24; columns 77; line = 0; intr = ^C; quit = ^; erase = ^?; kill = ^U; eof = ^D; eol = <undef>; eol2 = <undef>; swtch = M-^?; start = ^Q; stop = ^S; susp = ^Z; rprnt = ^R; werase = ^W; lnext = ^V; flush = ^O; min = 1; time = 0; ….
  • 14. 14 El envío de señales  La función alarm hace que se envíe una señal SIGALRM al proceso que la invoca después de un tiempo determinado en segundos.  No se apilan, si se llama de nuevo se reinicia con el nuevo valor.  Su efecto por default es terminar el proceso.  Ejemplo: programa que termina en x segundos. #include <unistd.h> #include <signal.h> #include <stdio.h> int main (void) { alarm(5); printf("Espero 5 segundos para terminar...n"); alarm(1); printf("no mejor 2 segundos ...n"); for(;;){ } printf("No creo llegar hasta aqui...n"); return 0; }
  • 15. 15 Máscaras de señales  Una máscara de señal también determina el tipo de acción a realizar.  La máscara contiene una lista de las señales que en determinado tiempo están bloquedas.  Las señales bloquedas no se desechan, esperan hasta que el proceso las libere y entonces serán depositadas.  Los programas utilizan:  sigprocmask para cambiar la máscara y bloquear señales.  O un manejador especificando a SIG_IGN como una llamada sigaction para ignorar señales.
  • 16. 16 Máscaras de señales  Sirven para impedir, de forma temporal, que un proceso deposite la señal, bloqueando las señales.  La mascara de señal indica el conjunto de señales que serán bloqueadas (no ignoradas).  Es de tipo sigset_t.  El proceso modifica la máscara mediante el sigprocmask de su señal.  Funciones de bloqueo y desbloqueo de grupos de señales:  Int sigemptyset(sigset_t *set); // ninguna señal  Int sigfillset(sigset_t *set); // todas las señales  Int sigaddset(sigset_t *set, int signo); // agregar una señal al grupo  Int sigdelset(sigset_t *set, int signo); // eliminar una señal del grupo  Int sigismember(const sigset_t *set, int signo); // 1 si es miembro del grupo
  • 17. 17 Máscaras de señales //uso de mascaras de señales #include <signal.h> #include <stdio.h> int main (void) { sigset_t dossigs; // inicializar mascaras sigemptyset(&dossigs); sigaddset(&dossigs, SIGINT); sigaddset(&dossigs, SIGQUIT); sigaddset(&dossigs, SIGKILL); sigaddset(&dossigs, SIGTERM); // aplicar mascara if(sigprocmask(SIG_BLOCK, &dossigs, NULL)) perror("No se pudo bloquear señalesn"); alarm(25); printf("Intenta salir de esto...n"); sleep(10); printf("Termino de dormirn"); // desbloquear señales if(sigprocmask(SIG_UNBLOCK, &dossigs, NULL)) perror("No se pudo desbloquear señalesn"); for(;;){ } printf("Algo no se configuro bien...n"); return 0; Sintaxis: Sigprocmask(int modo, const sigset_t *set, sigset_t *pset) El modo puede ser: SIG_BLOCK: añade para bloquear el conjunto de señales. SIG_UNBLOCK: borrar una colección se señales del bloqueo. SIG_SETMASK: establece la máscara de las señales que serán bloqueadas.
  • 18. 18 Como atrapar señales  Se usa la función sigaction para establecer los manejadores de señales de un proceso.  La información del manejador se almacena en una estructura de tipo struct sigaction.  La llamada al sistema tiene tres parámetros:  Número de señal o apuntador a función.  Apuntador a la estructura de tipo sigaction del nuevo manejador  Apuntador a la estructura anterior  En el llamado se llenan los valores con la información anterior de la llamada, si se coloca un apuntador NULL, nada cambia.  Sintaxis:  Int sigaction(int señal, const struct sigaction *act, struct sigaction *oact);  Struct sigaction { void()*sa_handler) (); // SIG_DFL, SIG_IGN o apuntador a función sigset_t sa_mask; // señales adicionales se bloquearán durante ejecución // del manejador int sa_flags; // banderas especiales y opciones }
  • 19. 19 Como atrapar señales: ejemplo #include <signal.h> static void handler(int signum) { /* Realizar acciones para la señal entregada */ } int main() { struct sigaction sa; sa.sa_handler = handler; sigemptyset(&sa.sa_mask); sa.sa_flags = SA_RESTART; /* reiniciar si se interrumpe por el manejador */ if (sigaction(SIGINT, &sa, NULL) == -1) /* manejo de error */; /* mas código */ } ¿Qué pasa después de ejecutar el manejador de señal?
  • 20. 20 Ejemplo mas detallado #include <stdio.h> #include <stdlib.h> #include <signal.h> static void manejador1(int signum){ // acciones si se captura señal printf("He capturado la señal ctrl-cn"); puts("Quieres continuar?: "); char sn=getc(stdin); //leer caracter desde stdin //fflush(stdin); // limpiar buffer if(sn=='n' || sn=='N') { printf("Proceso interrumpido por el usuario"); exit(0); } else printf("Continuar hasta que expire mi tiempo...n"); } int main() { struct sigaction sa; sa.sa_handler = manejador1; sigemptyset(&sa.sa_mask); sa.sa_flags = SA_RESTART; if( sigaction(SIGINT, &sa, NULL) ==-1) perror("Error al tratar la señaln"); printf("Para interrumpir el proceso ctrl-cn"); alarm(25); for(;;){ // pensando... } printf("Continuamos con el proceson"); return 0; }
  • 21. 21 Ignorar una señal // Ignorar la señal ctrl-c #include <stdio.h> #include <unistd.h> #include <stdlib.h> #include <signal.h> #include <string.h> char mensaje[]="Se encontro un ctrl- cn"; static void catch_ctrl_c(int signum){ write(STDERR_FILENO,mensaje ,strlen(mensaje)); // write es seguro para llamadas asincronas } int main() { struct sigaction sa; //sa.sa_handler = catch_ctrl_c; // establecer nuevo manejador sa.sa_handler = SIG_IGN; // ignorar señal sigemptyset(&sa.sa_mask); // no mas señales bloqueadas sa.sa_flags = 0; // ninguna opcion especial if( sigaction(SIGINT, &sa, NULL) < 0) perror("Error al tratar la señaln"); printf("Para interrumpir el proceso ctrl- c!!!!!n"); alarm(15); for(;;){ // pensando... } printf("Continuamos con el proceson"); return 0; }
  • 22. Ejemplo con signal // ejemplo signal.c con funcion signal() #include <stdio.h> #include <stdlib.h> #include <signal.h> #include <unistd.h> #include <errno.h> static void manejador1(int signum){ // acciones si se captura señal if(signum==SIGINT){ printf("He capturado la señal ctrl-cn"); puts("Quieres continuar?: "); char sn[20]; fflush(stdin); // limpiar buffer gets(sn); //leer caracter desde stdin //fflush(stdin); // limpiar buffer if(sn[0]=='n' || sn[0]=='N') { printf("Proceso interrumpido por el usuario"); exit(0); } else { printf("Continuar hasta que expire mi tiempo...n"); if( signal(SIGINT, manejador1) ) // necesario volver a especificar señal a capturar perror("Error al tratar la señaln"); } }else { fprintf(stderr,"Error: esperado=%d, recibido= %d n", SIGINT, signal); } } int main() { int n, i=1,j=0; if( signal(SIGINT, manejador1) ) perror("Error al tratar la senialn"); printf("Para interrumpir el proceso ctrl-cn"); for(i=1;i<5000; i++){ // pensando... for(j=0; j<35000; j++) printf(""); } printf("Fin de proceson"); system("pause"); return 0; } 22
  • 23. 23 Ejercicio  Hacer un comando mycat , que despliegue por pantalla el contenido de un archivo de texto, pasado como argumento en la línea de comandos. El programa debe aceptar una interrupción por software en donde se pregunte si se desea continuar con el despliegue o terminar.  Variantes:  Mientras se esta desplegando se acepta la señal. Si esta fuera del despliegue no.  Ignorar ctrl-d y otras interrupciones.