Le pid d'un SIGCHILD

Le pid d'un SIGCHILD - C++ - Programmation

Marsh Posté le 11-01-2006 à 22:17:00    

Bonjour à tous,
 
J'utilise les signaux en C++, et en particulier je déroute l'un de ceux-ci, SIGCHLD, à l'aide de la fonction sigaction. (SIGCHLD est le signal qui indique la mort d'un processus fils)
Or dans ma fonction de déroutage, j'aurais aimé connaitre le PID du processus fils mort, et là je ne vois pas comment faire.
Si qqun aurait une solution, merci d'avance...

Reply

Marsh Posté le 11-01-2006 à 22:17:00   

Reply

Marsh Posté le 11-01-2006 à 22:47:55    

samycookie a écrit :

Bonjour à tous,
 
J'utilise les signaux en C++, et en particulier je déroute l'un de ceux-ci, SIGCHLD, à l'aide de la fonction sigaction. (SIGCHLD est le signal qui indique la mort d'un processus fils)
Or dans ma fonction de déroutage, j'aurais aimé connaitre le PID du processus fils mort, et là je ne vois pas comment faire.
Si qqun aurait une solution, merci d'avance...


 
Dès le "fork()" le père stocke le pid créé dans un tableau des pid défini en global.
Dans ta fonction de déroutage, tu balayes le tableau avec "wait(p" ou "waitpid()" et tu identifies le pid qui n'y est plus.


---------------
Vous ne pouvez pas apporter la prospérité au pauvre en la retirant au riche.
Reply

Marsh Posté le 11-01-2006 à 22:53:33    

Et s'il utilise juste wait dans le handler du SIGCHLD, cela lui permet de récupérer le pid du fils qui vient de mourir, non ?
 
http://www.linux-kheops.com/doc/ma [...] ait.2.html
 
Par contre il faut faire attention dans le cas ou plusieurs fils meurent en même temps :
 

Citation :

On some flavors of Unix, the SIGCHLD signal handler is called if
one *or more* children have died.  This means that if your signal
handler only does one wait() call, then it won't clean up all of
the children.  Fortunately, I believe that all Unix flavors for
which this is the case have available to the programmer the
wait3() or waitpid() call, which allows the WNOHANG option to
check whether or not there are any children waiting to be cleaned
up.  Therefore, on any system that has wait3()/waitpid(), your
signal handler should call wait3()/waitpid() over and over again
with the WNOHANG option until there are no children left to clean
up.


Message édité par fat le 11-01-2006 à 22:58:27
Reply

Marsh Posté le 12-01-2006 à 09:17:56    

moi je te conseille avant tout de toujour utiliser waitpid plutôt que wait.

Reply

Marsh Posté le 12-01-2006 à 16:55:08    

BILAN
- Sve@r : J'ai utilisé ta méthode, et après en avoir bavé parce que je faisais n'importe quoi avec waitpid(). J'utilisais celle avec en deuxieme parametre la variable int & Status, qui renvoie des infos sur la mortdu fils, et Status(WIFEXITED) selon le man devrait m'informer de sa mort ou non, et  ben ca renvoie nimporte nawak ^^ En fait suffisait juste de prendre les valeurs de retour qui étaient à 0 si le fils était encore vivant, en gros prise de tête pour rien. Au final, ca marche au poil
- fat : je pouvait pas récupérer le pid si facilement au vu du fait qu'elle n'était pas directement capturé par un waitpid, mais par une fonction de déroutage
- Taz : en effet, waitpid cay mieux ^^
 
Merci de vos réponses

Message cité 1 fois
Message édité par samycookie le 12-01-2006 à 16:56:16
Reply

Marsh Posté le 12-01-2006 à 18:04:42    

Je suppose que lorsque tu parle de fonction de déroutage, tu parles de fonction handler pour le signal SIGCHLD, un handler mis en place en utilisant la fonction signal.
si c'est bien le cas, tu peux récupérer le pid du fils mort ayant généré le SIGCHLD par un wait dans le handler
 
