Ich bin auf ein seltsames Problem gestoßen, bei dem ein ps -o args -p <pid>
Befehl gelegentlich den betreffenden Prozess nicht findet, obwohl er definitiv auf dem betreffenden Server ausgeführt wird. Bei den fraglichen Prozessen handelt es sich um lang laufende Wrapper-Skripte, mit denen einige Java-Apps gestartet werden.
Das "in the wild" -Ereignis des Problems scheint immer früh am Morgen aufzutreten, daher gibt es Hinweise darauf, dass es mit der Festplattenlast auf dem betreffenden Server zusammenhängt, da sie dann ziemlich stark geladen sind, aber durch Ausführen des ps
Eingangs Frage in einer engen Schleife, ich kann schließlich das Problem replizieren - einmal alle paar hundert oder so läuft, erhalte ich eine Fehlermeldung.
Durch Ausführen des folgenden Bash-Skripts habe ich es geschafft, eine Strace-Ausgabe sowohl für einen fehlgeschlagenen als auch für einen erfolgreichen Lauf zu generieren:
while [ $? == 0 ] ; do strace -o fail.out ps -o args -p <pid> >/dev/null ; done ; strace -o good.out ps -o args -p <pid>
Wenn ich die Ausgabe von fail.out
und vergleiche good.out
, kann ich sehen, dass der getdents
Systemaufruf auf dem Lauf, der irgendwie fehlschlägt, eine viel kleinere Anzahl als die tatsächliche Anzahl von Prozessen auf dem System zurückgibt (in der Größenordnung von ~ 500 im Vergleich zu ~ 1100).
grep getdents good.out
getdents(5, /* 1174 entries */, 32768) = 32760
getdents(5, /* 31 entries */, 32768) = 992
getdents(5, /* 0 entries */, 32768) = 0
grep getdents fail.out
getdents(5, /* 673 entries */, 32768) = 16728
getdents(5, /* 0 entries */, 32768) = 0
... und diese kürzere Liste enthält nicht die tatsächlich fragliche PID, daher wird sie nicht gefunden.
Sie können diesen Abschnitt ignorieren. Die ENOTTY-Fehler werden durch den Kommentar von dave_thompson unten erklärt und stehen in keinem Zusammenhang
Darüber hinaus werden bei dem fehlgeschlagenen Lauf einige
ENOTTY
Fehler angezeigt, die im erfolgreichen Lauf nicht angezeigt werden. Nahe dem Anfang der Ausgabe sehe ichioctl (1, TIOCGWINSZ, 0x7fffe19db310) = -1 ENOTTY (unangemessenes ioctl für Gerät) ioctl (1, TCGETS, 0x7fffe19db280) = -1 ENOTTY (unangemessenes ioctl für Gerät)
Und am Ende sehe ich eine Single
ioctl (1, TCGETS, 0x7fffe19db0d0) = -1 ENOTTY (Unangemessenes ioctl für Gerät)
Der Fehler
ioctl
am Ende tritt direkt vor derps
Rückgabe auf, aber er tritt auf, nachdem derps
bereits eine leere Ergebnismenge gedruckt hat, sodass ich nicht sicher bin, ob sie zusammenhängen. Ich weiß, dass sie in allen fehlgeschlagenen Strace-Ausgaben, die ich habe, konsistent sind, aber nicht in den erfolgreichen erscheinen.
Ich habe absolut keine Ahnung, warum ich getdents
gelegentlich nicht die vollständige Liste der Prozesse finden würde, und jetzt bin ich an dem Punkt angelangt, an dem ich nur noch ein Pflaster auf das Ganze legen werde, indem ich das Steuerungsskript ändere, das das Wrapper-Skript überprüft in Frage, das ps
zweite Mal anzurufen, wenn das erste fehlschlägt, aber ich wäre interessiert zu wissen, ob jemand irgendwelche Ideen hat, was hier los ist.
Auf dem betreffenden System wird Kernel 4.16.13-1.el7.elrepo.x86_64 unter CentOS 7 und Procps-ng Version 3.3.10-17.el7_5.2.x86_64 ausgeführt
>/dev/null
den Aufruf 'fehlgeschlagen' (in der Schleife), aber nicht den Aufruf 'gut', daher die ENOTTY auf fd 1.