PPID — identyfikator procesu macierzystego Ani w Uniksie, ani w Linuksie nie ma funkcji systemowej, która inicjalizowałaby nowy procesprzez uruchomienie jakiegoś określonego programu. Odbywa się to w dwóch krokach. Aby powstał nowy proces, jakiś istniejący proces musi się sklonować. Sklonowany proces może następnie zastąpić wykonywany program innym. Po sklonowaniu pierwotny proces jest określany jako macierzysty, a kopia nazywana jest procesem potomnym. Atrybutem PPID danego procesu jest identyfikator PID procesu macierzystego, z którego został sklonowany.
Identyfikator procesu macierzystego to przydatna informacja w sytuacji, gdy napotykasz nieznany (i być może niewłaściwie działający) proces. Wyśledzenie pochodzenia procesu (czy byłato powłoka, czy inny program) może dać Ci wskazówki dotyczące jego przeznaczenia i wagi. UID i EUID — rzeczywisty i efektywny identyfikator użytkownika Identyfikator UID procesu to numer identyfikacyjny użytkownika, który utworzył proces, a do-kładniej mówiąc, jest to kopia wartości UID procesu macierzystego. Zazwyczaj procesem mogą manipulować tylko jego twórca (czyli „właściciel”) i superużytkownik.

EUID to „efektywny” identyfikator użytkownika, dodatkowy identyfikator UID, który określa, do jakich plików i zasobów proces może w danym momencie uzyskać dostęp. Dla większości procesów identyfikatory UID i EUID są takie same, typowym wyjątkiem są programy z ustawionym atrybutem setuid.

Po co aż dwa identyfikatory, UID i EUID? Po prostu dlatego, że jest to przydatne, gdyż pomaga zachować rozróżnienie między tożsamością a uprawnieniami, a także dlatego, że program z ustawionym atrybutem setuid nie zawsze powinien działać przez cały czas z rozszerzonymi uprawnieniami. W większości systemów efektywny identyfikator UID może być ustawiany i kasowany, aby włączać lub ograniczać dodatkowe uprawnienia, jakie daje. Większość systemów śledzi również „zachowany UID”, który jest kopią identyfikatora EUID procesu w momencie, gdy proces po raz pierwszy rozpoczyna swoje działanie. Jeśli proces nie podejmie kroków w celu wymazania tego zapisanego UID, pozostanie on dostępny do wykorzystania jako rzeczywisty lub efektywny UID. Konserwatywnie napisany program setuid może więc zrzec się swoich specjalnych przywilejów przez większą część swojego czasu wykonywania, korzystając z nich tylko przy określonych działaniach, które wymagają dodatkowych uprawnień. System Linux definiuje również niestandardowy parametr procesu FSUID, który odpowiada za określenie praw dostępu do systemu plików. Jest on rzadko używany poza jądrem i da się go przenieść na inne systemy uniksowe. Przynajmniej początkowo. Jeśli pierwotny proces zakończy działanie, nowym procesem macierzystym stanie się init (proces o identyfikatorze 1);

GID i EGID — rzeczywisty i efektywny identyfikator grupy GID to numer identyfikacyjny grupy procesu. EGID jest powiązany z GID w taki sam sposób, jak EUID jest związany z UID, w tym znaczeniu, że może być „podwyższony” przy wykonywaniu programu z atrybutem setgid. Podobnie jak w przypadku zachowanego UID, jądro utrzymuje zachowany GID dla każdego procesu. Atrybut GID procesu ma przeważnie znaczenie szczątkowe. Dla celów określania praw dostępu proces może być członkiem wielu grup naraz. Pełna lista grup przechowywana jest oddzielenie od wyróżnionych GID i EGID. Przy określaniu uprawnień dostępowych zwykle bierze się pod uwagę EGID i uzupełniającą listę grup, ale nie GID.

