Vamos a empezar a realizar una serie de ejercicios para asimilar los conocimientos adquiridos en entradas anteriores. Las soluciones de los mismos las añadiré en un comentario de las correspondientes entradas a los ejercicios.
Diseñe e implemente un proceso que cada vez que reciba una señal SIGUSR1 incremente el valor de un contador (inicialmente a cero). Para ello, instale un manejador de la señal SIGUSR1 tal que cada vez que reciba dicha señal incremente el valor de un contador que cuente la cantidad de señales SIGUSR1 recibidas desde el inicio del programa.
Además, cuando reciba una señal SIGUSR2, debe terminar el proceso mostrando un mensaje de finalización con el valor final del contador.
El programa debe mostrar al principio de la ejecución su identificador de proceso (pid), así como el número de la señal en la que ha instalado un manejador de señales y el número de la señal por la que espera por su terminación.
Nota 1: puede enviar señales al proceso desde un Terminal mediante el comando: kill -USR2 pid-del-proceso.
Nota 2: puede conocer los identificadores de los procesos desde un Terminal mediante el comando: ps -ef
Autor de los ejercicios (Profesorado UMA)
Mostrando entradas con la etiqueta señales posix. Mostrar todas las entradas
Mostrando entradas con la etiqueta señales posix. Mostrar todas las entradas
jueves, 6 de febrero de 2014
Extensiones de Tiempo Real
El mecanismo de manejo de señales de POSIX.4 cuenta con la posibilidad de encolar las señales de tiempo real. Las señales pendientes están ordenadas por prioridad y se permite el intercambio de datos.
El rango de señales de Tiempo Real van desde SIGRTMIN a SIGRTMAX (el número de estas señales viene definido en RTSIG_MAX, constante de "rt_limits.h", se puede saber usando sysconf(_SC_RTSIG_MAX))
El rango de señales de Tiempo Real van desde SIGRTMIN a SIGRTMAX (el número de estas señales viene definido en RTSIG_MAX, constante de "rt_limits.h", se puede saber usando sysconf(_SC_RTSIG_MAX))
Señales POSIX
Configuración
Bloquear una señal significa que, en el caso de que sea generada, la señal no se pierde y se posterga su atención. El bloque se realiza mediante la máscara de señal
int sigemptyset(sigset_t *set);
int sigaddset(sigset_t *set, int signo);
El bloqueo se genera por:
int pthread_sigmas(int how, const singset_t *restrict set, sigset_t *restrict oset);
Le pasamos como primer parámetro el bloqueo/desbloqueo "SIG_BLOQ" y "SIG_UNBLOQ". Acto seguido le pasamos el conjunto de señales.
int sigprocmask(int how, const sigset_t *restrict set, sigset_t *restrict oset);
Esta función afecta a todas las hebras del proceso. Si el "oset" no es NULL, almacena el conjunto de señales antiguo.
La asignación de un manejador para la señal se realiza mediante la función sigaction. Nos permitirá, entre otras cosas, ignorar una señal, asignar un manejador por defecto y asignar un manejador propio.
int sigaction (int signum, const struct sigaction *act, struct sigaction *oldact);
struct sigaction {
void (*sa_handler) (int);
sigset_t_t sa_mask;
int sa_flagas;
};
SIG_DFL: Manejador por defecto.
SIG_IGN: Ignora la señal
Manejador
Los manejadores de señales deben ser muy cortos y simples. Si una hebra necesita esperar hasta que se produzca una señal:
int sigwait (cont sigset_t *set, int *sig);
int sigwaitinfo(const sigset_t *set, siginfo_t *info);
Esta función realiza tres operaciones de forma atómica. Desbloquea el conjunto de señales, queda a la espera de que se produzca alguna señal no bloqueada y cuando se produce, se restablecen los bloqueos y se devuelve la señal producida.
Suscribirse a:
Entradas (Atom)