Signalwarteschlangen in C

Lesezeit: 2 Minuten

Benutzer-Avatar
Peter Krejci

Ich habe ein einfaches Programm unter Linux, das in einem Zyklus ein SIGUSR1-Signal an seinen untergeordneten Prozess sendet. Aber wenn ich zB 10 Signale sende, kommt es manchmal vor, dass das Kind nur 3 davon bekommt. Das zuletzt gesendete Signal ist immer SIGUSR2 und wird jedes Mal empfangen.

Stehen die Signale in der Warteschlange, oder wenn der Prozess das vorherige nicht verarbeitet hat, wird es einfach überschrieben? Gibt es eine Möglichkeit, Signale in einer Warteschlange zu senden?

Benutzer-Avatar
Mailand

Folgendes passiert:

  1. Erstes empfangenes Signal, nämlich SIGUSR1, Handler wird aufgerufen und läuft
  2. Zweites Signal empfangen, da Handler von nr1 noch läuft, wird das Signal nr2 anstehend und blockiert.
  3. Drittes Signal empfangen, da Handler von Nr1 noch läuft, wird Signal 3 verworfen.
  4. Viertes, fünftes … usw. Signal des gleichen Typs wie das Signal nr1 werden verworfen.

Sobald der Signalhandler mit Signal Nr1 fertig ist, verarbeitet er Signal Nr2, und dann verarbeitet der Signalhandler SIGUSR2.

Grundsätzlich werden anstehende Signale des gleichen Typs nicht in die Warteschlange gestellt, sondern verworfen. Und nein, es gibt keine einfache Möglichkeit, Signale auf diese Weise zu senden. Man geht immer davon aus, dass es mehrere Signale geben kann, die verworfen werden, und versucht, den Hundeführer die Arbeit des Putzens und Ermittelns zu überlassen (z. B. Kinder ernten, wenn alle Kinder gleichzeitig sterben).

  • Vielen Dank, das war das Problem. Meine Lösung ist also, dass ich nach jedem empfangenen SIGUSR1 im untergeordneten Prozess mit SIGUSR2 antworte und der übergeordnete Prozess kein weiteres SIGUSR1 sendet, bevor er die SIGUSR2-Bestätigung vom untergeordneten Prozess erhält. Und es scheint zu funktionieren! Noch einmal vielen Dank:)

    – Peter Krejci

    12. März 2011 um 22:52 Uhr

Benutzer-Avatar
kubi

Wenn mehrere Signale desselben Typs gesendet und nicht verarbeitet werden, werden sie nicht in die Warteschlange gestellt. Sprich die Programmmasken SIGUSR1Anrufe kill(getpid(), SIGUSR1) 10 mal und demaskiert SIGUSR1. Es wird erhalten SIGUSR1 nur einmal.

Ihr Problem ist wahrscheinlich, dass SIGUSR2 ein Signal ist, das sofort geliefert wird, während andere Signale blockiert oder in die Warteschlange gestellt werden (im Status „Pending“).

So können Sie nach ausstehenden Signalen suchen: http://www.gnu.org/s/libc/manual/html_node/Checking-for-Pending-Signals.html

Benutzer-Avatar
Sami Kivistö

Das gleichzeitige I/O vieler Dateien mit SIGIO scheint also nur möglich zu sein, wenn man Flag verwendet SA_NODEFER für struct sigaction sa_flags Feld und blockiert niemals Signale.

Dann könnte man einen Interrupt aus einem Signalhandler heraus bekommen und einen neuen Thread für jedes einzelne verarbeitete Signal erstellen. Das wird kompliziert 🙂 Kein Wunder also, dass anscheinend niemand SIGIO verwendet.

1175260cookie-checkSignalwarteschlangen in C

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy