Provided by: manpages-de-dev_1.4-1_all bug

BEZEICHNUNG

       ptrace - Prozessverfolgung

ÜBERSICHT

       #include <sys/ptrace.h>

       long ptrace(enum __ptrace_request Anfrage, pid_t Pid,
                   void *Adresse, void *Daten);

BESCHREIBUNG

       Der  Systemaufruf ptrace() stellt ein Mittel bereit, wodurch ein Prozess (der »Verfolger«)
       die Ausführung eines anderen Prozesses (des »verfolgten Prozesses«) beobachten und steuern
       kann und seinen Speicher sowie die Register untersuchen und ändern kann. Er wird in erster
       Linie benutzt, um Fehlersuche mittels Haltepunkten zu implementieren und Systemaufrufe  zu
       verfolgen.

       Ein  verfolgter  Prozess  muss  zuerst  an  den  Verfolger  angehängt werden. Anhängen und
       nachfolgende Befehle bestehen pro Thread: In einem Prozess mit mehreren Threads kann jeder
       Thread  individuell an einen (möglicherweise unterschiedlichen) Verfolger angehängt werden
       oder nicht angehängt und folglich nicht  auf  Fehler  untersucht  werden.  Daher  bedeutet
       »verfolgter  Prozess«  immer  »(ein)  Thread«,  niemals  »ein  Prozess (mit möglicherweise
       mehreren Threads)«. Ptrace-Befehle werden immer an  einen  bestimmten  verfolgten  Prozess
       gesandt. Der Aufruf hat folgende Form:

           ptrace(PTRACE_foo, PID, …)

       wobei PID die Thread-Kennung des zugehörigen Linux-Threads ist.

       (Beachten Sie, dass auf dieser Seite ein »Prozess aus mehreren Threads« eine Thread-Gruppe
       bezeichnet, die aus Threads  besteht,  die  mittels  des  clone(2)-Schalters  CLONE_THREAD
       erzeugt wurde.)

       Ein  Prozess  kann  eine  Verfolgung  mittels  fork(2)  starten  und  als  Ergebnis  einen
       Kindprozess erhalten, der PTRACE_TRACEME ausführt, was (üblicherweise) von einem execve(2)
       gefolgt  wird.  Alternativ kann ein Prozess die Verfolgung eines anderen Prozesses mittels
       PTRACE_ATTACH oder PTRACE_SEIZE beginnen.

       Während der verfolgte Prozess verfolgt wird, wird er jedesmal  stoppen,  wenn  ein  Signal
       gesandt  wird, sogar wenn das Signal ignoriert wird. (Eine Ausnahme ist SIGKILL, das seine
       normale Wirkung erzielt.) Der Verfolger wird bei seinem  nächsten  Aufruf  von  waitpid(2)
       (oder  den  zugehörigen  »wait«-Systemaufrufen) benachrichtigt; dies wird einen Statuswert
       zurückgeben, der Informationen enthält, die  den  Grund  angeben,  weshalb  der  verfolgte
       Prozess  stoppte.  Während  der  verfolgte  Prozess  angehalten  ist,  kann  der Verfolger
       verschiedene Ptrace-Anfragen verwenden, um den verfolgten Prozess zu  untersuchen  und  zu
       verändern. Dann veranlasst der Verfolger den verfolgten Prozess fortzufahren und wahlweise
       das versandte Signal zu ignorieren (oder stattdessen sogar ein anderes Signal zu senden).

       Falls die Option PTRACE_O_TRACEEXEC nicht in Kraft ist, werden alle erfolgreichen  Aufrufe
       von  execve(2)  durch den verfolgten Prozess zum Senden eines SIGTRAP-Signals veranlassen,
       um dem Elternprozess die Möglichkeit zu  geben,  die  Kontrolle  zu  erlangen,  bevor  die
       Ausführung des neuen Programms beginnt.

       Wenn  der  Verfolger die Verfolgung beendet hat, kann er veranlassenden, das der verfolgte
       Prozess mit PTRACE_DETACH in einem normal Modus ohne Verfolgung fortfährt.

       Der Wert des Arguments Anfrage legt die Aktion des Systemaufrufs fest:

       PTRACE_TRACEME
              zeigt an, dass dieser Prozess durch seinen Elternprozess verfolgt wird. Ein Prozess
              sollte  diese  Anfrage wahrscheinlich nicht stellen, falls sein Elternprozess nicht
              erwartet, ihn zu verfolgen.(PID, Adresse und Daten werden ignoriert.)

              Since Ubuntu 10.10, PTRACE_ATTACH is not  allowed  against  arbitrary  matching-uid
              processes.  The  traced  "child"  must  be  a descendant of the tracer or must have
              called prctl(2)  using PR_SET_PTRACER, with the pid of the tracer (or  one  of  its
              ancestors). For more details, see /etc/sysctl.d/10-ptrace.conf.

       Die  PTRACE_TRACEME-Anfrage  wird  nur  vom  verfolgten Prozess benutzt; die verbleibenden
       Anfragen werden nur vom verfolgenden Prozess benutzt. In den folgenden Anfragen  gibt  PID
       die  Thread-Kennung  des  verfolgten Prozesses an, der beeinflusst werden soll. Für andere
       Anfragen als  PTRACE_ATTACH,  PTRACE_SEIZE,  PTRACE_INTERRUPT  und  PTRACE_KILL  muss  der
       verfolgte Prozess gestoppt werden.

       PTRACE_PEEKTEXT, PTRACE_PEEKDATA
              liest  ein  »word«  an  der Stelle Adresse im Speicher des verfolgten Prozesses und
              gibt das »word« als Ergebnis des ptrace()-Aufrufs zurück. Linux hat keine separaten
              Adressräume   für  Text  und  Daten,  daher  sind  diese  beiden  Anfragen  derzeit
              gleichwertig. (Das Argument Daten wird ignoriert.)

       PTRACE_PEEKUSER
              Liest ein »word« bei Versatz Adresse im BENUTZERbereich des  verfolgten  Prozesses,
              der  die  Register  und  andere  Informationen  über  den  Prozess  enthält  (siehe
              <sys/user.h>). Das »word« wird als  Ergebnis  des  ptrace()-Aufrufs  zurückgegeben.
              Typischerweise  muss  der  Versatz am »word« ausgerichtet sein, obwohl dies je nach
              Architektur variieren kann. Lesen Sie die ANMERKUNGEN. (Daten wird ignoriert.)

       PTRACE_POKETEXT, PTRACE_POKEDATA
              kopiert das »word« Daten  an  die  Stelle  Adresse  im  Speicher  des  verfolgenden
              Prozesses.  Wie  bei  PTRACE_PEEKTEXT  und PTRACE_PEEKDATA sind die beiden Abfragen
              derzeit gleichwertig.

       PTRACE_POKEUSER
              kopiert das »word« Daten an den Versatz Adresse im BENUTZERbereich  des  verfolgten
              Prozesses. Wie für PTRACE_PEEKUSER muss der Versatz am »word« ausgerichtet sein. Um
              die Integrität  des  Kernels  aufrecht  zu  erhalten,  sind  einige  Änderungen  in
              BENUTZERbereich nicht erlaubt.

       PTRACE_GETREGS, PTRACE_GETFPREGS
              kopiert  die Mehrzweck- beziehungsweise Fließpunktregister des verfolgten Prozesses
              an die Stelle Daten im Verfolger. Lesen Sie <sys/user.h>, um Informationen über das
              Format  dieser  Daten zu erhalten. (Adresse wird ignoriert.) Beachten Sie, dass auf
              SPARC-Systemen die Bedeutung von Daten und Adresse umgekehrt ist; daher wird  Daten
              ignoriert  und  die  Register werden an die Adresse Adresse kopiert. PTRACE_GETREGS
              und PTRACE_GETFPREGS sind nicht auf allen Architekturen verfügbar.

       PTRACE_GETREGSET (seit Linux 2.6.34)
              liest die Register  des  verfolgten  Prozesses.  Adresse  gibt  auf  eine  von  der
              Architektur  unabhängige  Weise  den Typ des Registers an, das gelesen werden soll.
              NT_PRSTATUS   (mit   numerischem   Wert   1)   führt   normalerweise   dazu,   dass
              Allzweckregister  gelesen  werden.  Falls die CPU zum Beispiel Fließkomma- und/oder
              Vektorregister hat, können sie durch  Setzen  von  Adresse  auf  die  entsprechende
              Konstante  NT_foo  ermittelt  werden.  Daten  zeigt auf einen struct iovec, der den
              Speicherort und die Länge des Zielpuffers beschreibt. Bei der Rückkehr  ändert  der
              Kernel iov.len, um die tatsächliche Anzahl zurückgegebener Byte anzuzeigen.

       PTRACE_SETREGS, PTRACE_SETFPREGS
              verändert   die   Mehrzweck-   beziehungsweise  Fließpunktregister  des  verfolgten
              Prozesses von der Adresse Daten im Verfolger. Wie für PTRACE_POKEUSER können einige
              Änderungen  am  Mehrzweckregister verboten sein. (Adresse wird ignoriert.) Beachten
              Sie, dass auf SPARC-Systemen die Bedeutung von Daten  und  Adresse  umgekehrt  ist;
              daher wird Daten ignoriert und die Register werden von der Adresse Adresse kopiert.
              PTRACE_SETREGS und PTRACE_SETFPREGS sind nicht auf allen Architekturen verfügbar.

       PTRACE_SETREGSET (seit Linux 2.6.34)
              verändert die Register des verfolgten Prozesses.  Die  Bedeutung  von  Adresse  und
              Daten ist analog zu PTRACE_GETREGSET.

       PTRACE_GETSIGINFO (seit Linux 2.3.99-pre6)
              ruft  Informationen  über  das  Signal  ab, das den Stopp verursachte. Kopiert eine
              siginfo_t-Struktur (siehe sigaction(2)) vom verfolgten Prozess an die Stelle  Daten
              im Verfolger. (Adresse wird ignoriert.)

       PTRACE_SETSIGINFO (seit Linux 2.3.99-pre6)
              setzt  Signalinformationen:  kopiert  eine siginfo_t-Struktur von der Adresse Daten
              vom verfolgenden zum verfolgten Prozess.  Dies  wird  nur  Signale  betreffen,  die
              normalerweise  an  den  verfolgten  Prozess  zugestellt  würden  und  vom Verfolger
              abgefangen  wurden.  Es  könnte  schwierig  werden,  diese  normalen  Signale   von
              künstlichen  Signalen  zu  unterscheiden, die von ptrace() selbst generiert wurden.
              (Adresse wird ignoriert.)

       PTRACE_SETOPTIONS (seit Linux 2.4.6; siehe FEHLER für Vorsichtsmaßnahmen)
              setzt Ptrace-Optionen von Daten. (Adresse wird ignoriert.) Daten wird  als  Bit  in
              der  Maske  der  Optionen interpretiert, die durch die folgenden Schalter angegeben
              wird:

              PTRACE_O_EXITKILL (seit Linux 3.8)
                     falls  ein  verfolgender  Prozess  diesen  Schalter  setzt,  wird  an  jeden
                     verfolgten  Prozess  ein  SIGKILL-Signal  geschickt,  falls  der verfolgende
                     Prozess beendet wird. Diese Option ist für diejenigen nützlich,  die  Ptrace
                     einsperren  und  sicherstellen  wollen,  dass  der verfolgte Prozess nie der
                     Steuerung des verfolgenden Prozesses entkommt.

              PTRACE_O_TRACECLONE (seit Linux 2.5.46)
                     Stop the tracee at the next clone(2)  and automatically  start  tracing  the
                     newly  cloned process, which will start with a SIGSTOP, or PTRACE_EVENT_STOP
                     if PTRACE_SEIZE was used. A waitpid(2)  by the tracer will return  a  status
                     value such that

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_CLONE<<8))

                     Die PID des neuen Prozesses kann mit PTRACE_GETEVENTMSG abgefragt werden.

                     Diese Option kann nicht in allen Fällen clone(2)-Aufrufe abfangen. Falls der
                     verfolgte Prozess  clone(2)  mit  dem  Schalter  CLONE_VFORK  aufruft,  wird
                     stattdessen  PTRACE_EVENT_VFORK  geschickt, wenn PTRACE_O_TRACEVFORK gesetzt
                     ist;  andernfalls  wird  PTRACE_EVENT_FORK  geschickt,  wenn  der  verfolgte
                     Prozess  clone(2) mit dem auf SIGCHLD gesetzten Beendigungssignal aufgerufen
                     wird, falls PTRACE_O_TRACEFORK gesetzt ist.

              PTRACE_O_TRACEEXEC (seit Linux 2.5.46)
                     stoppt den verfolgten Prozess beim nächsten execve(2). Ein waitpid(2)  durch
                     den Verfolger wird einen Statuswert wie diesen zurückgeben:

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_EXEC<<8))

                     Falls  der ausführende Thread kein führender Thread der Gruppe ist, wird die
                     Thread-Kennung vor dem Stopp auf  die  Kennung  des  führenden  Threads  der
                     Gruppe  zurückgesetzt.  Seit Linux 3.0 kann die vorherige Thread-Kennung mit
                     PTRACE_GETEVENTMSG abgefragt werden.

              PTRACE_O_TRACEEXIT (seit Linux 2.5.60)
                     stoppt den  verfolgten  Prozess  beim  Beenden.  Ein  waitpid(2)  durch  den
                     Verfolger wird einen Statuswert wie diesen zurückgeben:

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_EXIT<<8))

                     Der   Exit-Status  des  verfolgten  Prozesses  kann  mit  PTRACE_GETEVENTMSG
                     abgefragt werden.

                     Der verfolgte Prozess wird frühzeitig während des  Beendens  gestoppt,  wenn
                     die Register noch verfügbar sind, was es dem Verfolger ermöglicht, zu sehen,
                     wo das Beenden veranlasst wurde,  wohingegen  die  normale  Benachrichtigung
                     über   die   Beendigung   geschickt  wird,  wenn  der  Prozess  das  Beenden
                     abgeschlossen hat. Auch wenn der Kontext verfügbar ist, kann  der  Verfolger
                     das Beenden an diesem Punkt nicht mehr verhindern.

              PTRACE_O_TRACEFORK (seit Linux 2.5.46)
                     Stop  the  tracee  at  the next fork(2)  and automatically start tracing the
                     newly forked process, which will start with a SIGSTOP, or  PTRACE_EVENT_STOP
                     if  PTRACE_SEIZE  was used. A waitpid(2)  by the tracer will return a status
                     value such that

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_FORK<<8))

                     Die PID des neuen Prozesses kann mit PTRACE_GETEVENTMSG abgefragt werden.

              PTRACE_O_TRACESYSGOOD (seit Linux 2.4.6)
                     Wenn Systemaufrufe abgefangen werden, wird Bit 7 in der Signalnummer gesetzt
                     (d.h.  SIGTRAP  |  0x80  geschickt).  Dies erleichtert es dem Verfolger, den
                     Unterschied zwischen normalen, abgefangenen Signalen und  denen,  die  durch
                     einen  Systemaufruf  verursacht  wurden, mitzuteilen. (PTRACE_O_TRACESYSGOOD
                     funktioniert möglicherweise nicht auf allen Architekturen.)

              PTRACE_O_TRACEVFORK (seit Linux 2.5.46)
                     Stop the tracee at the next vfork(2)  and automatically  start  tracing  the
                     newly vforked process, which will start with a SIGSTOP, or PTRACE_EVENT_STOP
                     if PTRACE_SEIZE was used. A waitpid(2)  by the tracer will return  a  status
                     value such that

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_VFORK<<8))

                     Die PID des neuen Prozesses kann mit PTRACE_GETEVENTMSG abgefragt werden.

              PTRACE_O_TRACEVFORKDONE (seit Linux 2.5.60)
                     stoppt  den  verfolgten  Prozess  bei  Vollendung des nächsten vfork(2). Ein
                     waitpid(2) durch den Verfolger wird einen Statuswert wie diesen zurückgeben:

                       status>>8 == (SIGTRAP | (PTRACE_EVENT_VFORK_DONE<<8))

                     Die PID des neuen Prozesses kann (seit Linux 2.6.18) abgefragt werden mit

       PTRACE_GETEVENTMSG (seit Linux 2.5.46)
              eine Nachricht (als unsigned long) über das Ptrace-Ereignis abfragen,  das  einfach
              so   auftrat   und   es   an   die  Adresse  Daten  im  Verfolger  platzieren.  Für
              PTRACE_EVENT_EXIT  ist  dies  der  Exit-Status  des   verfolgten   Prozesses.   Für
              PTRACE_EVENT_FORK,  PTRACE_EVENT_VFORK  und PTRACE_EVENT_CLONE ist dies die PID des
              neuen Prozesses. (Adresse wird ignoriert.)

       PTRACE_CONT
              startet den gestoppten, verfolgten Prozess erneut. Falls Daten nicht Null ist, wird
              es  als  Nummer  des Signals interpretiert, das an den verfolgten Prozess geschickt
              wird; andernfalls wird kein  Signal  geschickt.  Dadurch  kann  der  Verfolger  zum
              Beispiel  steuern,  ob  ein  Signal  an  den verfolgten Prozess geschickt wird oder
              nicht. (Adresse wird ignoriert.)

       PTRACE_SYSCALL, PTRACE_SINGLESTEP
              startet den gestoppten, verfolgten Prozess wie für  PTRACE_CONT,  arrangiert  aber,
              dass   der  verfolgte  Prozess  beim  nächsten  Eintritt  oder  einem  Systemaufruf
              beziehungsweise nach der Ausführung einer einzelnen Anweisung gestoppt  wird.  (Der
              verfolgte  Prozess  wird  auch, wie üblich, über den Empfang des Signals gestoppt.)
              Aus der Sicht des Verfolgers scheint es, als ob der verfolgte Prozess durch Empfang
              eines  SIGTRAP  gestoppt  wurde.  Daher gibt es zum Beispiel für PTRACE_SYSCALL die
              Idee, beim ersten Stopp die Argumente  des  Systemaufrufs  zu  prüfen,  dann  einen
              anderen  PTRACE_SYSCALL  zu  schicken  und  den  Rückgabewert  des Systemaufrufs am
              zweiten Stopp zu prüfen. Das Argument Daten wird  wie  für  PTRACE_CONT  behandelt.
              (Adresse wird ignoriert.)

       PTRACE_SYSEMU, PTRACE_SYSEMU_SINGLESTEP (seit Linux 2.6.14)
              für PTRACE_SYSEMU beim nächsten Eintritt für den Systemaufruf, der nicht ausgeführt
              wird, fortfahren und stoppen; für PTRACE_SYSEMU_SINGLESTEP das gleiche tun, aber in
              einem  einzigen  Schritt,  wenn es sich nicht um einen Systemaufruf handelt. Dieser
              Aufruf wird von Programmen wie »User Mode Linux« verwandt,  die  die  Systemaufrufe
              des  verfolgten  Prozesses  emulieren  wollen.  Das  Argument  Daten  wird  wie für
              PTRACE_CONT behandelt. Das Argument Adresse wird ignoriert. Diese  Anfragen  werden
              derzeit nur unter x86 unterstützt.

       PTRACE_LISTEN (seit Linux 3.4)
              startet   den   gestoppten  verfolgten  Prozess  erneut,  verhindert  jedoch  seine
              Ausführung. Der resultierende Status ist dem eines Prozesses ähnlich, der durch ein
              SIGSTOP  (oder ein anderes Stoppsignal) angehalten wurde. Zusätzliche Informationen
              finden Sie im Unterabschnitt »Gruppenstopp«.  PTRACE_LISTEN  funktioniert  nur  bei
              verfolgten Prozessen, die durch PTRACE_SEIZE angehängt wurden.

       PTRACE_KILL
              sendet  dem  verfolgten  Prozess ein SIGKILL, um ihn zu beenden. (Adresse und Daten
              werden ignoriert.)

              Diese Transaktion ist überholt; benutzen Sie sie nicht! Senden Sie stattdessen  ein
              SIGKILL  direkt  mittels  kill(2)  oder tgkill(2). Das Problem bei PTRACE_KILL ist,
              dass es verlangt,  dass  sich  der  verfolgte  Prozess  in  eine  Signallieferstopp
              befindet, andernfalls funktioniert es möglicherweise nicht (d.h. es könnte komplett
              erfolgreich sein, würde aber den verfolgten Prozess killen). Im Gegensatz dazu  hat
              das direkte Senden von einem SIGKILL keine derartige Beschränkung.

       PTRACE_INTERRUPT (seit Linux 3.4)
              Stop  a  tracee.  If  the  tracee  is  running  or  sleeping  in  kernel  space and
              PTRACE_SYSCALL is in effect, the system call is interrupted  and  syscall-exit-stop
              is  reported.  (The  interrupted  system  call  is  restarted  when  the  tracee is
              restarted.) If the tracee was already stopped by a  signal  and  PTRACE_LISTEN  was
              sent  to  it,  the tracee stops with PTRACE_EVENT_STOP and WSTOPSIG(status) returns
              the stop signal. If any other ptrace-stop  is  generated  at  the  same  time  (for
              example,  if  a signal is sent to the tracee), this ptrace-stop happens. If none of
              the above applies (for example, if the tracee is running in  userspace),  it  stops
              with  PTRACE_EVENT_STOP  with  WSTOPSIG(status)  ==  SIGTRAP. PTRACE_INTERRUPT only
              works on tracees attached by PTRACE_SEIZE.

       PTRACE_ATTACH
              hängt an den Prozess, der durch PID angegeben wird, an, lässt  ihn  zum  verfolgten
              Prozess  des  aufrufenden Prozesses werden. Dem verfolgten Prozess wird ein SIGSTOP
              gesandt, er wird aber nicht notwendigerweise durch die  Vollendung  dieses  Aufrufs
              gestoppt;  benutzen  Sie waitpid(2), um auf das Stoppen des verfolgten Prozesses zu
              warten. Lesen Sie  den  Unterabschnitt  »Anhängen  und  Loslösen«,  um  zusätzliche
              Informationen zu erhalten. (Adresse und Daten werden ignoriert.)

       PTRACE_SEIZE (seit Linux 3.4)
              hängt  an  den  durch  PID angegebenen Prozess an und macht ihn zu einem verfolgten
              Prozess  des  aufrufenden  Prozesses.  Im   Gegensatz   zu   PTRACE_ATTACH   stoppt
              PTRACE_SEIZE  den  Prozess nicht. Nur ein mit PTRACE_SEIZE angehängter Prozess kann
              PTRACE_INTERRUPT- und PTRACE_LISTEN-Befehle entgegennehmen. Adresse muss Null sein.
              Daten enthält eine Bitmaske von Ptrace-Optionen, die sofort aktiviert werden.

       PTRACE_DETACH
              startet  den  gestoppten,  verfolgten  Prozess  wie  für PTRACE_CONT, löst ihn aber
              zuerst vom Prozess ab. Unter Linux  kann  ein  verfolgter  Prozess  auf  diese  Art
              abgelöst  werden,  ohne  Rücksicht darauf zu nehmen, welche Methode zum Starten der
              Verfolgung benutzt wurde.(Adresse wird ignoriert.)

   Tod unter Ptrace
       Wenn ein Prozess (der möglicherweise aus mehreren Threads besteht)  ein  killendes  Signal
       erhält  (eines,  dessen  Einstellung auf SIG_DFL gesetzt ist und dessen Standardaktion das
       Killen des Prozesses ist) werden alle Threads beendet. Verfolgte Prozesse melden ihren Tod
       an  ihre(n)  Verfolger.  Die  Benachrichtigung  über  dieses Ereignis wird über waitpid(2)
       zugestellt.

       Beachten Sie, dass das killende Signal  zuerst  einen  Signallieferstopp  (auf  nur  einen
       verfolgten  Prozess)  verursachen  wird und nur nachdem es durch den Verfolger eingespeist
       wurde (oder nachdem es an einen nicht verfolgten Thread versandt wurde), wird der Tod  von
       dem  Signal  auf  alle  verfolgten Prozesse innerhalb eines Prozesses mit mehreren Threads
       ausgehen. (Der Begriff »Signallieferstopp« wird nachfolgend erklärt.)

       SIGKILL  erzeugt  keinen  »Signallieferstopp«.  Daher  kann   der   Verfolger   es   nicht
       unterdrücken.     SIGKILL     killt    sogar    innerhalb    von    Systemaufrufen    (der
       Systemaufrufbeendigungsstopp wird nicht vorrangig vor dem Tod durch SIGKILL erzeugt).  Der
       reine  Effekt  besteht  darin,  dass  SIGKILL den Prozess (all seine Threads) immer killt,
       sogar dann, wenn einige Threads des Prozesses verfolgt werden.

       Wenn der verfolgte Prozess _exit(2) aufruft, meldet er seinem Verfolger seinen Tod. Andere
       Threads werden nicht beeinflusst.

       Wenn  irgendein  Thread  exit_group(2)  ausführt, meldet jeder verfolgte Prozess in dessen
       Gruppe seinen Tod an den Verfolger.

       Falls  die  Option  PTRACE_O_TRACEEXIT  aktiv  ist,   wird   PTRACE_EVENT_EXIT   vor   dem
       tatsächlichen  Tod  auftreten.  Dies wird angewandt, um mittels exit(2), exit_group(2) und
       Todessignalen (ausgenommen SIGKILL) zu beenden und wenn Threads  bei  execve(2)  in  einem
       Prozess mit mehreren Threads zerrissen werden.

       Der  Verfolger  kann  nicht  abschätzen, ob der von Ptrace gestoppte Prozess existiert. Es
       gibt mehrere Szenarien, in denen der verfolgte Prozess sterben kann, während  er  gestoppt
       ist   (wie   SIGKILL).   Daher   muss   der   Verfolger   vorbereitet  werden,  bei  allen
       Ptrace-Transaktionen einen ESRCH-Fehler zu  handhaben.  Leider  wird  der  gleiche  Fehler
       zurückgegeben, falls der verfolgte Prozess existiert, aber nicht von Ptrace gestoppt wurde
       (für Befehle, die einen gestoppten, verfolgten Prozess  erfordern)  oder  falls  er  nicht
       durch  den Prozess verfolgt wird, der den Ptrace-Aufruf abschickte. Der Verfolger muss den
       Überblick über den »laufend«-/»gestoppt«-Status  des  verfolgten  Prozesses  behalten  und
       ESRCH  nur  dann  als »verfolgter Prozess starb unerwartet« interpretieren, falls er weiß,
       dass der verfolgte  Prozess  beobachtet  wurde,  um  in  einen  Ptrace-stopp  einzutreten.
       Beachten  Sie,  dass  es  keine  Garantie  gibt,  dass  waitpid(WNOHANG)  zuverlässig  den
       Todesstatus  des  verfolgten  Prozesses  meldet,  falls  eine   Ptrace-Transaktion   ESRCH
       zurückgibt.  waitpid(WNOHANG)  könnte stattdessen 0 zurückgeben. In anderen Worten kann es
       sein,  dass  der  verfolgte  Prozess  »noch  nicht  vollständig  tot«  ist,  aber  bereits
       Ptrace-Anfragen ablehnt.

       Der  Verfolger  kann  nicht  abschätzen,  ob  der verfolgte Prozess immer sein Leben durch
       melden von WIFEXITED(status) oder WIFSIGNALED(status) aushaucht. Es gibt Fälle,  in  denen
       dies  nicht geschieht. Falls ein Thread, der nicht führender Thread der Thread-Gruppe ist,
       zum Beispiel ein execve(2) ausführt, verschwindet er; seine PID wird  nie  wieder  gesehen
       und  alle  nachfolgenden  Ptrace-Stopps  werden  unter  der  PID des führenden Threads der
       Thread-Gruppe gemeldet.

   Gestoppt-Status
       A tracee can be in two states: running or stopped. For the purposes of  ptrace,  a  tracee
       which  is  blocked  in  a  system  call  (such as read(2), pause(2), etc.) is nevertheless
       considered to be running, even if the tracee is blocked for a long time. The state of  the
       tracee  after  PTRACE_LISTEN  is  somewhat  of  a  gray area: it is not in any ptrace-stop
       (ptrace commands won't work on it, and it will deliver waitpid(2) notifications),  but  it
       also  may  be  considered  "stopped"  because  it  is  not  executing instructions (is not
       scheduled), and if it was in group-stop before  PTRACE_LISTEN,  it  will  not  respond  to
       signals until SIGCONT is received.

       Es  gibt  viele  Arten  von  Status,  wenn  ein  verfolgter  Prozess gestoppt wurde und in
       Ptrace-Diskussionen werden sie oft durcheinandergebracht. Daher ist  es  wichtig,  präzise
       Begriffe zu verwenden.

       In  dieser  Handbuchseite  wird jeder Gestoppt-Status, in dem der verfolgte Prozess bereit
       ist, Ptrace-Befehle vom Verfolger  zu  akzeptieren,  Ptrace-Stopp  genannt.  Ptrace-Stopps
       können  weiter  in  Signallieferstopp,  Gruppenstopp  und so fort unterteilt werden. Diese
       gestoppten Status werden nachfolgend im Detail beschrieben.

       Wenn der laufende, verfolgte Prozess in Ptrace-Stopp eintritt,  benachrichtigt  er  seinen
       Verfolger  mittels waitpid(2) (oder einem anderen der »wait«-Systemaufrufe). Meistens geht
       diese Handbuchseite davon aus, dass der Verfolger wartet mit:

           PID = waitpid(pid_or_minus_1, &status, __WALL);

       Mit Ptrace-Stopp angehaltene, verfolgte Prozesse werden als Rückgaben mit PID größer als 0
       und »WIFSTOPPED(status) true« gemeldet.

       Der  Schalter __WALL enthält nicht die Schalter WSTOPPED und WEXITED, impliziert aber ihre
       Funktionalität.

       Es wird nicht empfohlen, den Schalter WCONTINUED zu  setzen,  wenn  waitpid(2)  aufgerufen
       wird:  Der  Status  »continued«  gilt  pro Prozess und ihn zu verbrauchen, kann den echten
       Elternprozess des verfolgten Prozesses verwirren.

       Die Benutzung des Schalters WNOHANG könnte waitpid(2) veranlassen, 0 zurückzugeben (»nocht
       keine  Warteergebnisse  verfügbar«),  sogar  dann, wenn der Verfolger weiß, dass dort eine
       Benachrichtigung sein soll. Beispiel:

           errno = 0;
           ptrace(PTRACE_CONT, pid, 0L, 0L);
           if (errno == ESRCH) {
               /* verfolgter Prozess ist tot */
               r = waitpid(tracee, &status, __WALL | WNOHANG);
               /* r kann hier immer noch 0 sein! */
           }

       Die folgenden  Arten  von  Ptrace-Stopps  existieren:  Signallieferstopps,  Gruppenstopps,
       PTRACE_EVENT-Stopps   und   Systemaufrufstopps.   Sie   alle  werden  von  waitpid(2)  mit
       »WIFSTOPPED(status) true« gemeldet. Sie könnten durch  Untersuchen  des  Wertes  status>>8
       unterschieden  werden  und,  falls  es  eine  Unklarheit  im Wert gibt, durch Abfragen von
       PTRACE_GETSIGINFO. (Hinweis: Das Makro WSTOPSIG(status) kann nicht für diese  Untersuchung
       verwandt werden, da es den Wert (status>>8) & 0xff zurückgibt.)

   Signallieferstopp
       Wenn  ein Prozess (möglicherweise mit mehreren Threads) ein Signal außer SIGKILL empfängt,
       wählt der Kernel einen beliebigen Thread aus, der das Signal handhabt. (Falls  das  Signal
       mit  tgkill(2)  erzeugt  wurde,  kann  der  Ziel-Thread  explizit  durch  den  Aufrufenden
       ausgewählt werden.) Falls  der  ausgewählte  Thread  verfolgt  wird,  tritt  er  in  einen
       Signallieferstopp  ein.  An  diesem  Punkt  wird  das  Signal  noch  nicht  an den Prozess
       zugestellt und kann durch den Verfolger unterdrückt werden. Falls der Verfolger das Signal
       nicht  unterdrückt,  übergibt er das Signal bei der nächsten Ptrace-Neustartanfrage an den
       verfolgten  Prozess.  Dieser  zweite  Schritt  der   Signalzustellung   wird   in   dieser
       Handbuchseite  Signaleinspeisung  genannt.  Beachten Sie, dass, falls das Signal blockiert
       ist, der Signallieferstopp nicht auftritt, bis die Blockade des Signals aufgehoben  wurde,
       mit der üblichen Ausnahme, dass SIGSTOP nicht blockiert werden kann.

       Der  Signallieferstopp  wird  vom  Verfolger  als  waitpid(2)  beobachtet  und  kehrt  mit
       »WIFSTOPPED(status) true« mit dem Signal zurück, das  von  WSTOPSIG(status)  zurückgegeben
       wurde. Falls das Signal SIGTRAP ist, könnte dies eine andere Art eines Ptrace-Stopps sein;
       Einzelheiten finden Sie in den Abschnitten »Systemaufrufstopps«  und  »execve«  unterhalb.
       Falls  WSTOPSIG(status)  ein  stoppendes  Signal  zurückgibt, könnte dies ein Gruppenstopp
       sein; siehe unten.

   Signaleinspeisung und -unterdrückung
       Nachdem der Signallieferstopp durch den Verfolger beobachtet wurde, sollte  der  Verfolger
       den verfolgten Prozess mit dem Aufruf

           ptrace(PTRACE_restart, PID, 0, Signal)

       neu  starten,  wobei  PTRACE_restart  einer  der neu startenden Ptrace-Anfragen ist. Falls
       Signal 0 ist, wird das  Signal  nicht  zugestellt.  Andernfalls  wird  das  Signal  Signal
       zugestellt.  Diese  Transaktion wird in dieser Handbuchseite Signaleinspeisung genannt, um
       sie vom Signallieferstopp zu unterscheiden.

       Der Signalwert kann sich vom  Wert  WSTOPSIG(status)  unterschieden:  Der  Verfolger  kann
       veranlassen, dass ein anderes Signal eingespeist wird.

       Beachten  Sie,  dass  ein  unterdrücktes  Signal  immer  noch Systemaufrufe verursacht, um
       vorzeitig zurückzukehren. In diesem Fall werden Systemaufrufe neu gestartet: Der Verfolger
       wird den verfolgten Prozess beobachten, um den unterbrochenen Systemaufruf neu auszuführen
       (oder den Systemaufruf restart_syscall(2) für wenige Systemaufrufe,  die  unterschiedliche
       Mechanismen  zum  erneuten Starten verwenden), falls der Verfolger PTRACE_SYSCALL benutzt.
       Sogar Systemaufrufe (wie poll(2)), die nach einem Signal nicht  mehr  neu  startbar  sind,
       werden nach dem Unterdrücken des Signals neu gestartet werden. Es existieren jedoch einige
       Kernelfehler, die zum Fehlschlagen einiger Systemaufrufe mit  EINTR  führen,  sogar,  wenn
       kein beobachtbares Sygnal in den verfolgten Prozess eingespeist wurde.

       Es  wird  nicht  garantiert,  dass  beim  Neustarten  von  Ptrace-Befehlen, die in anderen
       Ptrace-Stopps als Signallieferstopps angestoßen wurden,ein Signal eingespeist wird,  nicht
       einmal, wenn Signal nicht Null ist. Es wird kein Fehler gemeldet; ein Signal ungleich Null
       könnte einfach ignoriert werden. Ptrace-Benutzer sollten nicht versuchen,  auf  diese  Art
       »ein neues Signal zu erzeugen«: Benutzen Sie stattdessen tgkill(2).

       Die  Tatsache,  dass  Signaleinspeisungsanfragen  beim  erneuten  Starten  des  verfolgten
       Prozesses nach Ptrace-Stopps, die keine Signallieferstopps sind, ignoriert werden  können,
       ist  ein  Grund  für Verwirrung bei Ptrace-Benutzern. Ein typisches Szenario ist, dass der
       Verfolger Gruppenstopps beobachtet, sie fälschlicherweise für Signallieferstopps hält  und
       den verfolgen Prozess mit

           ptrace(PTRACE_restart, PID, 0, Stoppsignal)

       neu  startet mit der Absicht Stoppsignal einzuspeisen, Stoppsignal aber ignoriert wird und
       der verfolgte Prozess weiter läuft.

       Das Signal SIGCONT hat einen Seiteneffekt, dass es einen  Prozess  im  Gruppenstopp  (alle
       Threads  davon)  aufweckt.  Dieser  Seiteneffekt  tritt vor dem Signallieferstopp auf. Der
       Verfolger kann diesen Seiteneffekt  nicht  unterdrücken  (er  kann  nur  Signaleinspeisung
       unterdrücken,  was nur dazu führt, dass die SIGCONT-Handhabung nicht im verfolgten Prozess
       ausgeführt wird, falls eine solche Handhabung installiert  ist).  Tatsächlich  könnte  dem
       Aufwecken  aus  den  Gruppenstopp  ein  Signallieferstopp  für  andere Signale als SIGCONT
       folgen, falls sie ausstehen, wenn SIGCONT gesandt wurde. In anderen Worten könnte es sein,
       dass  SIGCONT  nicht  das  erste  durch  den  Verfolger beobachtete Signal ist, nachdem es
       gesandt wurde.

       Stoppen von Signalen führt dazu, das ein Prozess (alle Treads davon) in einen Gruppenstopp
       eintreten.  Dieser  Seiteneffekt tritt nach der Signaleinspeisung auf und kann daher durch
       den Verfolger unterdrückt werden.

       In Linux 2.4 und älter kann das Signal SIGSTOP nicht eingespeist werden.

       PTRACE_GETSIGINFO kann benutzt werden, um eine siginfo_t-Struktur  zu  erhalten,  die  dem
       gesandten  Signal  entspricht.  PTRACE_SETSIGINFO kann benutzt werden, um es zu verändern.
       Falls PTRACE_SETSIGINFO benutzt wurde, um siginfo_t zu verändern, müssen das Feld si_signo
       und  der  Parameter  Signal  im  Befehl  zum  Neustart übereinstimmen, andernfalls ist das
       Ergebnis undefiniert.

   Gruppenstopp
       Wenn ein Prozess  (der  möglicherweise  aus  mehreren  Threads  besteht)  ein  Stoppsignal
       empfängt,  werden  alle Threads gestoppt. Falls einige Threads verfolgt werden, treten sie
       in  eine  Thread-Gruppe  ein.  Beachten   Sie,   dass   das   Stoppsignal   zuerst   einen
       Signallieferstopp  verursachen  wird  (nur auf den verfolgten Prozess) und nur, nachdem es
       durch den Verfolger eingespeist wurde (oder nachdem es an einen  Thread  geschickt  wurde,
       der  nicht  verfolgt  wird),  wird der Gruppenstopp auf alle verfolgten Prozesse innerhalb
       eines Prozesses aus mehreren  Threads  eingeleitet.  Wie  üblich  meldet  jeder  verfolgte
       Prozess seinen Gruppenstopp separat an den entsprechenden Verfolger.

       Der   Gruppenstopp   wird   vom   Verfolger   als  waitpid(2)  beobachtet  und  kehrt  mit
       »WIFSTOPPED(status) true« mit dem Stoppsignal zurück, das über WSTOPSIG(status)  verfügbar
       ist.  Dasselbe  Ergebnis wird von einigen anderen Klassen von Ptrace-Stopps zurückgegeben,
       daher ist die empfohlene Vorgehensweise, folgenden Aufruf zu tätigen:

           ptrace(PTRACE_GETSIGINFO, PID, 0, &siginfo)

       Der Aufruf kann vermieden werden, falls das Signal nicht SIGSTOP,  SIGTSTP,  SIGTTIN  oder
       SIGTTOU  ist.  Nur diese vier Signale sind Stoppsignale. Falls der Verfolger etwas anderes
       sieht, kann es kein Gruppenstopp sein.  Andernfalls  benötigt  der  Verfolger  den  Aufruf
       PTRACE_GETSIGINFO.  Falls  PTRACE_GETSIGINFO  mit EINVAL fehlschlägt, ist es definitiv ein
       Gruppenstopp. (Andere Fehlerkodes wie ESRCH  (»kein  derartiger  Prozess«)  sind  möglich,
       falls ein SIGKILL den verfolgten Prozess gekillt hat.

       If  tracee  was attached using PTRACE_SEIZE, group-stop is indicated by PTRACE_EVENT_STOP:
       status>>16 == PTRACE_EVENT_STOP. This allows detection of group-stops without requiring an
       extra PTRACE_GETSIGINFO call.

       Ab  Linux  2.6.38  wird  der verfolgte Prozess, nachdem der Verfolger den Ptrace-Stopp des
       verfolgten Prozesses sieht und bis er neu startet oder ihn killt, nicht laufen  und  keine
       Benachrichtigungen  an  den  Verfolger senden (außer dem Tod durch SIGKILL), nicht einmal,
       wenn der Verfolger in einen anderen waitpid(2)-Aufruf gelangt.

       Das  im  vorhergehenden  Absatz  beschriebene  Verhalten  verursacht   ein   Problem   bei
       transparenter  Behandlung  von  Stoppsignalen.  Falls der Verfolger den verfolgten Prozess
       nach einem  Gruppenstopp  neu  startet,  wird  das  Stoppsignal  effektiv  ignoriert  —der
       verfolgte  Prozess  bleibt  nicht  gestoppt,  er läuft. Falls der Verfolger den verfolgten
       Prozess neu startet, bevor er  in  das  nächste  waitpid(2)  eintritt,  werden  zukünftige
       SIGCONT-Signale  nicht  an  den  Verfolger  gemeldet.  Dies  würde  dazu  führen, dass die
       SIGCONT-Signale keine Auswirkungen auf den verfolgten Prozess haben.

       Seit Linux 3.4 gibt es eine Methode, die dieses Problem bewältigt: Statt PTRACE_CONT  kann
       ein  PTRACE_LISTEN-Befehl  zum  Neustart eines verfolgten Prozesses auf eine Weise benutzt
       werden, die ihn nicht ausführt, aber auf ein neues Ereignis wartet, das er über waitpid(2)
       melden kann, wenn er zum Beispiel mit SIGCONT neu gestartet wird.

   PTRACE_EVENT-Stopps
       Falls  der  Verfolger  PTRACE_O_TRACE_*-Optionen  setzt,  wird  der  verfolgte  Prozess in
       PTRACE_EVENT-Stopps genannte Stopps gelangen.

       PTRACE_EVENT-Stopps werden durch den Verfolger als als waitpid(2) beobachtet,  kehren  mit
       »WIFSTOPPED(status)  true«  zurück  und  WSTOPSIG(status) gibt SIGTRAP zurück. Es wird ein
       zusätzliches Bit in das höhere Bit des Status (Datentyp Word) gesetzt: Der Wert  status>>8
       wird wie folgt sein:

           (SIGTRAP | PTRACE_EVENT_foo << 8).

       Es gibt die folgenden Ereignisse:

       PTRACE_EVENT_VFORK
              stoppt   vor   dem  Zurückkehren  von  vfork(2)  oder  clone(2)  mit  dem  Schalter
              CLONE_VFORK. Wenn der verfolgte Prozess nach diesem Stopp fortgeführt wird, wird er
              auf  das Beenden/Ausführen des Kindprozesses warten, bevor er mit seiner Ausführung
              fortfährt (in anderen Worten, das übliche Verhalten auf vfork(2)).

       PTRACE_EVENT_FORK
              stoppt vor dem Zurückkehren von fork(2) oder clone(2) mit dem auf SIGCHLD gesetzten
              Beendigungssignal.

       PTRACE_EVENT_CLONE
              stoppt vor dem Zurückkehren von clone(2).

       PTRACE_EVENT_VFORK_DONE
              stoppt   vor   dem  Zurückkehren  von  vfork(2)  oder  clone(2)  mit  dem  Schalter
              CLONE_VFORK, aber nachdem die Blockade dieses verfolgten  Prozesses  durch  Beenden
              oder Ausführung aufgehoben wurde.

       Für  alle  vier  oben  beschriebenen  Stopps tritt der Stopp im Elternprozess auf (d.h. im
       verfolgenden Prozess), nicht im neu erstellten  Thread.  PTRACE_GETEVENTMSG  kann  benutzt
       werden, um die Kennung des neuen Threads zu erhalten.

       PTRACE_EVENT_EXEC
              stoppt  vor  dem  Zurückkehren von execve(2). Ab Linux 3.0, gibt PTRACE_GETEVENTMSG
              die vorherige Thread-Kennung zurück.

       PTRACE_EVENT_EXIT
              stoppt vor dem Beenden (einschließlich des Todes aus exit_group(2)), dem  Signaltod
              oder  endet,  verursacht  durch  execve(2),  in einem Prozess aus mehreren Threads.
              PTRACE_GETEVENTMSG gibt den Exit-Status zurück. Register können  untersucht  werden
              (solange  nicht  »wirklich«  beendet  wird).  Der  verfolgte Prozess ist immer noch
              lebendig;  er  benötigt   zum   Fertigstellen   des   Beendens   PTRACE_CONT   oder
              PTRACE_DETACH.

       PTRACE_EVENT_STOP
              Stop  induced  by  PTRACE_INTERRUPT  command, or group-stop, or initial ptrace-stop
              when  a  new  child  is  attached  (only  if  attached  using   PTRACE_SEIZE),   or
              PTRACE_EVENT_STOP if PTRACE_SEIZE was used.

       PTRACE_GETSIGINFO  auf  PTRACE_EVENT-Stopps gibt SIGTRAP in si_signo zurück, wobei si_code
       auf (event<<8) | SIGTRAP gesetzt ist.

   Systemaufrufstopps
       Falls der verfolgte Prozess durch PTRACE_SYSCALL neu gestartet wurde, gerät der  verfolgte
       Prozess   in  einen  Systemaufrufeintrittsstopp  kurz  vor  dem  Eintritt  in  irgendeinen
       Systemaufruf. Falls der Verfolger den verfolgten Prozess mit PTRACE_SYSCALL  neu  startet,
       gerät  der  verfolgte Prozess in einen Systemaufrufbeendigungsstopp, wenn der Systemaufruf
       beendet  ist  oder  falls  er  durch  ein  Signal   unterbrochen   wurde.   (Sprich,   der
       Signallieferstopp      tritt      nie      zwischen     Systemaufrufeintrittsstopp     und
       Systemaufrufbeendigungsstopp auf; er findet nach dem Systemaufrufbeendigungsstopp statt.)

       Andere Möglichkeiten sind, dass der verfolgte Prozess in einem PTRACE_EVENT-Stopp  stoppen
       könnte,  endet  (falls  er in _exit(2) oder exit_group(2) eintritt), durch SIGKILL gekillt
       wird oder leise stirbt (falls er die Thread-Gruppe anführt, kommt das execve(2)  in  einem
       anderen  Thread  vor  und  der  Thread  wird  nicht  vom  selben Verfolger verfolgt; diese
       Situation wird später besprochen).

       Systemaufrufeintrittsstopp und Systemaufrufbeendigungsstopp werden vom Verfolger  als  als
       waitpid(2)  beobachtet,  kehren  mit »WIFSTOPPED(status) true« zurück und WSTOPSIG(status)
       gibt SIGTRAP zurück. Falls die Option PTRACE_O_TRACESYSGOOD durch  den  Verfolger  gesetzt
       wurde, wird WSTOPSIG(status) den Wert (SIGTRAP | 0x80) zurückgeben.

       Systemaufrufstopps   können   von   Signallieferstopps   mit  SIGTRAP  durch  Abfrage  von
       PTRACE_GETSIGINFO für die folgenden Fälle unterschieden werden:

       si_code <= 0
              SIGTRAP wurde  mit  einem  Ergebnis  einer  Userspace-Aktion,  zum  Beispiel  einem
              Systemaufruf    ((tgkill(2),    kill(2),    sigqueue(3),    etc.),   Ablauf   eines
              POSIX-Zeitnehmers,   Statusänderung   einer   POSIX-Nachrichtenwarteschlange   oder
              Vervollständigung einer asynchronen E/A-Anfrage geliefert.

       si_code == SI_KERNEL (0x80)
              SIGTRAP wurde vom Kernel gesandt.

       si_code == SIGTRAP or si_code == (SIGTRAP|0x80)
              Dies ist ein Systemaufrufstopp.

       Systemaufrufstopps kommen jedoch sehr oft vor (zweimal pro Systemaufruf) und das Ausführen
       von PTRACE_GETSIGINFO für jeden Systemaufrufstopp könnte etwas aufwendig sein.

       Einige Architekturen erlauben, die Fälle durch Untersuchen der Register zu  unterscheiden.
       Zum  Beispiel auf x86, rax == -ENOSYS im Systemaufrufeintrittsstopp. Da SIGTRAP (wie jedes
       andere Signal) immer nach dem Systemaufrufbeendigungsstopp  auftritt  und  rax  an  diesem
       Punkt  fast nie ENOSYS enthält, sieht das SIGTRAP aus wie ein »Systemaufrufstopp, der kein
       Systemaufrufeintrittsstopp« ist; in anderen Worten, er  sieht  aus  wie  ein  »herrenloser
       Systemaufrufbeendigungsstopp«  und  kann  auf  diese Art entdeckt werden. Aber eine solche
       Entdeckung ist fragil und wird am besten vermieden.

       Die  Benutzung  der  Option  PTRACE_O_TRACESYSGOOD  ist   die   empfohlene   Methode,   um
       Systemaufrufstopps   von   anderen  Arten  der  Ptrace-Stopps  zu  unterscheiden,  da  sie
       zuverlässig ist und sich keine Leistungseinbuße zuzieht.

       Systemaufrufeintrittsstopp und Systemaufrufbeendigungsstopp sind für den  Verfolger  nicht
       voneinander  zu  unterscheiden.  Der  Verfolger  muss  den  Überblick über die Abfolge der
       Ptrace-Stopps behalten, um  nicht  den  Systemaufrufeintrittsstopp  fälschlicherweise  als
       Systemaufrufbeendigungsstopp  oder  umgekehrt  zu  interpretieren.  Die Regel besagt, dass
       diesem     Systemaufrufeintrittsstopp     immer     ein      Systemaufrufbeendigungsstopp,
       PTRACE_EVENT-Stopp  oder  der  Tod des verfolgten Prozesses folgt; dazwischen können keine
       anderen Arten von Ptrace-Stopps auftreten.

       Falls  der  Verfolger  nach  dem  Systemaufrufeintrittsstopp  einen  anderen  Befehl   zum
       Neustarten  als  PTRACE_SYSCALL  verwendet,  wird  der  Systemaufrufbeendigungsstopp nicht
       erzeugt.

       PTRACE_GETSIGINFO auf Systemaufrufstopps gibt SIGTRAP in si_signo  zurück,  wobei  si_code
       auf SIGTRAP oder (SIGTRAP|0x80) gesetzt ist.

   PTRACE_SINGLESTEP-, PTRACE_SYSEMU-, PTRACE_SYSEMU_SINGLESTEP-Stopps
       [Einzelheiten dieser Arten von Stopps sind noch nicht dokumentiert.]

   Benachrichtigende und neustartende Ptrace-Befehle
       Die  meisten  Ptrace-Befehle  (alle  außer  PTRACE_ATTACH,  PTRACE_SEIZE,  PTRACE_TRACEME,
       PTRACE_INTERRUPT  und  PTRACE_KILL)  erfordern,  dass  der  verfolgte  Prozess  in   einem
       Ptrace-Stopp ist, andernfalls scheitern sie mit ESRCH.

       Wenn  der  verfolgte  Prozess im Ptrace-Stopp ist, kann der Verfolger Daten des verfolgten
       Prozesses mittels benachrichtigenden Befehlen lesen und schreiben. Diese Befehle  belassen
       den verfolgten Prozess im Status Ptrace-gestoppt:

           ptrace(PTRACE_PEEKTEXT/PEEKDATA/PEEKUSER, PID, Adresse, 0);
           ptrace(PTRACE_POKETEXT/POKEDATA/POKEUSER, PID, Adresse, long_val);
           ptrace(PTRACE_GETREGS/GETFPREGS, PID, 0, &struct);
           ptrace(PTRACE_SETREGS/SETFPREGS, PID, 0, &struct);
           ptrace(PTRACE_GETREGSET, PID, NT_foo, &iov);
           ptrace(PTRACE_SETREGSET, PID, NT_foo, &iov);
           ptrace(PTRACE_GETSIGINFO, PID, 0, &siginfo);
           ptrace(PTRACE_SETSIGINFO, PID, 0, &siginfo);
           ptrace(PTRACE_GETEVENTMSG, PID, 0, &long_var);
           ptrace(PTRACE_SETOPTIONS, PID, 0, PTRACE_O_flags);

       Beachten Sie, dass einige Fehler nicht gemeldet wurden. Das Setzen des Informationssignals
       (siginfo) hat zum Beispiel in einigen Ptrace-Stopps möglicherweise keine Auswirkungen, der
       Aufruf  kann  jedoch erfolgreich sein (0 zurückgeben und errno nicht setzen); Abfragen von
       PTRACE_GETEVENTMSG könnte erfolgreich sein und einen zufälligen  Wert  zurückgeben,  falls
       der    aktuelle   Ptrace-Stopp   nicht   dokumentiert   ist,   um   eine   aussagekräftige
       Ereignisnachricht zuückzugeben.

       Der Aufruf

           ptrace(PTRACE_SETOPTIONS, PID, 0, PTRACE_O_flags);

       beeinflusst einen verfolgten Prozess. Die  aktuellen  Schalter  des  verfolgten  Prozesses
       werden  ersetzt.  Schalter  werden  geerbt  durch  neu  erzeugte Prozesse und »automatisch
       angehängt«     über     aktive     PTRACE_O_TRACEFORK-,     PTRACE_O_TRACEVFORK-      oder
       PTRACE_O_TRACECLONE-Optionen.

       Eine  weitere  Gruppe  von  Befehlen  lässt die per Ptrace gestoppten, verfolgten Prozesse
       laufen. Sie haben die Form:

           ptrace(Befehl, PID, 0, Signal);

       wobei Befehl PTRACE_CONT, PTRACE_LISTEN, PTRACE_DETACH, PTRACE_SYSCALL, PTRACE_SINGLESTEP,
       PTRACE_SYSEMU  oder  PTRACE_SYSEMU_SINGLESTEP  ist.  Falls  der  verfolgte Prozess sich im
       Signallieferstopp befindet, ist Signal das Signal, das eingespeist wird (falls es ungleich
       Null  ist).  Andernfalls  kann  Signal  ignoriert werden. (Wenn ein verfolgter Prozess von
       einem  anderen  Ptrace-Stopp  als  dem  Signallieferstopp  neu  gestartet  wird,  ist  die
       empfohlene Vorgehensweise, 0 in Signal zu übergeben.)

   Anhängen und Loslösen
       Ein Thread kann an den Verfolger angehängt werden mit dem Aufruf

           ptrace(PTRACE_ATTACH, PID, 0, 0);

       oder

           ptrace(PTRACE_SEIZE, PID, 0, PTRACE_O_flags);

       PTRACE_ATTACH  sendet  außerdem SIGSTOP an diesen Thread. Falls der Verfolger möchte, dass
       dieser SIGSTOP keine Auswirkungen hat, muss er ihn unterdrücken. Beachten  Sie,  dass  der
       Verfolger,  falls  während  des  Anhängens  gleichzeitig  weitere Signale an diesen Thread
       gesandt werden, den Eintritt in den Signallieferstopp mit anderen Signalen  zuerst  sieht!
       Die  übliche  Vorgehensweise ist, diese Signale neu einzuspeisen, bis SIGSTOP gesehen wird
       und dann die Einspeisung von SIGSTOP zu unterdrücken. Der Entwurfsfehler ist hierbei, dass
       sich ein Ptrace-Anhängen und ein gleichzeitig gesandtes SIGSTOP einen Wettlauf liefern und
       das gleichzeitige SIGSTOP verloren gegangen sein kann.

       Da Anhängen SIGSTOP sendet und der Verfolger es üblicherweise unterdrückt, könnte dies  zu
       einer   herrenlosen   EINTR-Rückgabe  vom  aktuell  ausgeführten  Systemaufruf  in  diesem
       verfolgten Prozess führen, wie er  im  Abschnitt  »Signaleinspeisung  und  -unterdrückung«
       beschrieben wird.

       Seit  Linux  3.4 kann PTRACE_SEIZE anstelle von PTRACE_ATTACH benutzt werden. PTRACE_SEIZE
       stoppt nicht den angehängten Prozess. Falls Sie ihn  nach  dem  Anhängen  (oder  zu  einem
       anderen  Zeitpunkt)  stoppen wollen ohne irgendwelche Signale zu senden, verwenden Sie den
       Befehl PTRACE_INTERRUPT.

       Die Anfrage

           ptrace(PTRACE_TRACEME, 0, 0, 0);

       verwandelt den aufrufenden Thread in einen verfolgten Prozess. Der Thread  fährt  mit  der
       Ausführung  fort  (gerät  nicht  in den Ptrace-Stopp). Eine übliche Vorgehensweise besteht
       darin, PTRACE_TRACEME mit

           raise(SIGSTOP);

       zu folgen  und  dem  Elternprozess  (der  nun  der  Verfolger  ist)  zu  ermöglichen,  den
       Signallieferstopp zu beobachten.

       Falls  die  Optionen  PTRACE_O_TRACEFORK,  PTRACE_O_TRACEVFORK oder PTRACE_O_TRACECLONE in
       Kraft sind, werden Kindprozesse mit vfork(2), beziehungsweise clone(2)  mit  dem  Schalter
       CLONE_VFORK, fork(2) oder clone(2) mit auf SIGCHLD gesetztem Beendigungssignal und anderen
       Arten  von  clone(2)  automatisch  an  den  gleichen  Verfolger   angehängt,   der   ihren
       Elternprozess  verfolgte. SIGSTOP wird an die Kindprozesse gesandt, was sie veranlasst, in
       einen Signallieferstopp zu gelangen, nachdem sie den Systemaufruf beenden, der sie erzeugt
       hat.

       Loslösen des verfolgten Prozesses wird erreicht durch:

           ptrace(PTRACE_DETACH, PID, 0, Signal);

       PTRACE_DETACH  ist eine Neustartoperation; daher erfordert sie, dass der verfolgte Prozess
       in einem Ptrace-Stopp ist. Falls der verfolgte Prozess  in  einem  Signallieferstopp  ist,
       kann  ein Signal eingespeist werden. Andernfalls wird der Parameter Signal stillschweigend
       ignoriert.

       Falls der verfolgte Prozess läuft, wenn der Verfolger ihn  loslösen  möchte,  besteht  die
       übliche Lösung darin, SIGSTOP zu senden (mittels tgkill(2), um sicherzustellen, dass es an
       den korrekten Thread geht),  darauf  zu  warten,  dass  der  verfolgte  Prozess  in  einen
       Signallieferstopp  für  SIGSTOP  stoppt  und ihn dann loszulösen (SIGSTOP-Einspeisung wird
       unterdrückt). Ein Entwurfsfehler ist, dass sich dies mit  gleichzeitigen  SIGSTOPs  Rennen
       liefern  kann.  Eine  weitere  Komplikation  besteht  darin, dass der verfolgte Prozess in
       andere Ptrace-Stopps geraten kann und neu gestartet werden muss und nochmals  wartet,  bis
       SIGSTOP  gesehen  wird.  Noch eine weitere Komplikation ist, dass nicht sicher ist, ob der
       verfolgte Prozess nicht bereits  mit  Ptrace  gestoppt  wurde,  da  keine  Signallieferung
       stattfindet, obwohl es —nicht gerade SIGSTOP ist.

       Falls  der Verfolger stirbt, werden alle verfolgten Prozesse automatisch losgelöst und neu
       gestartet, es sei denn, sie sind im Gruppenstopp. Die Handhabung  des  Neustarts  aus  dem
       Gruppenstopp  ist derzeit fehlerhaft, aber das »wie-geplant«-Verhalten ist, den verfolgten
       Prozess gestoppt zu lassen und auf SIGCONT zu warten. Falls der verfolgte Prozess neu  vom
       Signallieferstopp gestartet wurde, wird das ausstehende Signal einspeist.

   execve(2) unter Ptrace
       Wenn  ein  Thread  in  einem  Prozess mit mehreren Threads execve(2) aufruft, zerstört der
       Kernel alle anderen Threads im Prozess  und  setzt  die  Thread-Kennung  des  ausführenden
       Threads auf die Gruppenkennung (Prozesskennung) zurück. (Oder anders ausgedrückt, wenn ein
       Prozess mit mehreren Threads ein execve(2) bei  Vervollständigung  des  Aufrufs  ausführt,
       scheint  es  durch  das  execve(2)  im  führenden  Thread  der  Prozessgruppe aufzutreten,
       unabhängig  davon,  welcher  Thread  das  execve(2)  aufrief.)  Dieses  Zurücksetzen   der
       Thread-Kennung sieht für Verfolger sehr verwirrend aus:

       *  Alle   anderen   Threads   stoppen   im   PTRACE_EVENT_EXIT-Stopp,   falls  die  Option
          PTRACE_O_TRACEEXIT eingeschaltet wurde. Dann melden  alle  anderen  Threads  außer  dem
          führenden  Thread  der  Gruppe  den  Tod,  als ob sie über _exit(2) mit dem Exit-Kode 0
          beendet worden wären.

       *  Der ausführende, verfolgte Prozess ändert  seine  Thread-Kennung,  während  er  in  dem
          execve(2)  ist.  (Denken  Sie daran, unter Ptrace ist die von waitpid(2) zurückgegebene
          oder in Ptrace-Aufrufe gespeiste »PID«, die Thread-Kennung des  verfolgten  Prozesses.)
          Sprich,  die  Thread-Kennung  des  verfolgten Prozesses wird zurückgesetzt, so dass sie
          ihrer Prozesskennung entspricht, die dieselbe ist, wie die Thread-Kennung des führenden
          Threads der Thread-Gruppe.

       *  Dann  kommt  es  zu  einem PTRACE_EVENT_EXEC-Stopp, falls die Option PTRACE_O_TRACEEXEC
          eingeschaltet wurde.

       *  Falls der  führende  Thread  der  Gruppe  seinen  PTRACE_EVENT_EXEC-Stopp  mittlerweile
          gemeldet  hat,  scheint  es für den Verfolger, als ob der tote führende Thread »aus dem
          Nichts wieder auftaucht«. (Hinweis: Der führende Thread der Gruppe meldet den Tod nicht
          über  WIFEXITED(status)  bis  es  mindestens  einen  lebenden anderen Thread gibt. Dies
          eliminiert die Möglichkeit, dass der Verfolger ihn sterben und dann  erneut  erscheinen
          sieht.)  Falls  der  führende  Thread  der  Gruppe immer noch lebt, könnte dies für den
          Verfolger so aussehen, als  ob  der  führende  Thread  der  Gruppe  von  einem  anderen
          Systemaufruf  als  dem  beigetretenen  zurückkehrt  oder  sogar »von einem Systemaufruf
          zurückkehrt, obwohl er in keinem Systemaufruf  war«.  Falls  der  führende  Thread  der
          Gruppe  nicht  verfolgt  wurde  (oder von einem anderen Verfolger verfolgt wurde), dann
          wird es während execve(2) so aussehen, als ob er ein verfolgter Prozess des  Verfolgers
          des ausführenden verfolgten Prozesses geworden wäre.

       All  die  Auswirkungen  oberhalb  sind Artefakte des Thread-Kennungswechsels im verfolgten
       Prozess.

       Die Option PTRACE_O_TRACEEXEC ist das  emfpohlene  Werkzeug  für  den  Umgang  mit  dieser
       Situation. Zuerst aktiviert es PTRACE_EVENT_EXEC-Stopp, der vor der Rückkehr von execve(2)
       auftritt. In  diesem  Stopp  kann  der  Verfolger  PTRACE_GETEVENTMSG  verwenden,  um  die
       vorherige  Thread-Kennung  des  verfolgten Prozesses zu erhalten. (Diese Funktion wurde in
       Lunux 3.0 eingeführt.) Als zweites deaktiviert  die  Option  PTRACE_O_TRACEEXEC  die  alte
       SIGTRAP-Erzeugung auf execve(2).

       Wenn  der  Verfolger die PTRACE_EVENT_EXEC-Stoppbenachrichtigung empfängt, ist garantiert,
       dass außer diesem verfolgten Prozess und dem führenden Thread  der  Gruppe  keine  anderen
       Threads des Prozesses lebendig sind.

       Beim  Empfang  der  PTRACE_EVENT_EXEC-Stoppbenachrichtigung sollte der Verfolger all seine
       internen Datenstrukturen aufräumen, die Threads dieses Prozesses beschreiben und nur  eine
       Datenstruktur behalten, —eine, die den einzelnen, laufenden, verfolgten Prozess beschreibt
       mit

           Thread-Kennung == Thread-Gruppenkennung == Prozesskennung.

       Beispiel: Zwei Thread rufen zur gleichen Zeit execve(2) auf:

       *** wir bekommen einen Systemaufrufeintrittsstopp in Thread 1: **
       PID1 execve("/bin/foo", "foo" <nicht abgeschlossen …>
       *** wir liefern PTRACE_SYSCALL für Thread 1 **
       *** wir bekommen einen Systemaufrufeintrittsstopp in Thread 2: **
       PID2 execve("/bin/bar", "bar" <nicht abgeschlossen …>
       *** wir liefern PTRACE_SYSCALL für Thread 2 **
       *** wir bekommen PTRACE_EVENT_EXEC für PID0, wir liefern  PTRACE_SYSCALL **
       *** wir bekommen Systemaufrufbeendigungsstopp für PID0: **
       PID0 <… execve wieder aufgenommen> )             = 0

       Falls die Option PTRACE_O_TRACEEXEC für den  ausführenden,  verfolgten  Prozess  nicht  in
       Kraft  ist,  sendet der Kernel ein zusätzliches SIGTRAP an den verfolgten Prozess, nachdem
       execve(2) zurückgekehrt ist. Dies ist ein gewöhnliches Signal (ähnlich  einem,  das  durch
       kill  -TRAP  erzeugt werden kann), keine Spezialart eines Ptrace-Stopps. Unter Einsatz von
       PTRACE_GETSIGINFO für dieses Signal gibt si_code auf 0 gesetzt  (SI_USER)  zurück.  Dieses
       Signal  kann  durch  die Signalmaske blockiert sein und könnte daher (viel) später gesandt
       werden.

       Üblicherweise würde der Verfolger dem  Anwender  dieses  zusätzliche  SIGTRAP-Signal  nach
       Execve  nicht  zeigen  wollen  und  seinen  Versand an den verfolgten Prozess unterdrücken
       (falls SIGTRAP auf SIGTRAP gesetzt ist, killt es das Signal). Es ist jedoch nicht  einfach
       zu  bestimmen,  welches  SIGTRAP zu unterdrücken ist. Die empfohlene Herangehensweise ist,
       die  Option  PTRACE_O_TRACEEXEC  zu  setzen  und  daher  dieses  zusätzliche  SIGTRAP   zu
       unterdrücken.

   Echter Elternprozess
       Die   Ptrace-API  (miss)braucht  die  Standard-UNIX-Eltern-/Kindprozess-Signalgebung  über
       waitpid(2). Diese wird benutzt,  um  den  echten  Elternprozess  zum  Stopp  des  Empfangs
       mehrerer  Arten  von  waitpid(2)-Benachrichtigungen  zu  veranlassen, wenn der Kindprozess
       durch einen anderen Prozess verfolgt wird.

       Viele dieser Fehler wurden behoben, aber ab Linux 2.6.38 existieren  etliche  immer  noch;
       siehe FEHLER oberhalb.

       Ab Linux 2.6.38 wird davon ausgegangen, dass das folgende korrekt funktioniert:

       *  Beenden/Sterben  durch  Signal  wird  zuerst  an den Verfolger gemeldet, dann, wenn der
          Verfolger das waitpid(2)-Ergebnis verbraucht,  an  den  echten  Elternprozess  (an  den
          echten Elternprozess nur, wenn der ganze Prozess aus mehreren Threads existiert). Falls
          der Verfolger und der echte Elternprozess derselbe Prozess sind, wird der  Bericht  nur
          einmal gesandt.

RÜCKGABEWERT

       On  success,  PTRACE_PEEK* requests return the requested data, while other requests return
       zero. (On Linux, this is done in the libc wrapper around ptrace system call. On the system
       call  level,  PTRACE_PEEK*  requests  have  a  different API: they store the result at the
       address specified by data parameter, and return value is the error flag.)

       On error, all requests return -1, and errno is set appropriately. Since the value returned
       by  a  successful  PTRACE_PEEK*  request may be -1, the caller must clear errno before the
       call, and then check it afterward to determine whether or not an error occurred.

FEHLER

       EBUSY  (nur i386) Es ist beim Reservieren oder  der  Freigabe  eines  Debug-Registers  ein
              Fehler aufgetreten.

       EFAULT Es  gab  einen  Versuch in einem ungültigen Bereich im Speicher des Verfolgers oder
              des verfolgten Prozesses zu lesen  oder  zu  schreiben,  wahrscheinlich,  weil  der
              Bereich  nicht  abgebildet  war  oder  kein Zugriff möglich war. Unglücklicherweise
              geben unter Linux mehrere Variationen dieser Störung mehr oder weniger  willkürlich
              EIO oder EFAULT zurück.

       EINVAL Es wurde versucht, eine ungültige Option zu setzen.

       EIO    Abfrage  ist  ungültig,  es wurde versucht, in einem ungültigen Bereich im Speicher
              des Verfolgers oder des verfolgten Prozesses zu lesen oder  zu  schreiben,  es  gab
              eine  Verletzung  der  Ausrichtung  an  der  »word«-Größe oder es wurde während des
              Neustarts der Abfrage ein ungültiges Signal angegeben.

       EPERM  Der angegebene Prozess kann nicht verfolgt werden. Dies könnte daher  rühren,  dass
              der  Verfolger über unzureichende Privilegien verfügt (die Fähigkeit CAP_SYS_PTRACE
              wird benötigt); unprivilegierte Prozesse können keine Prozesse verfolgen, denen sie
              keine   Signale   senden   können  oder  die  SUID-/SGID-Programme  ausführen,  was
              naheliegend ist. Alternativ könnte der Prozess bereits verfolgt  werden  oder  (auf
              Kerneln vor 2.6.26) init(8) (PID 1) sein.

       ESRCH  Der angegebene Prozess existiert nicht, wird derzeit nicht vom Aufrufenden verfolgt
              oder ist nicht gestoppt (bei Anfragen,  die  einen  gestoppten  verfolgten  Prozess
              erfordern).

KONFORM ZU

       SVr4, 4.3BSD.

ANMERKUNGEN

       Obwohl  Argumente  für  ptrace()  gemäß  dem  angegebenen Prototypen interpretiert werden,
       deklariert  Glibc  derzeit  ptrace()  als  eine  variable  Funktion  mit  nur  dem  festen
       Anfrage-Argument.  Es wird empfohlen, immer vier Argumente anzugeben, sogar dann, wenn die
       angeforderte Transaktion sie nicht verwendet. Setzen Sie  unbenutzte/ignorierte  Argumente
       auf 0L oder (void *) 0.

       In  Linux-Kerneln  vor  2.6.26  kann  init(8)  den  Prozess  mit der Prozessnummer 1 nicht
       verfolgen.

       Das Layout des Speicherinhalts und des BENUTZERbereichs sind ziemlich  Betriebsystem-  und
       Architekturspezifisch.  Der  mitgelieferte  Versatz  und  die zurückgegebenen Daten passen
       möglicherweise nicht ganz zu der Definition von struct user.

       Die Größe eines »word« wird durch die Betriebsystemvariante festgelegt (z.B.  ist  es  für
       ein 32-Bit-Linux 32 Bit).

       Diese  Seite  dokumentiert  die  Möglichkeit,  wie  der  ptrace()-Aufruf  derzeit in Linux
       arbeitet.  Sein  Verhalten  unterscheidet  sich  auf   anderen   UNIX-Geschmacksrichtungen
       deutlich.  Auf  jeden  Fall  ist  die  Benutzung  von  ptrace() in hohem Grad abhängig vom
       Betriebssystem und der Architektur.

FEHLER

       Auf  Rechnern  mit  2.6  Kernel-Headern  ist  PTRACE_SETOPTIONS  mit  einem  anderen  Wert
       deklariert,   als  auf  einem  für  2.4.  Dies  führt  dazu,  dass  Anwendungen,  die  mit
       2.6-Kernel-Headern kompiliert wurden, bei der Ausführung auf 2.4er Kerneln scheitern. Dies
       kann  durch  Neudefinieren  von PTRACE_SETOPTIONS zu PTRACE_OLDSETOPTIONS umgangen werden,
       wenn dies definiert ist.

       Gruppenstoppbenachrichtigungen werden an der Verfolger gesandt, aber nicht an  den  echten
       Elternprozess. Zuletzt auf 2.6.38.6 bestätigt.

       Falls ein führender Thread einer Gruppe verfolgt und durch den Aufruf von _exit(2) beendet
       wird, wird es für ihn zu einem PTRACE_EVENT_EXIT-Stopp kommen  (falls  angefordert),  aber
       die  nachfolgende  WIFEXITED-Benachrichtigung wird nicht gesandt, bis alle anderen Threads
       beendet sind. Wie oben erklärt, wird der Tod des führenden Prozesses der Gruppe  gemeldet,
       falls  einer  der  anderen  Threads  execve(2) aufruft. Falls der ausgeführte Thread nicht
       durch den Verfolger verfolgt wird, wird der Verfolger  niemals  erfahren,  dass  execve(2)
       auftrat.  Eine  mögliche  Notlösung  ist  ein  PTRACE_DETACH  für den führenden Thread der
       Gruppe, anstatt ihn in diesem Fall neu zu starten. Zuletzt auf 2.6.38.6 bestätigt.

       Ein SIGKILL-Signal kann immer noch einen  PTRACE_EVENT_EXIT-Stopp  vor  dem  tatsächlichen
       Signaltod  verursachen.  Dies könnte in Zukunft geändert werden; SIGKILL ist dazu gedacht,
       Aufgaben immer sofort zu killen, sogar unter Ptrace. Zuletzt auf 2.6.38.6 bestätigt.

       Einige Systemaufrufe kehren mit EINTR zurück, falls ein Signal an den  verfolgten  Prozess
       gesandt,  die Auslieferung aber durch den Verfolger unterdrückt wurde. (Dies ist eine ganz
       typische Transaktion: Sie wird normalerweise von Fehlersuchprogrammen bei  jedem  Anhängen
       durchgeführt, um kein fingiertes SIGSTOP einzuleiten.) Ab Linux 3.2.9 werden die folgenden
       Systemaufrufe  beeinflusst   (diese   Liste   ist   wahrscheinlich   nicht   vollständig):
       epoll_wait(2)  und read(2) von einem inotify(7)-Dateideskriptor. Das übliche Anzeichen für
       diesen Fehler ist, falls Sie einen ruhenden Prozess mit dem Befehl

           strace -p <Prozess-ID>

       anhängen, dass Sie statt der erwarteten einzeilige Ausgabe, wie

           restart_syscall(<... resuming interrupted call ...>_

       oder

           select(6, [5], NULL, [5], NULL_

       ('_' kennzeichnet  die  Cursor-Position)  mehr  als  eine  Zeile  beobachten  können,  zum
       Beispiel:

           clock_gettime(CLOCK_MONOTONIC, {15370, 690928118}) = 0
           epoll_wait(4,_

       Was hier nicht sichtbar ist, ist, dass der Prozess in epoll_wait(2) blockiert wurde, bevor
       strace(1) an ihn angehängt  hat.  Das  Anhängen  verursachte  ein  epoll_wait(2),  um  zum
       User-Space  mit  dem  Fehler  EINTR zurückzukehren. In diesem besonderen Fall reagiert das
       Programm auf EINTR,  indem  die  aktuelle  Zeit  geprüft  und  dann  epoll_wait(2)  erneut
       ausgeführt  wird.  (Programme,  die  keine  derartigen  »verirrten« EINTR-Fehler erwarten,
       können sich bei einem strace(1)-Anhängen in unbeabsichtigter Weise verhalten.)

SIEHE AUCH

       gdb(1), strace(1),  clone(2),  execve(2),  fork(2),  gettid(2),  sigaction(2),  tgkill(2),
       vfork(2), waitpid(2), exec(3), capabilities(7), signal(7)

KOLOPHON

       This  page  is  part  of release 3.54 of the Linux man-pages project. A description of the
       project,    and    information    about    reporting    bugs,    can    be    found     at
       http://www.kernel.org/doc/man-pages/.

ÜBERSETZUNG

       Die  deutsche  Übersetzung  dieser  Handbuchseite wurde von Patrick Rother <krd@gulu.net>,
       Chris Leick <c.leick@vollbio.de> und Helge Kreutzmann <debian@helgefjell.de> 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>.