fork () i sposób dostarczania sygnałów do procesów

13

Programuję, że napisałem w C fork () poza procesem potomnym. Żaden proces nie zostanie zakończony. Jeśli uruchomię program z wiersza poleceń i naciśniesz control-c, który proces (procesy) otrzyma sygnał przerwania?

Neil Locketz
źródło

Odpowiedzi:

20

Dlaczego tego nie wypróbujemy i nie zobaczymy? Oto trywialny program wykorzystujący signal(3)pułapkę SIGINTzarówno w procesie nadrzędnym, jak i podrzędnym oraz do wydrukowania komunikatu identyfikującego proces po jego nadejściu.

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <signal.h>
void parent_trap(int sig) {fprintf(stderr, "They got back together!\n");}
void child_trap(int sig) {fprintf(stderr, "Caught signal in CHILD.\n");}
int main(int argc, char **argv) {
    if (!fork()) {
        signal(SIGINT, &child_trap);
        sleep(1000);
        exit(0);
    }
    signal(SIGINT, &parent_trap);
    sleep(1000);
    return 0;
}

Nazwijmy to test.c. Teraz możemy go uruchomić:

$ gcc test.c
$ ./a.out
^CCaught signal in CHILD.
They got back together!

Sygnały przerwań generowane w terminalu są dostarczane do aktywnej grupy procesów, która obejmuje tutaj zarówno element nadrzędny, jak i podrzędny . Możesz to zobaczyć child_trapi parent_trapzostały wykonane, gdy nacisnąłem Ctrl- C.

Jest długi omówienie interakcji pomiędzy forki sygnałów POSIX . Najbardziej materialną częścią tego jest to, że:

Sygnał wysyłany do grupy procesów po rozwidleniu () powinien być dostarczany zarówno do rodzica, jak i dziecka.

Zauważają również, że niektóre systemy mogą nie zachowywać się dokładnie w odpowiedni sposób, w szczególności gdy sygnał zbliża się bardzo blisko czasu fork(). Ustalenie, czy korzystasz z jednego z tych systemów, prawdopodobnie będzie wymagać przeczytania kodu lub dużo szczęścia, ponieważ interakcje są znikome w każdej próbie.

Inne przydatne punkty to:

  • Sygnał wygenerowany ręcznie i wysłany do indywidualnego procesu (być może z kill) zostanie dostarczony tylko do tego procesu, niezależnie od tego, czy jest to rodzic, czy dziecko.
  • Kolejność, w której procedury obsługi sygnałów działają między procesami, nie jest zdefiniowana, więc nie można polegać na żadnym z nich.
  • Jeśli nie zdefiniujesz modułu obsługi przerwań (lub jawnie zignorujesz sygnał), oba procesy zakończą się SIGINTkodem (zachowanie domyślne).
  • Jeśli jeden traktuje sygnał nieśmiertelnie, a drugi nie, jeden bez przewodnika umrze, a drugi będzie kontynuował.
Michael Homer
źródło
Zakładam, że pociski mogą również przeszkadzać w interesujący sposób? Jeśli jest to sygnał, że mogą złapać w pułapkę, może wysłać go do swoich dzieci? (A potem jest SIGHUP) (Wszystko to może oznaczać, że chociaż system operacyjny nie wysyła sygnałów, proces potomny może nie zostać zakłócony przez sygnał do rodzica ...)
Gert van den Berg