Jedyny moment, kiedy GID ma jakieś znaczenie, występuje wtedy, gdy proces tworzy nowe pliki. W zależności od tego, jak ustawione zostały uprawnienia systemu plików, nowe pliki mogą przyjmować domyślnie identyfikator GID tworzącego je procesu. Uprzejmość Priorytet przełączania procesu decyduje o tym, ile czasu procesora zostanie mu przydzielne. Jądro wylicza priorytety przy użyciu algorytmu dynamicznego, uwzględniając ilość czasu procesora, jaką proces ostatnio wykorzystał, oraz jego czas oczekiwania na wykonanie. Jądro zwraca też uwagę na administracyjnie ustawioną wartość zwaną zwykle „uprzejmością” (ang.nice value, niceness). Nazwa pochodzi stąd, że wartość ta określa, na ile uprzejmy zamierzasz być w stosunku do innych użytkowników systemu. Terminal sterujący Większość procesów niebędących demonami ma swoje terminale sterujące. Terminal sterujący określa domyślne połączenia kanałów standardowego wejścia, standardowego wyjścia i standardowego błędu. Rozprowadza również sygnały do procesów w odpowiedzi na zdarzenia pochodzące z klawiatury, takie jak kombinacja klawiszy Ctrl+C. Oczywiście rzeczywiste terminale są obecnie rzadko spotykane poza muzeami kompute rowymi. Niemniej jednak istnieją one w postaci pseudoterminali, które nadal są szeroko stosowane w systemach Unix i Linux. Gdy uruchomisz polecenie z poziomu powłoki, okno terminala stanie się terminalem sterującym tego procesu.

4.2. CYKL ŻYCIA PROCESU
Aby utworzyć nowy proces, istniejący proces kopiuje się za pomocą funkcji systemowej fork3. Funkcja fork tworzy kopię pierwotnego procesu, która w dużej mierze jest identyczna z proce sem macierzystym. Nowy proces ma inny identyfikator PID i własne informacje rozliczeniowe. Funkcja fork ma unikatową właściwość zwracania dwóch różnych wartości. Z punktu widzenia procesu potomnego zwraca zero. Proces macierzysty otrzymuje natomiast PID nowo utworzonego procesu potomnego. Ponieważ poza tym te dwa procesy są identyczne, oba muszą sprawdzić zwracane wartości, aby ustalić, jaką rolę mają odgrywać. Po wykonaniu funkcji fork proces potomny często używa jednej z funkcji z rodziny exec, aby rozpocząć wykonywanie nowego programu. Funkcje te wymieniają program wykonywany przez proces i przywracają segmenty pamięci do predefiniowanego stanu początkowego. Odmienne formy funkcji exec różnią się jedynie sposobem, w jaki określają argumenty wiersza poleceń i środowisko dla nowego programu. Przy rozruchu systemu jądro autonomicznie tworzy i instaluje kilka procesów. Najważniejszy z nich to init lub systemd, których numer identyfikacyjny jest zawsze równy 1. Pro ces ten odpowiedzialny jest za wykonywanie skryptów startowych systemu, choć dokładny sposób wykonywania tej czynności różni się nieco w Uniksie i w Linuksie. Wszystkie procesy, poza tymi utworzonymi przez jądro, są procesami potomnymi tego procesu pierwotnego. Proces init (lub systemd) odgrywa również ważną rolę w zarządzaniu procesami. Gdy proces zakończy swoje działanie, wywołuje funkcję _exit, aby powiadomić jądro, że jest gotowy do zamknięcia. Podaje przy tym kod zakończenia (będący liczbą całkowitą) informujący o przyczynie zakończenia pracy. Zgodnie z konwencją kod 0 oznacza normalne lub „pomyślne” zakończenie działania. Zanim proces będzie mógł całkowicie zniknąć, jądro wymaga, aby informacja o jego zniszczeniu była potwierdzona przez proces macierzysty, co odbywa się za pomocą wywołania funkcji wait przez proces macierzysty. Proces macierzysty odbiera kopię kodu zakończenia procesu potomnego (albo informację o tym, dlaczego proces został unicestwiony, jeśli nie zrobił tego dobrowolnie); na życzenie może też otrzymać zestawienie zasobów używanych przez proces potomny. Taki schemat działa poprawnie w sytuacji, gdy proces macierzysty żyje dłużej niż jego procesy potomne i zawsze usuwa je przez wywoływanie funkcji wait. Jeśli jednak proces macierzysty zostanie unicestwiony jako pierwszy, jądro rozpozna, że nie nadejdą już żadne wywołania wait, i przekaże osierocone procesy do adopcji procesowi init lub systemd, a one uprzejmie przeprowadzą wywołania funkcji wait, aby je usunąć, gdy zostaną zakończone. Sygnały Sygnały są żądaniami przerwań na poziomie procesu. Istnieje około trzydziestu różnego rodzaju przerwań, których używa się na różne sposoby. Technicznie rzecz biorąc, systemy linuksowe korzystają z clone, nadzestawu fork, który obsługuje wątki i posiada dodatkowe funkcje. fork pozostaje w jądrze dla zapewnienia zgodności wstecznej, ale za kulisami wywołuje funkcję clone.

