Provided by: manpages-de-dev_2.5-1_all bug

BEZEICHNUNG

       clone, __clone2 - erzeugt einen Kindprozess

ÜBERSICHT

       /* Prototyp für die Glibc-Wrapper-Funktion */

       #define _GNU_SOURCE
       #include <sched.h>

       int clone(int (*fn)(void *), void *child_stack,
                 int flags, void *arg, 
                 /* pid_t *ptid, void *newtls, pid_t *ctid */ );

       /* Für den Prototyp des den rohen Systemaufrufs siehe ANMERKUNGEN */

BESCHREIBUNG

       clone() erzeugt auf eine ähnliche Weise wie fork(2) einen neuen Prozess.

       Diese  Seite  beschreibt  sowohl  die  clone()-Wrapper-Funktion  von  Glibc  als  auch den
       darunterliegenden  Systemaufruf,  auf  dem  sie  basiert.  Der   Haupttext   erklärt   die
       Wrapper-Funktion.  Die  Unterschiede zum rohen Systemaufruf werden gegen Ende dieser Seite
       erläutert.

       Im Gegensatz zu fork(2) erlaubt clone(), dass der Kindprozess Teile seines  Kontextes  mit
       dem  aufrufenden  Prozess  teilt.  Dazu  zählen  der virtuelle Adressraum, die Tabelle der
       Dateideskriptoren und die Tabelle der Signal-Handler.  (Beachten  Sie,  dass  »aufrufender
       Prozess«  auf dieser Handbuchseite »Elternprozess« entspricht. Aber lesen Sie im Folgenden
       die Beschreibung von CLONE_PARENT.)

       clone() wird  benutzt,  um  Threads  zu  implementieren:  mehrere  Steuerflüsse  in  einem
       Programm, die gleichzeitig in einem gemeinsamen Speicherbereich ausgeführt werden.

       Wird  mit  clone()  ein  Kindprozess  erzeugt,  beginnt es die Ausführung durch Aufruf der
       Funktion, auf die das Argument fn zeigt. (Dies ist ein  Unterschied  zu  fork(2),  wo  die
       Ausführung  im Kindprozess vom Punkt des fork(2)-Aufrufs fortfährt.) Das Argument arg wird
       als Argument der Funktion fn übergeben.

       Kehrt die Funktion fn(arg) zurück, so beendet sich der Kindprozess. Der Ganzzahlwert,  der
       von fn zurückgeliefert wird, entspricht dem Exit-Status des Kindprozesses. Der Kindprozess
       kann auch durch den expliziten Aufruf von exit(2) oder durch  den  Empfang  eines  fatalen
       Signals beendet werden.

       Das  Argument  child_stack  bestimmt  den  Ort  des  Stapelspeichers,  der vom Kindprozess
       verwendet wird. Da der aufrufende und der Kindprozess sich Speicherbereiche teilen können,
       kann  der  Kindprozess  nicht  auf  dem  selben  Stapelspeicher wie der aufrufende Prozess
       laufen. Der aufrufende Prozess muss daher einen Speicherbereich als Stapelspeicher für den
       Kindprozess  bereithalten  und per clone einen Zeiger darauf an den Kindprozess übergeben.
       Der Stapelspeicher wächst (mit Ausnahme der PA-Prozessoren von HP)  auf  allen  von  Linux
       unterstützten  Prozessoren  nach unten, so dass child_stack für gewöhnlich auf die oberste
       Adresse im bereitgehaltenen Speicherbereich zeigt.

       Das niederwertige Byte von flags enthält die Nummer des  Beendigungssignals,  das  an  den
       Elternprozess  gesandt  wird,  wenn  der  Kindprozess endet. Falls dieses Signal als etwas
       anderes als SIGCHLD angegeben wurde, dann muss der Elternprozess die Optionen __WALL  oder
       __WCLONE  angeben,  wenn  er  mit  wait(2)  auf  den Kindprozess wartet. Falls kein Signal
       angegeben wurde, wird dem Elternprozess nicht signalisiert, wenn der Kindprozess endet.

       flags kann darüber hinaus noch  durch  bitweises  »ODER«  mit  keiner  oder  mehreren  der
       folgenden  Konstanten  verknüpft  werden.  Dadurch wird festgelegt, welche Ressourcen sich
       Eltern- und Kindprozess teilen:

       CLONE_CHILD_CLEARTID (seit Linux 2.5.49)
              Die Kind-Thread-ID an der Stelle ctid im Kindspeicher bereinigen (nullen), wenn das
              Kind   existiert  und  beim  Futex  (»fast  userspace  mutual  exclusion«/schneller
              gegenseitiger Ausschluss im Userspace) an  dieser  Adresse  aufwachen  lassen.  Die
              betroffene  Adresse  könnte  durch  den  Systemaufruf  set_tid_address(2)  geändert
              werden. Dies wird von Threading-Bibliotheken benutzt.

       CLONE_CHILD_SETTID (seit Linux 2.5.49)
              Speichert die Kind-Thread-ID an der Stelle ctid im Kindspeicher. Die Speicheraktion
              wird abgeschlossen, bevor clone() die Steuerung an den Benutzerraum zurückgibt.

       CLONE_FILES (since Linux 2.0)
              Ist  CLONE_FILES  gesetzt,  teilen  sich  der  aufrufende  und der Kindprozess ihre
              Dateideskriptor-Tabellen. Jeder Dateideskriptor, der im  aufrufenden  Prozess  oder
              vom Kindprozess erzeugt wird, ist auch im anderen Prozess gültig. Ebenso wirkt sich
              das Schließen eines Dateideskriptors  oder  das  Ändern  der  zugehörigen  Schalter
              (benutzen  der  F_SETFD-Operation  von fcntl(2)) auf den anderen Prozess aus. Falls
              sich ein Prozess eine Dateideskriptor-Tabelle teilt  und  execve(2)  aufruft,  wird
              seine Dateideskriptor-Tabelle dupliziert (nicht länger geteilt).

              Ist CLONE_FILES nicht gesetzt, erbt der Kindprozess zur Ausführungszeit von clone()
              eine Kopie der aktuell geöffneten Dateideskriptoren.  Anschließende  Aktionen,  die
              Dateideskriptoren öffnen oder schließen bzw. deren Schalter ändern, werden entweder
              vom aufrufenden Prozess oder dem Kindprozess durchgeführt und betreffen  nicht  den
              jeweils   anderen   Prozess.   Beachten   Sie  aber,  dass  sich  die  duplizierten
              Dateideskriptoren  im  Kind  auf  die  gleiche  offene  Dateideskription  wie   der
              korrespondierende Dateideskriptor im aufrufenden Prozess bezieht und sich daher den
              Dateiversatz und die Dateistatusschalter mit diesem teilt (siehe open(2)).

       CLONE_FS (seit Linux 2.0)
              Ist  CLONE_FS  gesetzt,  teilen  sich  aufrufender  Prozess  und  Kindprozess  ihre
              Informationen  über  das Dateisystem. Dazu zählen der Ort des Wurzelverzeichnisses,
              das aktuelle Arbeitsverzeichnis und  die  Maske  der  Dateizugriffsrechte  (umask).
              Jeder  Aufruf von chroot(2), chdir(2) oder umask(2), entweder durch den aufrufenden
              Prozess oder den Kindprozess, beeinflusst auch den jeweils anderen Prozess.

              Ist CLONE_FS nicht gesetzt, arbeitet der Kindprozess von clone()  mit  einer  Kopie
              der    Dateisysteminformationen    des   aufrufenden   Prozesses   zur   Zeit   des
              clone()-Aufrufs. Spätere Aufrufe von chroot(2), chdir(2) oder umask(2) beeinflussen
              den anderen Prozess nicht.

       CLONE_IO (seit Linux 2.6.25)
              Ist  CLONE_FS  gesetzt,  teilt  sich  der  neue  Prozess  einen E/A-Kontext mit dem
              aufrufenden Prozess. Falls dieser Schalter nicht gesetzt ist (wie bei fork(2)), hat
              der neue Prozess seinen eigenen E/A-Kontext.

              Der  E/A-Kontext entspricht dem E/A-Gültigkeitsbereich des Platten-Steuerprogramms,
              d.h., welches das E/A-Steuerprogramm  zur  Modellplanung  für  E/As  des  Prozesses
              benutzt.  Falls  sich  Prozesse  den  gleichen  E/A-Kontext  teilen, werden sie vom
              E/A-Steuerprogramm als ein einziger betrachtet. Als Konsequenz  daraus  müssen  sie
              sich   die   gleiche   Plattenzeitzugriffzeit  teilen.  Einige  E/A-Steuerprogramme
              ermöglichen zwei Prozessen, die einen E/A-Kontext teilen, ihren  Plattenzugriff  zu
              verzahnen. Falls mehrere Prozesse E/A im Auftrag des gleichen Prozesses durchführen
              (aio_read(3) zum Beispiel), sollten sie  für  eine  bessere  E/A-Leistung  CLONE_IO
              verwenden.

              Falls  der  Kernel  nicht  mit  der Option CONFIG_BLOCK konfiguriert wurde, bewirkt
              dieser Schalter nichts.

       CLONE_NEWCGROUP (seit Linux 4.6)
              Erstellt den Prozess in einem neuen cgroup-Namensraum. Falls dieser Schalter  nicht
              gesetzt   ist,   dann   wird   (wie  mit  fork(2))  der  Prozess  in  den  gleichen
              cgroup-Namensräumen wie der aufrufende Prozess erstellt. Der Schalter ist  für  die
              Implementierung von Containern gedacht.

              Weitere     Informationen     über     cgroup-Namensräume    finden    Sie    unter
              cgroup_namespaces(7).

              Nur ein privilegierter Prozess (CAP_SYS_ADMIN) kann CLONE_NEWCGROUP angeben.

       CLONE_NEWIPC (seit Linux 2.6.19)
              Ist CLONE_NEWIPC gesetzt, dann wird  der  Prozess  in  einem  neuen  IPC-Namensraum
              erstellt.  Falls  dieser Schalter nicht gesetzt ist, dann wird der Prozess (wie bei
              fork(2)) im gleichen IPC-Namensraum wie der  aufrufende  Prozess  erstellt.  Dieser
              Schalter ist für die Implementierung von Containern gedacht.

              Ein  IPC-Namensraum  stellt eine isolierte Ansicht von System-V-IPC-Objekten (siehe
              svipc(7)) und (seit 2.6.30) POSIX-Nachrichtenwarteschlangen (siehe  mq_overview(7))
              bereit.  Das  gemeinsame Merkmal dieser IPC-Mechanismen ist, dass IPC-Objekte durch
              andere Mechanismen als Dateisystempfadnamen identifiziert werden.

              Objekte, die in  einem  IPC-Namensraum  erstellt  wurden,  sind  für  alle  anderen
              Prozesse  sichtbar,  die  Mitglieder  des Namensraums sind. Die Objekte sind jedoch
              nicht für Prozesse in anderen Namensräumen sichtbar.

              Wenn ein IPC-Namensraum zerstört wird, d.h. wenn der letzte Prozess  im  Namensraum
              beendet wird, werden alle IPC-Objekte im Namensraum automatisch zerstört.

              Nur  ein  privilegierter  Prozess (CAP_SYS_ADMIN) kann CLONE_NEWIPC angeben. Dieser
              Schalter darf nicht zusammen mit CLONE_SYSVSEM angegeben werden.

              Weitere Informationen zu IPC-Namensräumen finden Sie in namespaces(7).

       CLONE_NEWNET (seit Linux 2.6.24)
              (Die Implementierung dieses Schalters wurde erst ungefähr  mit  der  Kernel-Version
              2.6.29 abgeschlossen.)

              Wenn   CLONE_NEWNET   gesetzt   ist,   dann   wird   der  Prozess  in  einem  neuen
              Netzwerk-Namensraum erstellt. Falls dieser Schalter nicht gesetzt  ist,  dann  wird
              der  Prozess  (wie  mit fork(2)) im gleichen Netzwerk-Namensraum wie der aufrufende
              Prozess erstellt. Dieser  Schalter  ist  für  die  Implementierung  von  Containern
              gedacht.

              Ein  Netzwerk-Namensraum stellt eine isolierte Ansicht des Netzwerk-Stapelspeichers
              (Netzwerkgeräteschnittstellen,     IPv4-     und     IPv6-Protokoll-Stapelspeicher,
              IP-Routing-Tabellen,    Firewall-Regeln,   die   Verzeichnisbäume   /proc/net   und
              /sys/class/net, Sockets, etc.) bereit. Ein physisches Netzwerkgerät kann  in  genau
              einem  Netzwerknamensraum  bestehen.  Ein  virtuelles  Netzwerkgerätepaar (veth(4))
              stellt eine einer Pipe ähnliche Abstraktion bereit, die  benutzt  werden  kann,  um
              Tunnel  zwischen Netzwerk-Namensräumen aufzubauen und eine Brücke in ein physisches
              Netzwerkgerät in einem anderen Namensraum zu erstellen.

              Wenn ein Netzwerk-Namensraum freigegeben wird, d.h.  wenn  der  letzte  Prozess  im
              Namensraum  beendet  wird,  werden  seine  physischen  Netzwerkgeräte zurück in den
              ursprünglichen   Namensraum   verschoben   (nicht   zum   Elternprozess).   Weitere
              Informationen zu Netzwerk-Namensräumen finden Sie in namespaces(7).

              Nur ein privilegierter Prozess (CAP_SYS_ADMIN) kann CLONE_NEWNET angeben.

       CLONE_NEWNS (seit Linux 2.4.19)
              Wenn  der  Schalter CLONE_NEWNS gesetzt ist, wird der geklonte Kindprozess in einem
              neuen, eingehängten Namensraum gestartet, der mit einer Kopie des  Namensraums  des
              Elternprozesses initialisiert wurde. Wenn CLONE_NEWNS nicht gesetzt ist, bleibt der
              Kindprozess im gleichen Namensraum wie der Elternprozess.

              Nur ein privilegierter Prozess (einer der die Fähigkeit CAP_SYS_ADMIN hat) kann den
              Schalter  CLONE_NEWNS  angeben.  Es  ist nicht erlaubt, sowohl CLONE_NEWNS als auch
              CLONE_FS im gleichen Aufruf von clone() anzugeben.

              Für weitere Informationen über  Einhängenamensräume  lesen  Sie  namespaces(7)  und
              mount_namespaces(7)

       CLONE_NEWPID (seit Linux 2.6.24)
              Wenn  CLONE_NEWPID gesetzt ist, dann wird der Prozess in einem neuen PID-Namensraum
              erstellt. Falls dieser Schalter nicht gesetzt ist (wie mit fork(2)), dann wird  der
              Prozess  in  dem  gleichen  PID-Namensraum wie der aufrufende Prozess erstellt. Der
              Schalter ist für die Implementierung von Containern gedacht.

              Weitere  Informationen  zu  PID-Namensräumen  finden  Sie  in   namespaces(7)   und
              pid_namespaces(7).

              Nur  ein  privilegierter  Prozess (CAP_SYS_ADMIN) kann CLONE_NEWPID angeben. Dieser
              Schalter darf nicht zusammen mit CLONE_THREAD oder CLONE_PARENT angegeben werden.

       CLONE_NEWUSER
              (Dieser Schalter hatte für clone() erstmals in Linux  2.6.23  eine  Bedeutung,  die
              aktuelle  clone()-Semantik  wurde in Linux 3.5 aufgenommen und die letzten Anteile,
              um  Benutzernamensräume  komplett  nutzbar  zu  bekommen,  wurden  in   Linux   3.8
              aufgenommen.)

              Wenn   CLONE_NEWUSER   gesetzt   ist,   dann   wird  der  Prozess  in  einem  neuen
              Benutzer-Namensraum erstellt. Falls dieser Schalter nicht gesetzt  ist,  dann  wird
              der  Prozess  (wie  mit fork(2)) im gleichen Benutzer-Namensraum wie der aufrufende
              Prozess erstellt.

              Vor Linux 3.8 verlangte die Verwendung von CLONE_NEWUSER, dass der Aufrufende  drei
              Capabilities hatte: CAP_SYS_ADMIN, CAP_SETUID und CAP_SETGID. Seit Linux 3.8 werden
              für die Erstellung eines Benutzernamensraums keine Privilegien benötigt.

              Dieser Schalter kann nicht zusammen mit CLONE_THREAD  oder  CLONE_PARENT  angegeben
              werden.  Aus  Sicherheitsgründen  darf  CLONE_NEWUSER  nicht  zusammen mit CLONE_FS
              angegeben werden.

              Für weitere Informationen über  Benutzernamensräume  lesen  Sie  namespaces(7)  und
              user_namespaces(7).

       CLONE_NEWUTS (seit Linux 2.6.19)
              Falls  CLONE_NEWUTS  gesetzt  ist,  erzeugt der Prozess einen neuen UTS-Namensraum,
              dessen Bezeichner durch Duplizieren  der  Bezeichner  aus  dem  UTS-Namensraum  des
              aufrufenden  Prozesses initialisiert werden. Wenn dieser Schalter nicht gesetzt ist
              (wie mit fork(2)), dann  wird  der  Prozess  im  gleichen  UTS-Namensraum  wie  der
              aufrufende  Prozess  erzeugt.  Dieser  Schalter  ist  für  die  Implementierung von
              Containern gedacht.

              Ein UTS-Namensraum ist eine Zusammenstellung  von  Bezeichnern,  die  von  uname(2)
              zurückgegeben  werden;  von  denen können der Domain-Name und der Rechnername durch
              setdomainname(2) beziehungsweise sethostname(2) geändert werden. Änderungen, die an
              Bezeichnern  in  einem  UTS-Namensraum  vorgenommen  werden,  sind für alle anderen
              Prozesse im gleichen Namensraum sichtbar, nicht  jedoch  für  Prozesse  in  anderen
              UTS-Namensräumen.

              Nur ein privilegierter Prozess (CAP_SYS_ADMIN) kann CLONE_NEWUTS angeben.

              Weitere Informationen zu UTS-Namensräumen finden Sie in namespaces(7).

       CLONE_PARENT (seit Linux 2.3.12)
              Falls CLONE_PARENT gesetzt ist, dann wird der Elternprozess des neuen Kindprozesses
              (wie er von getppid(2) zurückgegeben wird) der gleiche wie der  aufrufende  Prozess
              sein.

              Falls  CLONE_PARENT nicht gesetzt ist (wie bei fork(2)), dann ist der Elternprozess
              des Kindprozesses der aufrufende Prozess.

              Beachten Sie, dass dem Elternprozess, wie er  von  getppid(2)  zurückgegeben  wird,
              signalisiert  wird  wenn der Kindprozess endet. Wenn also CLONE_PARENT gesetzt ist,
              wird dem Elternprozess des aufrufenden Prozesses anstatt  dem  aufrufenden  Prozess
              selbst das Signal gesandt.

       CLONE_PARENT_SETTID (seit Linux 2.5.49)
              Die  Kindprozess-Thread-ID  an der Stelle ptid im Elternspeicher ablegen. (In Linux
              2.5.32-2.5.48 gab es einen Schalter CLONE_SETTID, der das tat.) Die  Speicheraktion
              wird abgeschlossen, bevor clone() die Steuerung an den Benutzerraum zurückgibt.

       CLONE_PID (Linux 2.0 bis 2.5.15)
              Falls  CLONE_PID  gesetzt ist, wird der Kindprozess mit der gleichen Prozess-ID wie
              der aufrufende Prozess erstellt. Dies ist  gut,  um  das  System  zu  hacken,  aber
              andererseits  zu  nicht  viel  mehr  zu gebrauchen. Seit Linux 2.3.21 konnte dieser
              Schalter nur durch den Boot-Prozess  angegeben  werden  (PID  0).  Dieser  Schalter
              verschwand  in  Linux  2.5.16 komplett aus den Kernelquellen. Seitdem ignoriert der
              Kernel dieses Bit, falls es in flags festgelegt ist.

       CLONE_PTRACE (seit Linux 2.2)
              Falls CLONE_PTRACE angegeben ist und der aufrufende  Prozess  verfolgt  wird,  dann
              wird der Kindprozess ebenfalls verfolgt (siehe ptrace(2)).

       CLONE_SETTLS (seit Linux 2.5.32)
              Der TLS (Thread Local Storage)-Deskriptor ist auf newtls gesetzt.

              Die Interpretation von newtls und der resultierende Effekt ist architekturabhängig.
              Auf  X86   ist   newtls   als   ein   struct   user_desc *   interpretiert   (siehe
              set_thread_area(2)).  Auf  X86-64  ist  es  der  neue  für das Basisregister %fs zu
              setzende Wert (siehe das Argument ARCH_SET_FS von arch_prctl(2)). Auf Architekturen
              mit einem dedizierten TLS-Register ist es der neue Wert dieses Registers.

       CLONE_SIGHAND (seit Linux 2.0)
              Ist  CLONE_SIGHAND  gesetzt, teilen sich der aufrufende Prozess und der Kindprozess
              die Tabelle der Signal-Handler. Ruft einer der beiden Prozesse sigaction(2) auf, um
              das Antwortverhalten auf ein Signal zu verändern, so betrifft dies auch den anderen
              Prozess. Jedoch besitzen aufrufender Prozess und Kindprozess nach wie vor getrennte
              Signalmasken  und  getrennte  Listen  der  noch ausstehenden Signale. Daher könnten
              Signale durch Aufruf von sigprocmask(2) für einen Prozess geblockt oder  zugelassen
              werden ohne den anderen Prozess zu beeinflussen.

              Ist  CLONE_SIGHAND  nicht gesetzt, erbt der Kindprozess durch den clone-Aufruf eine
              Kopie des Signal-Handlers vom aufrufenden Prozess. Spätere Aufrufe von sigaction(2)
              durch einen der Prozesse hat dann keine Auswirkung auf den anderen Prozess.

              Seit  Linux  2.6.0-test6  müssen  die  flags  außerdem  CLONE_VM  enthalten,  falls
              CLONE_SIGHAND angegeben wurde.

       CLONE_STOPPED (seit Linux 2.6.0-test2)
              Falls CLONE_STOPPED gesetzt ist, ist der Kindprozess anfangs gestoppt (als  ob  ein
              SIGSTOP-Signal  gesendet  worden  wäre) und muss durch Senden eines SIGCONT-Signals
              wieder aufgenommen werden.

              Dieser Schalter  war  ab  Linux  2.6.25  missbilligt  und  wurde  in  Linux  2.6.38
              vollständig  entfernt. Seitdem ignoriert der Kernel ihn ohne Fehler. Seit Linux 4.6
              wird dasselbe Bit für den Schalter CLONE_NEWCGROUP wiederverwendet.

       CLONE_SYSVSEM (seit Linux 2.5.10)
              Wenn CLONE_SYSVSEM gesetzt ist, dann teilen sich der Kindprozess und der aufrufende
              Prozess   eine   einzige   Liste  von  System-V-Semaphore-Anpassungswerten,  (siehe
              semop(2)). In diesem Fall sammelt die  gemeinsame  Liste  semadj  Werte  über  alle
              Prozesse,  die  die  Liste  gemeinsam  nutzen  und Semaphore-Anpassungen werden nur
              durchgeführt, wenn der letzte Prozess, der die Liste gemeinsam nutzt, sich  beendet
              (oder  mittels  unshare(2)  aufhört,  die Liste mitzunutzen). Falls dieser Schalter
              nicht gesetzt ist, besitzt der Kindprozess eine separate semadj-Liste, die  anfangs
              leer ist.

       CLONE_THREAD (seit Linux 2.4.0-test8)
              Falls  CLONE_THREAD  gesetzt ist, wird der Kindprozess in die gleiche Thread-Gruppe
              wie der aufrufende Prozess platziert. Um den Rest der Diskussion  von  CLONE_THREAD
              leserlicher  zu  machen,  wird  der Begriff »Thread« benutzt, um Bezug auf Prozesse
              innerhalb einer Thread-Gruppe zu nehmen.

              Thread-Gruppen waren ein Leistungsmerkmal, das in Linux 2.4 hinzugefügt  wurde,  um
              den  POSIX-Thread-Gedanken  von  einer Thread-Zusammenstellung zu unterstützen, die
              sich eine einzelne PID teilt. Intern  ist  diese  gemeinsame  PID  ein  sogenannter
              Thread-Gruppen-Bezeichner  (TGID)  für  die  Thread-Gruppe.  Seit  Linux  2.4 geben
              Aufrufe von getpid(2) die TGID des Aufrufers zurück.

              Die Threads innerhalb einer Gruppe  können  durch  ihre  (systemweit)  einheitliche
              Thread-ID  (TID)  unterschieden  werden.  Die  TID  eines  neuen  Threads  ist  als
              Funktionsergebnis verfügbar, das an den Aufrufenden von clone() zurückgegeben wird.
              Ein Thread kann durch Benutzen von gettid(2) seine eigene TID erhalten.

              Wenn  clone()  ohne  Angabe  von  CLONE_THREAD  aufgerufen  wurde,  dann  wird  der
              resultierende Thread in eine neue Thread-Gruppe platziert, deren TGID der  TID  des
              Threads entspricht. Dieser Thread ist der Führer der neuen Thread-Gruppe.

              Ein neuer mit CLONE_THREAD erzeugter Thread hat den gleichen Elternprozess wie der,
              der clone() aufruft (d.h. wie CLONE_PARENT), so dass  Aufrufe  von  getppid(2)  den
              gleichen  Wert  für  alle  Threads  in  der  Thread-Gruppe  zurückliefern. Wenn ein
              CLONE_THREAD-Thread endet, wird dem Thread, der ihn per clone() erstellt hat, weder
              ein  SIGCHLD-Signal  (oder  ein  anderes Ende-Signal) gesandt, noch kann der Status
              eines solchen Threads per wait(2) abgefragt werden. (Der Thread wird als  losgelöst
              bezeichnet.)

              Nachdem  alle  Threads  in einer Thread-Gruppe beendet sind, wird dem Elternprozess
              ein SIGCHLD-Signal (oder ein anderes Ende-Signal) gesandt.

              Falls einige der Threads in einer Thread-Gruppe  ein  execve(2)  durchführen,  dann
              werden  alle  Threads außer dem Thread-Führer beendet und das neue Programm wird im
              Thread-Gruppenführer ausgeführt.

              Falls einer der Threads  in  einer  Thread-Gruppe  per  fork(2)  einen  Kindprozess
              erzeugt,  dann  kann  jeder  Thread  in  der  Gruppe wait(2) für diesen Kindprozess
              ausführen.

              Seit Linux 2.5.35 müssen die flags auch CLONE_SIGHAND enthalten, wenn  CLONE_THREAD
              angegeben  wurde. Beachten Sie auch, dass seit Linux 2.6.0-test6 CLONE_SIGHAND auch
              CLONE_VM enthalten muss.

              Signale können an eine Thread-Gruppe als Ganzes geschickt werden (d.h. einer  TGID)
              unter  Benutzung  von  kill(2)  oder an einen bestimmten Thread unter Benutzung von
              tgkill(2).

              Signalanordnungen und Aktionen  sind  prozessweit:  Falls  ein  nicht  abgefangenes
              Signal  an  den  Thread  geschickt  wird,  dann  wird  es  alle  Mitglieder  in der
              Thread-Gruppe beeinflussen (beenden, stoppen, fortfahren, darin ignoriert werden).

              Jeder Thread hat seine eigene Signalmaske, wie sie von sigprocmask(2) gesetzt wird,
              Signale  können  aber  entweder  für  den  ganzen  Prozess  anstehen (d.h. an jedes
              Mitglied der Thread-Gruppe zu liefern sein), wenn sie mit  kill(2)  gesandt  wurden
              oder  für einen einzelnen Thread, wenn sie mit tgkill(2) gesandt wurden. Ein Aufruf
              von sigpending(2) gibt eine  Signalzusammenstellung  zurück,  die  eine  Verbindung
              ausstehender  Signale  für  den  ganzen  Prozess  und  der Signale ist, die für den
              aufrufenden Prozess anstehen.

              Falls kill(2) benutzt wird, um ein Signal an eine Thread-Gruppe zu senden  und  die
              Thread-Gruppe  einen  Handler für dieses Signal installiert hat, dann dann wird der
              Handler  in  exakt  einem  willkürlich  ausgewählten  Mitglied  der   Thread-Gruppe
              aufrufen, das das Signal nicht blockiert hat. Falls mehrere Threads in einer Gruppe
              darauf warten das gleiche Signal per sigwaitinfo(2) zu akzeptieren, wird der Kernel
              einen  dieser  Threads  willkürlich auswählen, um das per kill(2) gesandt Signal zu
              empfangen.

       CLONE_UNTRACED (seit Linux 2.5.46)
              Falls CLONE_UNTRACED angegeben ist, kann ein verfolgender Prozess kein CLONE_PTRACE
              auf diesem Kindprozess erzwingen.

       CLONE_VFORK (seit Linux 2.2)
              Falls  CLONE_VFORK  gesetzt  ist,  wird  die  Ausführung  des aufrufenden Prozesses
              aufgeschoben bis der Kindprozess seine virtuellen Speicherressourcen durch Aufrufen
              von execve(2) oder _exit(2) (wie bei vfork(2)) freigibt.

              Falls CLONE_VFORK nicht gesetzt ist, dann werden sowohl der aufrufende Prozess, als
              auch der Kindprozess nach dem Aufruf planbar und eine Anwendung sollte  sich  nicht
              darauf verlassen, dass die Ausführung in einer speziellen Reihenfolge erfolgt.

       CLONE_VM (seit Linux 2.0)
              Ist  CLONE_VM  gesetzt,  laufen  aufrufender  Prozess  und  Kindprozess  im  selben
              Speicherbereich. Insbesondere sind Schreibzugriffe des aufrufenden  Prozesses  oder
              des  Kindprozesses  in  den  gemeinsamen  Speicher  auch  vom  anderen  Prozess aus
              sichtbar. Zudem beeinflusst jede Veränderung der Speicher-Mappings mit mmap(2) oder
              munmap(2)  durch  den  Kindprozess  oder  den  aufrufenden Prozess auch den jeweils
              anderen Prozess.

              Ist  CLONE_VM  nicht  gesetzt,  erhält  der  Kindprozess  eine  eigene  Kopie   des
              Speicherbereichs  des aufrufenden Prozesses zur Zeit des clone()-Aufrufs. Führt ein
              Prozess Schreibzugriffe auf den Speicher oder Änderungen  am  Dateispeicher-Mapping
              aus, beeinflussen diese Operationen nicht den jeweils anderen, wie bei fork(2).

ANMERKUNGEN

       Beachten  Sie,  dass  die Glibc-Wrapperfunktion clone() einige Änderungen am Speicher, auf
       den  child_stack  zeigt,  vornimmt  (Änderungen,  um  den  Stack  korrekt  für  das   Kind
       einzurichten),  bevor  der  Systemaufruf  clone()  ausgelöst  wird. Verwenden Sie daher in
       Fällen, in denen clone() zur rekursiven Erstellung von Kindern verwandt  wird,  nicht  den
       Puffer, der für den Stack der Eltern eingesetzt wird, als Stack der Kinder.

   Unterschiede C-Bibliothek/Kernel
       Der  rohe  sys_clone-Systemaufruf  entspricht  eher  fork(2), da er mit der Ausführung des
       Kindprozesses am Zeitpunkt des Aufrufs fortfährt. Von daher werden die  Argumente  fn  und
       arg der clone()-Wrapper-Funktion weggelassen.

       Ein  weiterer  Unterschied  für  den  rohen  Systemaufruf  clone() besteht darin, dass das
       Argument child_stack Null sein könnte, so dass in diesem Fall das Kind eine  Dublette  des
       Stacks  des  Elternprozesses  verwendet. (»Copy-on-write«-Semantik stellt sicher, dass der
       Kindprozess getrennte Kopien des Stapelspeichers erhält, wenn einer  der  beiden  Prozesse
       den  Stapelspeicher  verändert.) In diesem Fall sollte die Option CLONE_VM nicht angegeben
       werden, damit es korrekt  funktioniert.  (Falls  das  Kind  sich  aufgrund  des  Schalters
       CLONE_VM    mit    dem    Elternprozess    den    Speicher   teilt,   dann   tritt   keine
       copy-on-write-Duplizierung auf und wahrscheinlich tritt Chaos ein.

       Die Reihenfolge der Argumente unterscheidet sich auch im rohen Systemaufruf  und  es  gibt
       über  die  Architekturen  hinweg  Variationen in den Argumenten, wie dies in den folgenden
       Absätzen dargestellt wird.

       Die rohe Schnittstelle für Systemaufrufe auf  x86-64  und  einigen  anderen  Architekturen
       (darunter Sh, Tile und Alpha) sieht ungefähr so aus:

           long clone(unsigned long flags, void *child_stack,
                      int *ptid, int *ctid,
                      unsigned long newtls);

       Auf  x86-32  und  mehreren  anderen  häufigen  Architekturen (darunter Score, ARM, ARM 64,
       PA-RISC, Arc, Power PC, Xtensa und MIPS) ist die Reihenfolge der  letzten  zwei  Argumente
       gedreht:

           long clone(unsigned long flags, void *child_stack,
                     int *ptid, unsigned long newtls,
                     int *ctid);

       Auf der Cris- und S30-Architektur ist die Reihenfolge der ersten zwei Argumente gedreht:

           long clone(void *child_stack, unsigned long flags,
                      int *ptid, int *ctid,
                      unsigned long newtls);

       Auf der Microblaze-Architektur wird ein zusätzliches Argument übergeben:

           long clone(unsigned long flags, void *child_stack,
                      int stack_size,         /* Größe des Stacks */
                      int *ptid, int *ctid,
                      unsigned long newtls);

   Blackfin, M68k und Sparc
       Die  Konventionen der Argumentübergabe weichen auf Blackfin, M68k und Sparc von der obigen
       Beschreibung ab. Einzelheiten finden Sie in der Kernel- (und Glibc-) Quelle.

   Ia64
       Auf ia64 wird eine andere Schnittstelle benutzt:

       int __clone2(int (*fn)(void *),
                    void *child_stack_base, size_t stack_size,
                    int flags, void *arg, 
                 /* pid_t *ptid, struct user_desc *tls,
                    pid_t *ctid */ );

       Der   oben   gezeigte   Prototyp   ist   für   die   Glibc-Wrapper-Funktion.   Die    rohe
       Systemaufrufschnittstelle  hat  kein  fn- oder arg-Argument und ändert die Reihenfolge der
       Argumente, so dass flags das erste und tls das letzte Argument ist.

       __clone2() arbeitet auf die gleiche Weise wie clone(), außer dass child_stack_base auf die
       niedrigste  Adresse  im  Stapelspeicherbereich  des Kindprozesses zeigt und stack_size die
       Größe des Stapelspeichers angibt, auf die child_stack_base zeigt.

   Linux 2.4 und früher
       Unter Linux 2.4 und früher gab es die Argumente ptid, tls und ctid noch nicht.

RÜCKGABEWERT

       Bei Erfolg wird im ausgeführten Thread des Aufrufenden  die  Thread-ID  des  Kindprozesses
       zurückgegeben.  Im  Fehlerfall  wird  im  Kontext  des  Aufrufenden -1 zurückgegeben, kein
       Kindprozess erzeugt und errno entsprechend gesetzt.

FEHLER

       EAGAIN Es laufen bereits zu viele Prozesse; siehe fork(2).

       EINVAL CLONE_SIGHAND wurde angegeben, aber nicht CLONE_VM. (Seit Linux 2.6.0-test6.)

       EINVAL CLONE_THREAD wurde angegeben, aber nicht CLONE_SIGHAND. (Seit Linux 2.5.35.)

       EINVAL In flags wurden sowohl CLONE_FS als auch CLONE_NEWNS angegeben.

       EINVAL (seit Linux 3.9)
              In flags wurden sowohl CLONE_NEWUSER als auch CLONE_FS angegeben.

       EINVAL In flags wurden sowohl CLONE_NEWIPC als auch CLONE_SYSVSEM angegeben.

       EINVAL Eines (oder beides) von CLONE_NEWPID oder CLONE_NEWUSER und eines (oder beides) von
              CLONE_THREAD oder CLONE_PARENT wurde in flags angegeben.

       EINVAL Wird  von  der Glibc-Wrapper-Funktion clone() zurückgegeben, wenn ein Wert von Null
              für fn oder child_stack angegeben wurde.

       EINVAL In flags wurde CLONE_NEWIPC angegeben,  der  Kernel  wurde  jedoch  nicht  mit  den
              Optionen CONFIG_SYSVIPC und CONFIG_IPC_NS konfiguriert.

       EINVAL In flags wurde CLONE_NEWNET angegeben, der Kernel wurde jedoch nicht mit der Option
              CONFIG_NET_NS konfiguriert.

       EINVAL In flags wurde CLONE_NEWPID angegeben, der Kernel wurde jedoch nicht mit der Option
              CONFIG_PID_NS konfiguriert.

       EINVAL In flags wurde CLONE_NEWUTS angegeben, der Kernel wurde jedoch nicht mit der Option
              CONFIG_UTS konfiguriert.

       EINVAL child_stack  ist  nicht  an  einer  geeigneten   Grenze   für   diese   Architektur
              ausgerichtet.  Beispielsweise  muss  child_stack  auf Aarch64 ein Vielfaches von 16
              sein.

       ENOMEM Es kann nicht ausreichend Speicher  für  eine  Aufgabenstruktur  des  Kindprozesses
              reserviert werden oder um benötigte Teile vom Kontext des Aufrufenden zu kopieren.

       ENOSPC (seit Linux 3.7)
              CLONE_NEWPID wurde in flags angegeben, aber die Begrenzung der geschachtelten Tiefe
              der PID-Namensräume würde überschritten; siehe pid_namespaces(7).

       ENOSPC (seit Linux 4.9; vorher EUSERS)
              CLONE_NEWUSER wurde in flags angegeben und der Aufruf würde dazu führen,  dass  die
              Anzahl   der   geschachtelten   Benutzernamensräume   überschritten   würde.  Siehe
              user_namespaces(7).

              Von Linux 3.11 bis Linux 4.8 war der in diesem Fall diagnostizierte Fehler EUSERS.

       ENOSPC (seit Linux 4.9)
              Einer der Werte in flags legte  die  Erstellung  eines  neuen  Benutzer-Namensraums
              fest,  dadurch  würde  aber  die  in  der  enstprechenden  Datei  in /proc/sys/user
              festgelegte Begrenzung überschritten. Für weitere Details siehe namespaces(7).

       EPERM  CLONE_NEWCGROUP,  CLONE_NEWIPC,  CLONE_NEWNET,   CLONE_NEWNS,   CLONE_NEWPID   oder
              CLONE_NEWUTS  wurde  von einem nicht privilegierten Prozess angegeben (Prozess ohne
              CAP_SYS_ADMIN).

       EPERM  CLONE_PID wurde von einem anderen Prozess als Prozess 0 angegeben.  (Dieser  Fehler
              tritt nur unter Linux 2.5.15 und früheren Versionen auf.)

       EPERM  CLONE_NEWUSER  was  specified  in  flags,  but  either the effective user ID or the
              effective group ID of the caller does not have a mapping in  the  parent  namespace
              (see user_namespaces(7)).

       EPERM (seit Linux 3.9)
              CLONE_NEWUSER   wurde   in   flags  angegeben  und  der  Aufrufende  ist  in  einer
              Chroot-Umgebung  (d.h.  das  Wurzelverzeichnis  des  Aufrufenden  passt  nicht  zum
              Wurzelverzeichnis des Einhängenahmensraums, in dem es liegt).

       ERESTARTNOINTR (seit Linux 2.6.17)
              Ein  Systemaufruf wurde durch ein Signal unterbrochen und wird neu gestartet. (Dies
              wird nur während einer Verfolgung sichtbar sein.)

       EUSERS (Linux 3.11 bis Linux 4.8)
              CLONE_NEWUSER  wurde  in  flags  angegeben  und  die  Anzahl   der   geschachtelten
              Benutzernamensräume  würde  überschritten.  Siehe  die Diskussion von ENOSPC weiter
              oben.

KONFORM ZU

       clone() ist Linux-spezifisch und sollte nicht in portierbaren Programmen benutzt werden.

ANMERKUNGEN

       Der Systemaufruf kcmp(2) kann zum Testen, ob zwei Prozesse sich  verschiedene  Ressourcen,
       wie  die  Dateideskriptortabelle, die Rücksetz-Aktionen der System-V-Semaphoren oder einen
       virtuellen Adressraum, teilen, verwandt werden.

       Handler, die mittels pthread_atfork(3) registriert sind, werden während eines Aufrufs  von
       clone() nicht ausgeführt.

       In  der  Linux 2.4.x-Serie gibt CLONE_THREAD generell dem neuen Prozess nicht den gleichen
       Elternprozess, wie dem aufrufenden Prozess. Für  die  Kernel-Versionen  2.4.7  bis  2.4.18
       implizierte  der  Schalter  CLONE_THREAD  jedoch  den Schalter CLONE_PARENT (wie in Kernel
       2.6.0 und neuer).

       Für eine Weile gab es CLONE_DETACHED (eingeführt in 2.5.32):  Elternprozesse  wollen  kein
       Ende-Signal  des Kindprozesses. In Linux 2.6.2 verschwand die Notwendigkeit, dies zusammen
       mit CLONE_THREAD zu übergeben. Dieser Schalter ist immer noch definiert,  hat  aber  keine
       Auswirkungen.

       Auf  i386-Architekturen  sollte  clone()  nicht  durch vsyscall aufgerufen werden, sondern
       direkt durch int $0x80.

FEHLER

       GNU-C-Bibliotheksversionen 2.3.4 bis einschließlich 2.24 enthielten eine  Wrapper-Funktion
       für  getpid(2),  die  Zwischenspeichern von PIDs vornahm. Dieses Zwischenspeichern beruhte
       auf der Unterstützung in dem  Glibc-Wrapper  von  clone(),  aber  Einschränkungen  in  der
       Implementierung  bedeuteten,  dass  unter  einigen  Umständen  der  Zwischenspeicher nicht
       aktuell  war.  Insbesondere  wenn  ein  Signal  sofort  nach  dem  clone()-Aufruf  an  den
       Kindprozess gesandt wurde, konnte ein Aufruf von getpid(2) in einem Signal-Handler die PID
       des aufrufenden Prozesses (des »Elternprozesses«)  zurückgeben,  falls  der  Clone-Wrapper
       noch  keine  Chance hatte den PID-Zwischenspeicher im Kindprozess zu aktualisieren. (Diese
       Diskussion ignoriert den Fall, dass der Kindprozess mit CLONE_THREAD  erstellt  wurde,  in
       dem  getpid(2)  den  gleichen  Wert  im Kindprozess zurückgeben sollte und im Prozess, der
       clone() aufrief, wie sich der Aufrufende und der Kindprozess in der gleichen Thread-Gruppe
       befinden.  Das  Problem des nicht mehr frischen Zwischenspeichers tritt auch auf, wenn das
       Argument flags CLONE_VM enthält.) Um die Wahrheit zu erfahren, war es  manchmal  notwendig
       gewesen, Code wie den folgenden zu verwenden:

           #include <syscall.h>

           pid_t mypid;

           mypid = syscall(SYS_getpid);

       Aufgrund  des  Problems  mit  dem  nicht  mehr  frischem Zwischenspeicher sowie anderen in
       getpid(2) bemerkten Problemen, wurde  die  Funktionalität  des  PID-Zwischenspeicherns  in
       Glibc 2.25 entfernt.

BEISPIEL

       Das   folgende  Programm  demonstriert  die  Benutzung  von  clone()  zum  Erzeugen  eines
       Kindprozesses, der in einem separaten  UTS-Namensraum  ausgeführt  wird.  Der  Kindprozess
       ändert  in  seinem  UTS-Namensraum  den  Rechnernamen. Dann zeigen sowohl Eltern- als auch
       Kindprozess den Rechnernamen des Systems an, wodurch sichtbar wird, dass  der  Rechnername
       sich  im  UTS-Namensraum  von  Eltern- und Kindprozess unterscheidet. Ein Beispiel für die
       Verwendung dieses Programms finden Sie in setns(2).

   Programmquelltext
       #define _GNU_SOURCE
       #include <sys/wait.h>
       #include <sys/utsname.h>
       #include <sched.h>
       #include <string.h>
       #include <stdio.h>
       #include <stdlib.h>
       #include <unistd.h>

       #define errExit(msg)    do { perror(msg); exit(EXIT_FAILURE); \
                               } while (0)

       static int              /* Startfunktion für geklonten Kindprozess */
       childFunc(void *arg)
       {
           struct utsname uts;

           /* Rechnername im UTS-Namensraum des Kindprozesses ändern */

           if (sethostname(arg, strlen(arg)) == -1)
               errExit("sethostname");

           /* Rechnernamen abfragen und anzeigen */

           if (uname(&uts) == -1)
               errExit("uname");
           printf("uts.nodename im Kindprozess:  %s\n", uts.nodename);

           /* Der Namensraum wird für eine Weile durch Schlafen offen gehalten.
              Dies ermöglicht etwas zu experimentieren –  zum Beispiel
              kann ein weiterer Prozess dem Namensraum beitreten. */

           sleep(200);

           return 0;           /* Kindprozess wird nun beendet */
       }

       #define STACK_SIZE (1024 * 1024)    /* Stapelspeichergröße für geklonten
                                              Kindprozess */

       int
       main(int argc, char *argv[])
       {
           char *stack;                    /* Start des Stapelspeicherpuffers */
           char *stackTop;                 /* Ende des Stapelspeicherpuffers */
           pid_t pid;
           struct utsname uts;

           if (argc < 2) {
               fprintf(stderr, "Aufruf: %s <Kindprozess-Rechnername>\n", argv[0]);
               exit(EXIT_SUCCESS);
           }

           /* Stapelspeicher für Kindprozess reservieren */

           stack = malloc(STACK_SIZE);
           if (stack == NULL)
               errExit("malloc");
           stackTop = stack + STACK_SIZE;  /* Annahme, dass Stapelspeicher nach
                                              unten wächst */

           /* Es wird ein Kindprozess erzeugt, der seinen eigenen Namensraum hat.
              Der Kindprozess beginnt die Ausführung in childFunc() */

           pid = clone(childFunc, stackTop, CLONE_NEWUTS | SIGCHLD, argv[1]);
           if (pid == -1)
               errExit("clone");
           printf("clone() gab %ld zurück\n", (long) pid);

           /* Elternprozess fällt bis hierher durch */

           sleep(1);   /* gibt dem Kindprozess Zeit zum Ändern des Rechnernamens */

           /* Den Rechnernamen im UTS-Namensraum des Elternprozesses anzeigen.
              Dieser wird sich vom Rechnernamen im UTS-Namensraum des Kindprozesses
              unterscheiden. */

           if (uname(&uts) == -1)
               errExit("uname");
           printf("uts.nodename im Elternprozess: %s\n", uts.nodename);

           if (waitpid(pid, NULL, 0) == -1)    /* Warten auf Kindprozess */
               errExit("waitpid");
           printf("Kindprozess wurde beendet\n");

           exit(EXIT_SUCCESS);
       }