exemple :
 
...
signal(SIGCHLD,handler_sigchld);
...
 
 
void handler_sigchld(int truc)
{
pid_t pid_fils;
 
pid_fils=wait(NULL);
...
 
}

Reply

Marsh Posté le 13-01-2006 à 00:46:05    

samycookie a écrit :

BILAN
- Sve@r : J'ai utilisé ta méthode, et après en avoir bavé parce que je faisais n'importe quoi avec waitpid(). J'utilisais celle avec en deuxieme parametre la variable int & Status, qui renvoie des infos sur la mortdu fils, et Status(WIFEXITED) selon le man devrait m'informer de sa mort ou non, et  ben ca renvoie nimporte nawak ^^


 
C'est plus cat. C que C++. Mais je vois pas la difficulté...
 


#include <sys/types.h>
#include <sys/wait.h>
#include <time.h>
#include <stdlib.h>
 
// Tableau des 10 fils
int tabPid[10];
 
int main ()
{
   int i,j;                          // Pour les boucles
   int pid;                        // pid fils créé/mort
   int status;                   // état fils mort (cause de sa mort)
   extern int tabPid[10];    // Juste pour être rigoureux (déclaration dans le bloc des variables utilisées par le bloc, même si elles sont globales)
 
   // initialisation germe aléatoire
   srand(time(NULL));
 
   // Création des 10 fils
   for (i=0; i < 10; i++)
   {
        if ((pid=fork()) == 0)
        {
             // Fils
 
             // Dormir aléatoirement entre 10 et 30 sec
             sleep(rand() % 20 + 10);
 
             // Sortir par kill ou exit suivant aléa pair ou impair
             if ((rand() % 2) == 0)
                 kill(getpid(), 15);
             else
                 exit(123);
        }
        else
            // Père => stockage du pid
            tabPid[i]=pid;
   }
 
   // Gestion de la mort des 10 fils
   for (i=0; i < 10; i++)
   {
       // Attente d'une mort quelconque
       pid=wait(&status);
 
       // Recherche fils mort
       for (j=0; j < 10; j++)
       {
            if (tabpid[j]==pid)
               break;
       }
             
       // Affichage fils mort
       if (WIFEXITED(status))
           // Mort par exit
           printf("Fils %d (pid=%d) mort par exit(%d)\n", j + 1, tabPid[j], WEXITSTATUS(status));
      else
           // Mort par kill
           printf("Fils %d (pid=%d) mort par kill(%d)\n", j + 1, tabPid[j], WTERMSIG(status));
}


 
=> fat, ton idée est bonne mais que faire après de ton pid ? Tu peux pas le renvoyer puisque ton handler est impérativement de type "void"...


Message édité par Sve@r le 13-01-2006 à 00:48:28

---------------
Vous ne pouvez pas apporter la prospérité au pauvre en la retirant au riche.
Reply

Marsh Posté le 13-01-2006 à 10:22:01    

Dans le handler, tu peux en faire ce que tu veux, tu peux par exemple le supprimer de la liste des fils.
 
Mais je pense aussi qu'utiliser waitpid est plus sur, notamment avec l'option WNOHANG, ce qui permet à waitpid de retourner tout de suite sans attendre la mort du fils, ce qui bloquerait le programme.
 
 
 

Reply

Marsh Posté le 14-01-2006 à 23:18:16    

fat a écrit :

Mais je pense aussi qu'utiliser waitpid est plus sur, notamment avec l'option WNOHANG, ce qui permet à waitpid de retourner tout de suite sans attendre la mort du fils, ce qui bloquerait le programme.


 
Exact. WNOHANG est un bon truc !!!


---------------
Vous ne pouvez pas apporter la prospérité au pauvre en la retirant au riche.
Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed