signale nicht posix & ansi konform?

Disclaimer: Dieser Thread wurde aus dem alten Forum importiert. Daher werden eventuell nicht alle Formatierungen richtig angezeigt. Der ursprüngliche Thread beginnt im zweiten Post dieses Threads.

signale nicht posix & ansi konform?
hi,

bin mittlerweile bis zu den signalen vorgekommen und kann den quellcode nur ohne den ansi- und posix-flag kompilieren. muss das so sein oder hab ich noch irgendwas falsch gemacht?


welche signale meinst du?
mysh oder wo bist du?


sigset_t set;
sigemptyset(&set);
sigaddset(&set, <SIGNAL>);
if(sigprocmask(<SIG_BLOCK | SIG_UNBLOCK>, &set, NULL)) {
    /* Fehlerbehandlung */
}

laut Manpages POSIX-konform …


falls Du SA_RESTART verwendest musst du mit XOPEN_SOURCE=500 kompilieren statt mit POSIX_SOURCE


ok, danke!
komischerweise hat es mit ansi aber ohne posix nicht funktioniert, nur wenn ich beides weggelassen habe.
kannst du (oder jemand anderes) vielleicht kurz erklaeren, was es mit diesen flags und zugehoerigen standards auf sich hat? wie man sieht, hab ich das nicht wirklich verstanden…


klar du siehst in der Manpage zur jeweiligen Funktion in welchen Standards diese grundsätzlich enthalten ist

Nun kann es, wie in diesem Fall vorkommen, dass einzelne Flags nicht in allen Standards enthalten sind, so etwas wird dann unter Notes erwähnt.

normalerweise steht es auch auf der Aufgabenstellung wenn nicht mit POSIX_SOURCE kompiliert werden kann, aber die Verwendung von SA_RESTART ist hier ja nicht zwingend also ist das ganze auch POSIX konform realisierbar!


Und wegen -ansi → sigaction ist ja wie aus der manpage ersichtlich nicht in ANSI C enthalten.
Wenn Du also -ansi angibst nimmt der gcc nur noch Sachen die ANSI-C konform sind.

Wenn du dem gcc GAR NICHTS mit gibst nimmt er alles was er finden kann.

Wenn Du neben ansi auch noch andere Makros wie D_XOPEN… nimmst, wird die “Vereinigungsmenge” der Funktionen genommen :wink:


Wie bring ich eigentlich meine Hintergrundprozesse dazu, das SIGINT zu ignorieren?

Ist das eigentlich normal, wenn ich einen Signalhandler beim Starten der Shell registriere, dass Vordergrundprozesse durch einen Interrupt ordnungsgemäß sterben, meine Hintergrundprozesse aber zu Zombies mutieren?

Und wieso wird meine Shell gekillt, wenn ich nur einen Prompt vor mir habe und einen Interrupt auslöse?

Erscheint mir alles ein bisschen suspekt :#:


Die Signalbehandlung bleibt ueber das exec hinweg erstmal erhalten, solang bis das da umgesetzt wird

„ordnungsgemäß sterben“ na rat mal, wer dafuer sorgt, dass die das tun! genau die shell aus der heraus du die trsh gestartet hast g
Was willst du eigentlich genau wissen?

So ist eben die Semantik des Signals, die zu ändern steht dir (bei vielen) Signalen frei, bzw so frei wie eben die Aufgabenstellung g


Mich hätte interessiert, wieso meine aus der trsh gestarteten Hintergrundprozesse in eine Zombiezustand fallen, wenn ich einen aus der trsh gestarteten Vordergrundprozess mit Strg+C abschieße.

Ich würde mich freuen, wenn du deine umfassende Weisheit mit mir teilen würdest.


Andere Frage: Was füe ne PID muss ich kill denn mitgeben, dass das SIGQUIT nur an alle Sohn-Prozesse geschickt wird? Wenn man für pid die 0 wählt wird anscheinend auch die trsh selbst ge"quit"et… :-/


ich hab jetzt da noch nix gemacht, aber ich geh mal davon aus, die PIDs derer prozesse, die sich killen sollen?
:wink:
also jew…


das würde bedeuten ich müsste die PIDs aller Sohnprozesse, die jemals erzeugt wurden, irgendwo speichern und im INTERRUPT-Fall mit kill ein SIGQUIT an all die Prozesse einzeln schicken? Klingt nach Arbeit… :-/


ja, aber die musst du sowieso irgendwo speichern (sogar mit kommandozeilenaufruf), damit du sie spaeter mit waitpid () einsammeln kannst. ich weiss ja nicht, wie du das bis jetzt realisiert hast?!
dafuer kannst du aber glaube ich die joblist nehmen (vom mikey, nicht die vom lehrstuhl, siehe anderer thread). ich weiss das nicht so genau, weil ich mir schon selber eine struktur gemacht hatte (nach unendlichen segfaults funktioniert diese nun auch). btw: ist das ok, wenn ich die joblist NICHT benutze, sondern etwas selberdefiniertes?


@steppenwolf: nein bitte benutzt die vorgegebene jobliste… (siehe aufgabestellung…)

die in meinem wwwcip ist bis auf den einen free mit der im /pub identisch :wink:
Es ist auch kein Problem die vom Lehrstuhl zu verwenden weil euch das sicher nicht als Fehler angekreidet wird, nur zum Testen auf Memory Leaks ist die natürlich denkbar ungeeignet…


also ich glaub ich hab da generell was nicht verstanden - bitte helft mir:

Wenn ich einen Hintergrundprozess erzeuge, soll meine trsh doch ausdrücklich NICHT auf diesen warten (waitpid), sondern gleich wieder ein neues Commando einlesen können, also wieder zur main-Funktion zurückehren. Wie bitte schön soll ich all meine Hintergrundprozesse dann wieder auflesen und deren exit-status auslgeben können?
verzweifel
:moody:


ja, du sollst nicht auf sie warten,
allerdings musst du regelmaessig checken, ob sie gestorben sind und sie dann einsammeln um den exitstatus auszugeben.

anleitung:

  • hintergrundprozesse beim erstellen in die joblist einfuegen
  • diese regelmaessig (du musst dir halt ueberlegen, wann das sinnvoll ist) mit waitpid (NOHANG) auf zombiezustand ueberpruefen
  • ggf. exitstatus ausgeben, wenn gestorben

alles klar?


ein Signalhandler, der die SIGCHLD entgegen nimmt, bietet sich da an um ein waitpid auf Hintergrundprozesse zu machen.
Damit bleiben dann auch keine Zombies uebrig.
Regelmaessiges pruefen nennt man polling bzw. “aktives warten”, das ist natuerlich nicht so ideal.

edit: aber bitte nie ein waitpid ohne NOHANG im Signalhandler! Auch Dateioperationen haben da nix verlohren.


wenn du es mal programmierst wirst du feststellen dass es nicht so ideal (bzw schoen) ist, wenn dir der signalhandler an beliebigen stellen (zB wenn du gerade ein kommando eingibst) den exitstatus des bg prozesses reinknallt. deshalb finde ich das polling doch die schoenere loesung

(btw >> wann gibt denn die bash den exitstatus aus :wink: )