ROZDZIAŁ 4. KONTROLOWANIE PROCESÓW
 Mogą być przesyłane między procesami jako środek komunikacji.
 Mogą być wysyłane przez sterownik terminala, aby zabić, przerwać lub zawiesić procesy po naciśnięciu skrótów klawiszowych, takich jak Ctrl+C i Ctrl+Z4.
 Mogą być wysyłane przez administratora (poleceniem kill), aby uzyskać różne zakończenia działania.
 Mogą być wysyłane przez jądro, gdy proces wykona niedozwolone działanie, np. dzielenie przez zero.
 Mogą być wysyłane przez jądro, aby powiadomić proces o „interesującej” go sytuacji, takiej jak zabicie procesu potomnego lub dostępność danych na kanale wejścia-wyjścia.
Po otrzymaniu sygnału może się zdarzyć jedna z dwóch rzeczy. Jeśli proces odbierający ma wyznaczoną funkcję obsługi tego określonego sygnału, wywoływana jest procedura obsługi z informacją na temat kontekstu, w którym sygnał został odebrany. W przeciwnym razie jądro podejmuje domyślne działanie na rzecz procesu. Działania domyślne różnią się w zależności od sygnału. Wiele sygnałów kończy działanie procesu; niektóre powodują również wygenerowanie zrzutu pamięci (jeśli ta funkcja nie została wyłączona).
 Zrzut pamięci (ang. core dump) to obraz pamięci procesu, który jest czasem przydatny przy wykrywaniu błędów. Umieszczenie w programie procedury obsługi sygnału określa się mianem przechwytywania sygnału. Po zakończeniu procedury obsługi proces kontynuuje swoje działanie od miejsca, w którym odebrał sygnał. Aby zapobiec nadsyłaniu sygnałów, programy mogą zażądać, by były one ignorowane lub blokowane. Sygnał zignorowany zostaje po prostu porzucony i nie ma żadnego wpływu na proces. Sygnał zablokowany zostaje umieszczony w kolejce i oczekuje na przekazanie, ale jądro nie wymaga od procesu jego obsługi, dopóki sygnał nie zostanie jawnie odblokowany. Procedura obsługi właśnie odblokowanego sygnału wywoływana jest tylko raz, nawet jeśli sygnał został wysłany kilkakrotnie w czasie blokady przyjmowania. W tabeli 4.1 zawarto listę niektórych sygnałów, które powinien znać każdy administrator.
Konwencja stosowania dużych liter w nazwach pochodzi z tradycji języka C. Z podobnych przyczyn czasem spotyka się nazwy sygnałów z prefiksem SIG (np. SIGHUP). Inne sygnały, niewymienione w tabeli 4.1, zgłaszają głównie nieokreślone błędy w rodzaju „niepoprawna instrukcja”. Domyślnym sposobem obsługi tego rodzaju sygnałów jest zakończenie procesu ze zrzutem pamięci. Przechwytywanie i blokowanie są na ogół dopusz czalne, ponieważ niektóre programy mogą być na tyle sprytne, aby podjąć próbę naprawy problemu, który wywołał błąd, i kontynuować działanie. Sygnały BUS i SEGV są również sygnałami błędów. Dołączyliśmy je do tej tabeli, ponieważ są często spotykane: gdy jakiś program ulegnie awarii, zazwyczaj jeden z tych dwóch sygnałów ostatecznie kończy jego działanie. Sygnały te same w sobie nie mają żadnej wartości diagnostycznej. Oba wskazują na próbę niepoprawnego użycia lub dostępu do pamięci. Sygnały o nazwach KILL i STOP nie mogą być przechwytywane, blokowane ani ignorowane. Sygnał KILL powoduje unicestwienie procesu, który go otrzymał, a sygnał STOP zawiesza jego wykonywanie do czasu otrzymania sygnału CONT. Sygnał CONT może być przechwycony lub zignorowany, ale nie można go blokować.

