Lösung 1:
Das klingt nach einem perfekten Job für auditd. Sobald Sie auditd ausgeführt haben, einen Standarddienst auf modernen RedHat-basierten Systemen, können Sie eine Regel erstellen, die genau das tut, was Sie wollen, indem Sie
ausführen
auditctl -a task,always -F uid=0
Wenn wir diese Befehlsregel aufschlüsseln und die Manpage übermäßig nutzen, finden wir Folgendes:
-a list,action task Add a rule to the per task list. This rule list is used only at the time a task is created -- when fork() or clone() are called by the parent task. When using this list, you should only use fields that are known at task creation time, such as the uid, gid, etc. always Allocate an audit context, always fill it in at syscall entry time, and always write out a record at syscall exit time.
Schreiben Sie also immer einen Datensatz für diese Aktion, wenn ein Fork- oder Clone-Systemaufruf beendet wird.
Die letzte Option kann man sich als Filterstring vorstellen, in unserem Fall -F uid=0
beschränkt uns einfach auf Fälle, in denen die UID des Prozesseigentümers 0 ist.
Beachten Sie, dass diese Regel zur Laufzeit ausgeführt werden kann, indem Sie sicherstellen, dass auditd richtig konfiguriert ist, und die Regel hinzufügen
-a task,always -F uid=0
in die relevante Datei für Ihre Distribution, höchstwahrscheinlich /etc/audit/audit.rules
Denken Sie nur daran, dass dies verdammt laut sein wird und wer auch immer Ihre Log-Überprüfungen durchführt, muss darauf vorbereitet sein.
Lösung 2:
Ich glaube nicht, dass es eine saubere Möglichkeit gibt, dies zu tun, ohne Ihren Kernel mit CONFIG_PROC_EVENTS und / oder CONFIG_KPROBES neu zu kompilieren (obwohl ich gerne wissen würde, ob es eine Möglichkeit gibt, also habe ich Ihre Frage positiv bewertet).
Ich hatte eine Idee, iwatch/inotify für die Verzeichniserstellung innerhalb von /proc zu verwenden, aber es schien nicht zu funktionieren, auditctl auch nicht. Es sieht so aus, als ob Ihre beste Wahl, obwohl schmutzig, darin besteht, ps zur Abwechslung von einem Skript kontinuierlich zu analysieren. Der folgende Perl-Code würde dies tun, obwohl er dazu neigt, einige zu übersehen, und ps
ignoriert (wie es sich sonst selbst auslösen würde):
perl -e 'my %pids; while(1) { my @pids = `ps -U root -u root`; foreach (@pids) { next if /ps$/; ($pid) = /^\s*(\d+)\D/; if (!$pids{$pid}) { $pids{$pid}++; print "Process $pid created (" . `cat /proc/$pid/cmdline` . ")\n"; } } }