fork(2)                       System Calls Manual                      fork(2)

NAZWA
       fork - tworzy proces potomny

BIBLIOTEKA
       Standardowa biblioteka C (libc, -lc)

SKLADNIA
       #include <unistd.h>

       pid_t fork(void);

OPIS
       fork() tworzy nowy proces, duplikujac proces wywolujacy. Nowy proces
       jest nazywany procesem potomnym (lub dzieckiem). Proces wywolujacy jest
       nazywany procesem macierzystym (lub rodzicem).

       Proces potomny i proces macierzysty dzialaja w oddzielnych rejonach
       pamieci. W momencie wykonania fork() oba rejony pamieci maja taka sama
       zawartosc. Zapisy do pamieci, przypisywania (mmap(2)) i odmapowywania
       (munmap(2)) pliku wykonane wobec jednego z procesow nie maja wplywu na
       drugi.

       Proces potomny jest dokladna kopia procesu macierzystego z wylaczeniem
       nastepujacych punktow:

       o  Proces potomny ma swoj unikatowy identyfikator procesu i nie pasuje
          ono do identyfikatora zadnej istniejacej sesji lub grupy
          (setpgid(2)) procesu.

       o  Identyfikator procesu macierzystego dla procesu potomnego jest taki
          sam jak identyfikator procesu macierzystego.

       o  Proces potomny nie dziedziczy blokad pamieci swojego procesu
          macierzystego (mlock(2), mlockall(2)).

       o  Uzycie zasobow procesu (getrusage(2)) i liczniki czasu procesora
          (times(2)) sa resetowane do zera dla procesu potomnego.

       o  Zestaw oczekujacych sygnalow dla procesu potomnego jest poczatkowo
          pusty (sigpending(2)).

       o  Proces potomny nie dziedziczy dostosowan semaforow od procesu
          macierzystego (semop(2)).

       o  Proces potomny nie dziedziczy blokad rekordow zwiazanych z procesem
          od swojego procesu macierzystego (fcntl(2)) (z drugiej strony
          dziedziczy blokady opisu otwartego pliku (OFD) fcntl(2) oraz blokady
          flock(2) od swojego procesu macierzystego).

       o  Proces potomny nie dziedziczy czasomierzy od swojego procesu
          macierzystego (setitimer(2), alarm(2), timer_create(2)).

       o  Proces potomny nie dziedziczy zaleglych, asynchronicznych operacji
          wejscia/wyjscia od procesu macierzystego (aio_read(3),
          aio_write(3)), ani nie dziedziczy zadnego kontekstu asynchronicznego
          wejscia/wyjscia od procesu macierzystego (zob. io_setup(2)).

       Atrybuty procesu w powyzszej liscie sa okreslone w normie POSIX.1.
       Proces macierzysty i potomny beda sie roznic rowniez w odniesieniu do
       nastepujacych, typowo linuksowych atrybutow procesu:

       o  Proces potomny nie odziedziczy notyfikacji o zmianie katalogu
          (dnotify) od swojego rodzica (wiecej informacji w opisie F_NOTIFY w
          podreczniku fcntl(2)).

       o  Ustawienie PR_SET_PDEATHSIG prctl(2) jest resetowane, dzieki czemu
          proces potomny nie otrzyma sygnalu, gdy jego proces macierzysty
          ulegnie zakonczeniu.

       o  Domyslna wartosc luzu czasomierza jest ustawiana na aktualna wartosc
          luzu czasomierza procesu macierzystego. Wiecej informacji w opisie
          PR_SET_TIMERSLACK w podreczniku prctl(2).

       o  Przypisania pamieci oznaczone znacznikiem MADV_DONTFORK madvise(2),
          nie sa dziedziczone poprzez fork().

       o  Pamiec w przedzialach adresowych oznaczonych znacznikiem
          MADV_WIPEONFORK madvise(2) jest zerowana dla procesu potomnego, po
          wykonaniu fork() (ustawienie MADV_WIPEONFORK nie ulega zmianie dla
          tych przedzialow adresowych, dla procesu potomnego).

       o  Sygnalem przerwania procesu potomnego jest zawsze SIGCHLD (zob.
          clone(2)).

       o  Bity uprawnien dostepu do portu ustawione za pomoca ioperm(2) nie sa
          dziedziczone przez proces potomny; musi on sam wlaczyc wszystkie
          wymagane bity przy uzyciu ioperm(2).

       Dalsze uwagi:

       o  Proces potomny jest tworzony jednym watkiem -- tym ktory wywolal
          fork(). Cala wirtualna przestrzen adresowa jest replikowana dla
          procesu potomnego; obejmuje to zatrzaski (muteksy), zmienne
          warunkowe i inne obiekty pthread; podrecznik pthread_atfork(3) moze
          okazac sie przydatny w radzeniu sobie z problemami, jakie to moze
          spowodowac.

       o  W programie wielowatkowym, po fork() proces potomny moze bezpiecznie
          wykonac jedynie funkcje ktore sa async-signal-safe (zob.
          signal-safety(7)) az do momentu, gdy nie wywola execve(2).

       o  Proces potomny dziedziczy kopie zestawu deskryptorow otwartego
          pliku. Kazdy deskryptor pliku procesu potomnego odnosi sie do tego
          samego opisu otwartego pliku (OFD, zob. open(2)) jako deskryptor
          odpowiadajacego pliku swego procesu macierzystego. Oznacza to, ze
          dwa deskryptory pliku dziela znaczniki statusu otwartego pliku,
          przesuniecia pliku oraz atrybuty wejscie/wyjscia zasilane sygnalami
          (zob. opis F_SETOWN i F_SETSIG w fcntl(2)).

       o  Proces potomny dziedziczy zestaw deskryptorow otwartej kolejki
          komunikatow procesu macierzystego (zob. mq_overview(7)). Kazdy
          deskryptor w procesie potomnym odnosi sie do tego samego opisu
          kolejki otwartego komunikatu, jak odpowiadajacy deskryptor pliku
          procesu macierzystego. Oznacza to, ze dwa deskryptory pliku dziela
          te same znaczniki (mq_flags).

       o  Proces potomny kopiuje zestaw strumieni otwartego katalogu procesu
          macierzystego (zob. opendir(3)).  POSIX.1 wskazuje, ze odpowiadajace
          strumienie katalogow procesu macierzystego i potomnego moga dzielic
          pozycjonowanie strumienia katalogu, w Linuksie/glibc tak sie nie
          dzieje.

WARTOSC ZWRACANA
       Po pomyslnym zakonczeniu, w procesie macierzystym zwracany jest PID
       procesu potomnego, a w procesie potomnym zwracane jest 0. Po bledzie
       zwracane jest -1 do procesu macierzystego, nie jest tworzony procesie
       potomny i odpowiednio ustawiane jest errno wskazujac blad.

BLEDY
       EAGAIN Napotkano nalozony systemowo limit liczby watkow. Wystepuje
              wiele limitow, ktore moga wyzwolic ten blad:

              o  osiagnieto miekki limit zasobow RLIMIT_NPROC (ustawiany za
                 pomoca setrlimit(2)), ktory ogranicza liczbe procesow i
                 watkow dla rzeczywistego identyfikatora uzytkownika;

              o  osiagnieto systemowy limit jadra na liczbe procesow i watkow
                 /proc/sys/kernel/threads-max (zob. proc(5));

              o  osiagnieto maksymalna liczbe identyfikatorow procesow
                 /proc/sys/kernel/pid_max (zob. proc(5)); albo

              o  osiagnieto limit identyfikatorow procesow (pids.max) nalozony
                 przez kontroler cgroup ,,liczba procesow" (PID-ow).

       EAGAIN Wywolanie dziala wedlug zasad planisty SCHED_DEADLINE i nie
              posiada znacznika zresetuj-przy-rozwidleniu. Zob. sched(7).

       ENOMEM fork() nie potrafil zaalokowac niezbednych struktur jadra z
              powodu niedostatecznej ilosci pamieci.

       ENOMEM Probowano utworzyc proces potomny w przestrzeni nazw PID, ktorej
              proces ,,init" ulegl zakonczeniu. Zob. pid_namespaces(7).

       ENOSYS fork() nie jest obslugiwane na tej platformie (np. sprzet bez
              jednostki Memory-Management Unit).

       ERESTARTNOINTR (od Linuksa 2.6.17)
              Wywolanie systemowe przerwano sygnalem i zostanie ono
              przeladowane (widac to tylko przy sledzeniu).

