Signaux POSIX en C

Signaux POSIX en C

«En conduisant sur le bord de la route, que faites-vous lorsque vous avez une rencontre avec un signal rouge? Vous arrêtez de conduire un moment pour attendre votre tour jusqu'à ce que le signal devienne vert. De même, lorsqu'un signal a une couleur orange, vous continuez à conduire et à ne jamais arrêter. Les signaux POSIX fonctionnent de la même manière que le signal de la circulation fonctionne. La bibliothèque de signaux POSIX a proposé une fonction très simple à utiliser dans le code C pour générer des signaux, faire attendre vos programmes, et bien d'autres. Cet article montrerait toutes ces fonctions de signal. Nous avons commencé nos exemples avec la création et l'ouverture d'un fichier C."

Exemple 01

Dans le tout premier exemple de signaux POSIX, nous allons démontrer l'utilisation d'une fonction de signal simple () pour créer et invoquer un signal. Par conséquent, nous avons utilisé le signal.h bibliothèque de C pour utiliser les fonctions de signal, le stdio.La bibliothèque H est utilisée pour les fonctions de sortie et d'entrée standard et l'UNISTD.La bibliothèque H est utilisée pour utiliser des structures définies par l'utilisateur, I.e., les fonctions. Le code contient une fonction de gestionnaire simple nommée «manche» avec un argument de type entier «s."Cette variable" S "fonctionnera comme un signal. Il contient une instruction PRINTF simple pour envoyer un signal «Arrête» à l'utilisateur.

La fonction Main () commence par créer un signal en utilisant la fonction «signal» ici tout en utilisant son option «sigint» pour initialiser un signal et la fonction «manche» pour utiliser cette fonction comme gestionnaire de signaux. La boucle «pour» commence à partir de «1», mais elle n'a pas de fin, je.e., ça va incrémenter mais ne s'arrête jamais jusqu'à ce que vous le fassiez vous-même en quittant le programme. La boucle contient une déclaration printf de C pour afficher que nous sommes actuellement dans la fonction principale (). En utilisant le raccourci Ctrl + C, nous pouvons invoquer la fonction Handle () pour afficher un message de signal.

Sur chaque itération de la boucle «pour», il dort pendant 5 secondes puis est incrémenté. Exécutons notre code C de signal après avoir correctement enregistré et supprimé ses erreurs.

#inclure
#inclure
#inclure
poignée vide (int s)
printf ("\ nstop… \ n");

int main()
Signal (sigint, poignée);
pour (int i = 1 ;; i ++)
printf ("% d: main… \ n", i);
sommeil (5);
retour 0;

Lorsque vous exécutez ce programme avec le compilateur de «C» et l'exécutez avec le «.un/.requête out, vous verrez une exécution infinie du fil principal ().

Lorsque nous avons appuyé sur «Ctrl + C» pour invoquer la fonction de gestionnaire de signaux, la fonction Handle () est exécutée et il affiche «Stop» pour le moment. Après cela, le contrôle revient à la méthode Main (), et il recommence à exécuter sa déclaration printf en utilisant la boucle «pour» infinie. Nous avons appuyé sur la touche de raccourci «Ctrl + Z» pour arrêter avec force ce programme.

Disons que vous souhaitez ignorer le signal invoqué par un utilisateur. Cela peut être fait en utilisant le paramètre SIG_IGN de ​​la fonction Signal () sans utiliser de fonction de gestionnaire. Nous utilisons le même code avec un léger changement dans la fonction Signal (). En utilisant cette fonction, lorsqu'un utilisateur invoque un signal à l'aide du raccourci «Ctrl + C», le programme ignorera le signal et continuera d'exécuter le thread de fonction principal (). Voyons rapidement et exécutez ce programme pour voir la sortie.

#inclure
#inclure
#inclure
int main()
Signal (Sigint, SIG_IGN);
pour (int i = 1 ;; i ++)
printf ("% d: ignorer le signal… \ n", i);
sommeil (5);
retour 0;

