获得有关进程终止的通知

Get notified about process termination

我正在尝试使用 NETLINK 和 CN_IDX_PROC 来监控我的进程。这可行,但需要以 root 权限启动监视进程。

我试图通过在我的监控可执行文件(包括 CAP_AUDIT_READ、CAP_SYS_ADMIN、CAP_SYS_PTRACE 和 CAP_IPC_OWNER 上设置文件系统功能来修复它,但它没有用,bind() 仍然失败,说“不允许操作”,除非使用 sudo 开始。

有没有办法让非根用户按照我想要的方式使用 netlink 连接器套接字?

如果不是,是否有任何其他可靠的方法在其他(非子进程,运行 在不同用户帐户下)进程终止时得到通知?我不想投票:它是嵌入式软件,我没有太多资源,我想尽快得到通知。我特别想在目标进程异常终止时得到通知,例如有分段错误,所以我不能依赖目标进程的合作。

在 Windows 我只是在目标进程中创建并锁定一个命名的互斥量,并让监视进程在其上休眠,保证在所有者进程死亡后立即释放互斥量。 Linux有没有类似的IPC机制?

在其中使用 pthread 互斥体实现了命名共享内存部分的解决方法。

Funfact:当由于所有者进程终止而强制释放互斥锁时,其他进程的 pthread_mutex_lock returns EOWNERDEAD 代码,但是此后互斥锁不再可用, 随后 pthread_mutex_lock 在该互斥量上 return 131 = EOTHER 错误代码。幸运的是,我只同步了 2 个进程,所以我可以在同一个共享内存部分重新创建互斥锁。

复制单个 WaitForSingleObject Win32 的代码量惊人 API :-(

因此,您希望收到有关进程终止的通知,例如运行 一些程序 foo.

顺便说一句,如果该进程运行良好,您可以使用 atexit(3) inside the source code of foo. Then, if that program exits correctly (by calling exit(3) explicitly, or by returning from main; the crt0 is calling exit(3) in such case just after main returned), the registered routine is running when you want. But that foo process can sadly be terminated by some signal(7) (e.g. a segmentation fault, or some external kill(1) command, etc etc...), then of course _exit(2) is not happening (and neither is exit(3) ....)。

因此编写一个简单的包装程序(例如 wrapfoo),其中 fork(2)-s then execve(2)-s foo in the child, and waitpid(2) in the parent. Then your wrapfoo is always notified of the end of foo (including when foo was terminated by some signal). It behaves as if it was a specialized "shell" to run foo (this is just for the explanation here, wrapfoo is not really a Unix shell)。

(当然,你不希望进程运行 wrapfoo自己终止)

wrapfoo 程序的编码非常简单。你应该期望它是正确的。你可以(小心地)使用 setuid techniques to have them using different users (if you need that). Beware that setuid tricks are difficult and without care can open a security hole.

在某些情况下,您可能会将 wrapfoo 的 C 源代码与 foo 的代码合并,但大多数时候您不想这样做(separation of concerns 原则)。特别是如果你使用危险的 setuid 技术,你希望你的 wrapfoo.c 尽可能简单(并且能够证明它像你想要的那样工作)。

阅读一些关于 Linux 编程的好书,例如下载旧的 Advanced Linux Programming (also here; it is legally freely downloadable) or something newer. setuid techiques and all the subtilities behind fork(2), execve(2), waitpid(2) ... are difficult to explain (so I won't even try here). See also credentials(7).

也许你可以使用 fifo(7), use some advisory locking (e.g. flock(2) or lockf(3)...);当进程终止时,内核也会释放它们。