SIEHE AUCH

       fork(2), futex(2), getpid(2), gettid(2), kcmp(2), set_thread_area(2),  set_tid_address(2),
       setns(2), tkill(2), unshare(2), wait(2), capabilities(7), namespaces(7), pthreads(7)

KOLOPHON

       Diese  Seite  ist  Teil  der  Veröffentlichung  4.15  des  Projekts  Linux-man-pages. Eine
       Beschreibung des Projekts, Informationen, wie Fehler  gemeldet  werden  können  sowie  die
       aktuelle Version dieser Seite finden sich unter https://www.kernel.org/doc/man-pages/.

ÜBERSETZUNG

       Die  deutsche  Übersetzung dieser Handbuchseite wurde von Daniel Kobras <kobras@linux.de>,
       Chris Leick <c.leick@vollbio.de>, Mario Blättermann <mario.blaettermann@gmail.com>,  Helge
       Kreutzmann <debian@helgefjell.de> und Dr. Tobias Quathamer <toddy@debian.org> erstellt.

       Diese  Übersetzung  ist  Freie  Dokumentation;  lesen  Sie  die GNU General Public License
       Version  3  oder  neuer  bezüglich  der  Copyright-Bedingungen.  Es  wird  KEINE   HAFTUNG
       übernommen.

       Wenn Sie Fehler in der Übersetzung dieser Handbuchseite finden, schicken Sie bitte eine E-
       Mail an <debian-l10n-german@lists.debian.org>.