Après cette exécution de code, l'instruction principale () de la fonction printf () continue de s'exécuter même après avoir utilisé le raccourci «Ctrl + C». Donc, nous avons arrêté avec force le programme à la fin.

Exemple 02

Si vous souhaitez augmenter automatiquement un signal pour votre programme C sans utiliser la clé de raccourci Ctrl + C, vous pouvez également le faire en utilisant la fonction Raisier () de la bibliothèque de signaux. Par conséquent, nous avons mis à jour le code à partir du premier exemple et ajouté à nouveau une fonction Handle (). La fonction Main () commence par la création d'un signal utilisant la fonction Signal () en lui faisant passer une option «Sigusr1» avec la fonction «manche» dans les paramètres. Cette option SIGUSSR1 est la clé pour générer un signal automatique. La boucle «pour» dort 10 secondes après avoir exécuté l'instruction PRINTF, puis appelle la fonction Raisie () avec l'option SIGUSR1 pour générer un signal automatique en appelant la fonction «manche». C'est ça; Nous sommes prêts à exécuter ce programme pour l'instant.

#inclure
#inclure
#inclure
poignée vide (int s)
printf ("\ nraise… \ n");
sommeil (5);

int main()
signal (Sigusr1, poignée);
pour (int i = 1 ;; i ++)
printf ("% d: main… \ n", i);
sommeil (10);
augmenter (Sigusr1);
retour 0;

Après la compilation réussie, l'exécution a lieu. Le fil principal () GPT est exécuté, et le programme dort pendant 10 secondes pendant qu'il est dans la boucle.

Après 10 secondes, la fonction d'élévation a été invoquée pour générer un signal automatique en appelant la fonction de poignée. L'exécution dort pendant les 5 prochaines secondes dans la fonction de poignée.

Le contrôle est rendu à la fonction principale () «Loop», et ce processus se poursuit jusqu'à ce que vous quittez le programme volontiers en utilisant le raccourci Ctrl + Z.

Tout comme votre signal automatique pour votre programme, vous pouvez également tuer le signal après avoir invoqué et envoyer le signal à un groupe de traitement. En d'autres termes, la fonction «Kill» de la bibliothèque des signaux POSIX C a été utilisée pour envoyer des alertes au groupe du programme. Par conséquent, nous avons mis à jour notre programme principal avec sa fonction de manche dans le code d'image décrit ci-dessus. L'objet PID_T est utilisé pour créer un ID «P» pour le processus. La fonction Signal () est appelée ici pour créer un signal à travers l'utilisation de la fonction Handle () définie auparavant à partir de la fonction principale.

La fonction getpid () est appelée dans la boucle «pour» pour obtenir l'ID de processus de ce thread et l'enregistrer dans une variable «P». Cet ID de processus «P» est transmis à la fonction «Kill» avec l'option SIGUSR1 pour tuer le signal et envoyer son rapport à un groupe de progrès. Ensuite, un programme dort 8 secondes et imprime «Back in Main» tandis que la boucle continue.

#inclure
#inclure
#inclure
poignée vide (int s)
printf ("\ nstop… \ n");

int main()
pid_t p;
signal (Sigusr1, poignée);
pour (int i = 1 ;; i ++)
printf ("% d: main… \ n", i);
p = getpid ();
Kill (P, Sigusr1);
sommeil (8);
printf ("Back in Main \ n");
retour 0;

La fonction est exécutée, envoie le signal au groupe de processus et dort pendant 8 secondes.

Le «dos dans la main» a été exécuté, et la boucle a poursuivi le même traitement.

Conclusion

Ce guide a démontré l'utilisation des fonctions de signal dans le programme C pour rendre votre environnement de travail plus efficace. Pour cela, nous avons essayé la fonction Signal () de POSIX, la fonction KIL () et Raising () avec les options SIGINT, SIG_IGN et SIGUSR1 dans les fonctions.