Za pomocą polecenia stty skróty klawiszowe Ctrl+C i Ctrl+Z mogą być przypisane innym klawiszom, ale w praktyce rzadko się to stosuje. W tym rozdziale będziemy odwoływać się do ich konwencjonalnego przypisania.

Sygnał TSTP to „łagodna” wersja sygnału STOP, którą można opisać jako żądanie zatrzymania. Jest to sygnał generowany przez sterownik terminala po naciśnięciu klawiszy Ctrl+Z. Programy, które przechwycą ten sygnał, zwykle porządkują swój stan, a następnie wysyłają sobie sygnał STOP, aby zakończyć operację zatrzymania. Programy mogą też ignorować sygnał TSTP, aby uniemożliwić ich wyłączenie za pomocą klawiatury. Sygnały KILL, INT, TERM, HUP i QUIT wydają się wykonywać to samo, ale w rzeczywistości ich zastosowanie jest całkiem różne. Szkoda, że wybrano dla nich tak niejednoznaczne nazwy. Oto ich właściwe znaczenia:
 Sygnał KILL jest nieblokowalny i powoduje zakończenie działania procesu na poziomie jądra. W rzeczywistości proces nigdy nie może odebrać lub obsłużyć tego sygnału.
 Sygnał INT jest wysyłany przez sterownik terminala po naciśnięciu klawiszy Ctrl+C. Jest to żądanie zakończenia bieżącej operacji. Proste programy powinny zakończyć działanie (jeśli przechwycą sygnał) albo po prostu zezwolić na zabicie, co jest działaniem domyślnym, gdy sygnał nie jest przechwytywany. Programy udostępniające interaktywny wiersz poleceń (takie jak powłoka) powinny przerwać wykonywanie dotychczasowych zadań, posprzątać i oczekiwać na ponowne wprowadzenie danych przez użytkownika.  Sygnał TERM jest żądaniem definitywnego zakończenia działania. Oczekuje się, że proces, który go odbierze, posprząta swój stan i zakończy działanie.

ROZDZIAŁ 4. KONTROLOWANIE PROCESÓW
 Sygnał HUP ma dwa znaczenia. Po pierwsze, wiele demonów traktuje go jako żądanie zresetowania. Jeśli demon może ponownie wczytać swój plik konfiguracyjny i do stosować się do zmian bez ponownego uruchamiania, na ogół można uzyskać taki efekt za pomocą sygnału HUP. Po drugie, sygnały HUP są czasem generowane przez sterownik terminala, który przystępuje do „czyszczenia” (tj. zabicia) procesów związanych z danym terminalem. Takie zachowanie jest w znacznej mierze reliktem z czasów terminali kablowych i połączeń modemowych, stąd nazwa HUP (od ang. hang up, rozłączyć się). W powłokach z rodziny C ( tcsh i inne) procesy działające w tle są zwykle odporne na sygnały HUP, dzięki czemu mogą działać nawet po wylogowaniu użytkownika. Użytkownicy powłok w stylu Bourne’a (ksh, bash itd.) mogą naśladować takie zachowanie za pomocą polecenia nohup.
 Sygnał QUIT jest podobny do TERM, z tą różnicą, że gdy nie zostanie przechwycony, jego domyślnym działaniem jest utworzenie zrzutu pamięci. Kilka programów prze chwytuje ten sygnał i interpretuje jego znaczenie inaczej. Sygnały USR1 i USR2 nie mają ustalonego znaczenia. Programy mogą je wykorzystywać w dowolny sposób. Przykładowo serwer WWW Apache interpretuje sygnał HUP jako żąda-
nie natychmiastowego zrestartowania. Sygnał USR1 inicjuje bardziej zgrabne przejście, które zezwala na zakończenie konwersacji z istniejącym klientem.

ZOSTAW ODPOWIEDŹ

Please enter your comment!
Please enter your name here