WERSJE
   Roznice biblioteki C/jadra
       Od glibc 2.3.3, zamiast przywolywac wywolanie systemowe jadra fork(),
       opakowanie fork() z biblioteki glibc, dostepne jako czesc implementacji
       watkowania NPTL, przywoluje clone(2) ze znacznikami, zapewniajacymi
       taki sam efekt, jak tradycyjne wywolanie systemowe (wywolanie fork()
       jest rownowazne wywolaniu clone(2) przy okresleniu flags jako wylacznie
       SIGCHLD). Opakowanie z biblioteki glibc przywoluje procedury obslugi
       rozwidlania, ktore ustanowiono za pomoca pthread_atfork(3).

STANDARDY
       POSIX.1-2008.

HISTORIA
       POSIX.1-2001, SVr4, 4.3BSD.

UWAGI
       Pod Linuksem fork() jest zaimplementowane za pomoca kopiowania stron
       pamieci przy zapisie, wiec jedynymi mankamentami sa czas i pamiec
       wymagane do powielenia tablic stron rodzica i utworzenia unikalnej
       struktury zadania dla potomka.

PRZYKLADY
       Zob. pipe(2) i wait(2), aby obejrzec wiecej przykladow.

       #include <signal.h>
       #include <stdint.h>
       #include <stdio.h>
       #include <stdlib.h>
       #include <sys/types.h>
       #include <unistd.h>

       int
       main(void)
       {
           pid_t pid;

           if (signal(SIGCHLD, SIG_IGN) == SIG_ERR) {
               perror("signal");
               exit(EXIT_FAILURE);
           }
           pid = fork();
           switch (pid) {
           case -1:
               perror("fork");
               exit(EXIT_FAILURE);
           case 0:
               puts("Child exiting.");
               fflush(stdout);
               _exit(EXIT_SUCCESS);
           default:
               printf("Child is PID %jd\n", (intmax_t) pid);
               puts("Parent exiting.");
               exit(EXIT_SUCCESS);
           }
       }

ZOBACZ TAKZE
       clone(2), execve(2), exit(2), _exit(2), setrlimit(2), unshare(2),
       vfork(2), wait(2), daemon(3), pthread_atfork(3), capabilities(7),
       credentials(7)

TLUMACZENIE
       Autorami polskiego tlumaczenia niniejszej strony podrecznika sa:
       Przemek Borys <pborys@dione.ids.pl>, Andrzej Krzysztofowicz
       <ankry@green.mf.pg.gda.pl> i Michal Kulach <michal.kulach@gmail.com>

       Niniejsze tlumaczenie jest wolna dokumentacja. Blizsze informacje o
       warunkach licencji mozna uzyskac zapoznajac sie z GNU General Public
       License w wersji 3 <https://www.gnu.org/licenses/gpl-3.0.html> lub
       nowszej. Nie przyjmuje sie ZADNEJ ODPOWIEDZIALNOSCI.

       Bledy w tlumaczeniu strony podrecznika prosimy zglaszac na adres listy
       dyskusyjnej <manpages-pl-list@lists.sourceforge.net>.

Linux man-pages 6.12          14 stycznia 2025 r.                      fork(2)