wait, waitpid y waitid, gestión de múltiples procesos

18 03 2008 Programación
    Tras ver como se pueden generar varios procesos empleando fork ahora veremos como podemos controlar sus tiempos de ejecución con wait, waitpid y waitid.

    Esta es la firma de las dos primeras funciones:

pid_t wait(int *status)
pid_t waitpid(pid_t pid, int *status, int options)

    Estas funciones se utilizan para esperar hasta que un proceso cambie de estado. Se emplean como ya hemos comentado para esperar por un cambio de estado en un proceso hijo del proceso que realiza la llamada ha estas funciones. Un cambio de estado para el proceso hijo puede ser uno de estos 3: el hijo ha muerto, el hijo ha sido detenido por una señal o el hijo continua su ejecución tras recibir una señal apropiada (resume).

    Si el hijo ha cambiado de estado antes de la ejecución del wait entonces la llamada a esta función retornará inmediatamente. En caso contrario la llamada bloqueará el proceso hasta que se produzca este cambio de estado.

    wait() espera hasta que uno cualquiera de los hijos del proceso que realiza la llamada a wait cambie de estado. waitpid en su lugar suspende la ejecución del proceso actual hasta que el hijo, especificado por el argumento pid cambie su estado. Por defecto, waitpid espera sólo por la muerte de los hijos, pero este comportamiento es modificable mediante el parámetro options.

    El valor de pid puede tomar estos valores

    Más pequeño que -1 hace que se espere por cualquier hijo cuyo id de proceso de grupo sea igual al valor absoluto de este argumento. Igual a -1 esperará por cualquier hijo, el primero en cambiar de estado (igual comportamiento que wait), cero indica que se esperará por cualquier proceso hijo que tenga el mismo id de grupo de procesos y mayor que cero hará que se espere por el hijo cuyo pid coincida con este valor.

    El parámetro optiones es una máscara OR de diversos constantes, sólo las enumeraré pero es sencillo encontrar información sobre ellas utilizando el comando man: WHOHANG, WUNTRACED, WCONTINUED, WIFEXITED, WEXITSTATUS, WIFSIGNALED, WTERMSIG, WCOREDUMP, WIFSTOPPED, WSTOPSIG y WIFCONFIRMED

    Existe además otra función llamada waitid que realiza una función análoga a las anteriores pero proporciona un mayor control sobre que cambios de estado en el hijo deben ser esperados. La firma de la función es la siguiente

int waitid(idtype_t idtype, id_t id, siginfo_t *infop, int options)

    Los archivos de cabecera donde se definen estas 3 funciones y las constantes y tipos necesarios para su utilización están en los archivos de cabecera sys/types.h y sys/wait.h

    Los parámetros id e idtype seleccionan a que hijo(s) se debe esperar, options tiene el mismo significado que en el caso de waitpid().

    En cuanto a los los parámetros que retornas estas tres funciones wait() en caso de éxito devuelve el pid del proceso hijo que ha cambiado de estado. En caso de error devuelve -1. waitpid() en caso de éxito devuelve lo mismo que wait() y en caso de error -1 pero si se ha especificado la constante WHOHANG la función no bloquea y devuelve cero si no hay ningún hijo que haya cambiado de estado. Por último waitid() devuelve cero en caso de éxito o si WHOHANG ha sido activado y no hay hijo que haya cambiado de estado y -1 en caso de error.

    Volviendo a nuestro programa fork vamos ha hacerle unas modificaciones para que el padre espere a la muerte de sus 2 hijos:


#include <sys/types.h>
#include <unistd.h>
#include <stdio.h>

int main(int argc, char *argv[])
{
pid_t pid1, pid2;
int status1, status2;

if ( (pid1=fork()) == 0 )
{ /* hijo */
printf("Hijo 1 (%d, hijo de %d)\n", getpid(), getppid());
}
else
{ /* padre */
if ( (pid2=fork()) == 0 )
{ /* segundo hijo */
printf("Hijo 2 (%d, hijo de %d)\n", getpid(), getppid());
}
else
{ /* padre */
/* Esperamos al primer hijo */
waitpid(pid1, &status1, 0);
/* Esperamos al segundo hijo */
waitpid(pid2, &status2, 0);
printf("Padre (%d, hijo de %d)\n", getpid(), getppid());
}
}

return 0;
}



    waitpid hace que se espere hasta que terminen los dos hijos identificados en el programa por pid1 y pid2

    Para compilar y ejecutar este programa copia el fragmento de código en un fichero llamado forks.c y después en el mismo directorio donde lo has grabado ejecuta las siguientes líneas

$ gcc forks.c
$ ./a.out

Recuerda que para ver la pid de la shell donde ejecutas el programa debes ejecutar:

$ echo $$





Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at del.icio.us Digg wait, waitpid y waitid, gestión de múltiples procesos Mixx wait, waitpid y waitid, gestión de múltiples procesos Bloglines wait, waitpid y waitid, gestión de múltiples procesos Technorati wait, waitpid y waitid, gestión de múltiples procesos Fark this: wait, waitpid y waitid, gestión de múltiples procesos Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at YahooMyWeb Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at Furl.net Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at reddit.com Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at blinklist.com Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at Spurl.net Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at NewsVine Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at Simpy.com Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at blogmarks Bookmark wait, waitpid y waitid, gestión de múltiples procesos  with wists Bookmark wait, waitpid y waitid, gestión de múltiples procesos  at Ma.gnolia.com wong it! Bookmark using any bookmark manager! Stumble It!

Referencias


No hay referencias

Comentarios

Mostrar comentarios como (Plano | Hilos)
No hay comentarios

Añadir comentario


Encerrando entre asteriscos convierte el texto en negrita (*palabra*), el subrayado es hecho así: _palabra_.
Smilies normales como :-) y ;-) son convertidos en imágenes.