![ein Kapitel weiter](../weiter.gif)
Auf Linuxsystemen gibt es außer dem von ANSI-C vorgeschriebenen Signalkonzept noch
ein besseres Konzept. Dies wurde entwickelt da beim alten Signalkonzept folgendes
zu Bemängeln war......
- Erfragen des akutellen Signalstatuses war nicht so ohne weiteres möglich
- Konlikte zwischen 2 gleichen Signalen im selben Programm. Beispielsweise
SIGINT. Ein Signalhandler soll diese Funktion ignorieren und ein anderer
eine bestimmte Fuktion ausführen. Dies können durcheinandergeraten.
Dafür wurde das neue Signalkonzept gemacht.
Zuerst benötigen wir eine Variable vom primitven Datentypen sigset_t
Beispielsweise....
sigset_t signal_menge;
Zuerst müssen wir die Signalmenge initialisieren mit der Funktion sigemptyset........
#include <signal.h>
int sigemptyset(sigset_t *sig_m);
Mit dieser Funktion werden alle Signalmengen aus sig_m entfernt und gleichzeitg wird
die Variable hiermit initialisiert. Mit dem Beispiel unserer Variable sieht dies
jetzt folgendermaßen aus........
sigset_t signal_menge;
sigsetempty(&signal_menge);
Da wir ja jetzt eine Art Maske für unsere Signalmenge haben, können wir fröhlich neue
Signale für diesen Prozeß hinzufügen. Dies machen wir mit der Funktion.......
#include <signal.h>
int sigaddset(sigset_t *sig_m, int signr);
Die Signalemenge sig_m ist die selbe die wir mit sigemptyset initialiert haben. signr
sind die Signale die sie der Signalmenge hinzufügen wollen. Auch hier sei geraten
den symbolischen Namen zu verwenden. Weiter zu unserem Beispiel......
sigset_t signal_menge;
sigemptyset(&signal_menge);
sigaddset(&signal_menge, SIGINT);
sigaddset(&signal_menge, SIGCHLD);
Hier haben wir SIGINT und SIGCHLD zu unserer Signalmenge hinzugefügt.
Im Gegensatz dazu könnten sie mit der Funkion....
#include <signal.h>
int sigdelset(setsig_t *sig_m, int signr);
...das Signal signr aus der Signalmenge sig_m entfernen.
Wollen sie jetzt überprüfen ob ein Signal in der Menge vorhanden ist um es anschließend
zu setzen, falls es noch nicht vorhanden ist, können sie folgende Funktion benutzen.......
#include <signal.h>
int sigismember(sigset_t sig_m,int signr);
Wenn ein Signal in der Signalmenge vorhanden ist gibt diese Funktion 1 zurück. Falls nicht dann 0.
In unserem Beispiel........
sigset_t signal_menge;
sigemptyset(&signal_menge);
sigaddset(&signal_menge, SIGINT);
if( (sigismember(&signal_menge, SIGCHLD)) == 0)
sigaddset(&signal_menge, SIGCHLD);
else
printf("SIGCHLD ist bereits in dieser Signalmenge vorhanden!!\n");
Irgendwann werden sie mal vorhaben die Signalmaske zu Erfragen oder
sie zu verändern. Dafür steht Ihnen die Funktion........
#include <signal.h>
int sigprocmask(int wie, const sigset_t *sig_m, sigset_t *alt_sig_m);
Dabei unterscheidet diese Fuktion sich in 3 Fällen...
- sigprocmask(wie, NULL, alt_sig_m);
Hiermit wird die, im gerade laufenden Prozeß, Signalmenge in die Adresse alt_sig_m geschrieben. 'wie' hat in diesem Fall keinen Effekt.
- sigprocmask(wie, sig_m, NULL);
Signalmaske wird geändert. Zu 'wie' kommen wir gleich.
- sigprocmask(wie, sig_m, alt_sig_m);
Zuerst wird die aktuelle im laufenden Prozeß verwendete Signalmaske in alt_sig_m geschrieben oder man könnte auch sagen gesichert. Anschließend wird die Signalmenge sig_m gesetzt. Beispielsweise......
sigprocmask(SIG_BLOCK, &neue_signal_maske, &backup_signal_maske);
/*...viele Zeilen Code später wollen
wir die alte Signalmaske wiederherstellen....*/
sigprocmask(SIG_SETMASK, &backup_signal_maske, NULL);
Folgende drei 'wie' Konstanten stehen in dabei zur Verfügung....
- SIG_BLOCK
Signalmenge bekommt alle in sig_m stehenden Signale hinzugefügt.
- SIG_UNBLOCK
Die in sig_m stehenden Signale werden alle entfernt.
- SIG_SETMASK
Eine neue Signalmaske wird komplett neu erstellt mit den Signale die sich in
sig_m befinden.
Wollen sie die Signalmaske ändern, oder keine Signale während eines bestimmten Codeabschnittes erlauben,
gibt es dafür die Fuktion.....
#include <signal.h>
int sigsuspend(const sigset_t *sig_m);
Mit dieser Funktion können sie einen Prozeß solang blockieren, bis ein Signal eintrifft.
Und wer in sigsuspend parallelen zu der Funktion pause() zieht hat recht. Nur ist sigsuspend
die zuverlässiger Alernative zu pause, da diese mit der Funktion sigprocmask zusammenhängt und eine einzige atomare Operation ist.
Bei Fehler geben übrigens alle Funktionen in diesem Kapitel -1 zurück.
Im nächsten Kapitel werden wir uns ein Beipiel zu diesen neuen Signalfunktionen ansehen.
![ein Kapitel weiter](../weiter.gif)
© 2001,2002 Jürgen Wolf
|