为了验证我想使用的第三方二进制分布式软件的行为,我正在实现一个内核模块,其目标是跟踪该软件产生和终止的每个子节点。
目标二进制文件是 Golang 生成的二进制文件,它是多线程的。我编写的内核模块在内核函数_do_fork()和 do_exit()上安装了钩子,以跟踪该二进制文件产生和终止的每个进程/线程。
LKM 或多或少有效。
然而,在某些情况下,我有一个我无法解释的场景。似乎一个进程/线程可以在不通过do_exit()的情况下终止。
我通过printk()收集的证据显示了进程的创建,但并不表示进程的终止。
我知道printk()可能会很慢,而且我也知道在这种情况下消息可能会丢失。
为了防止由于控制台速度慢而导致消息丢失(对于这个特定的应用程序,使用串行 tty 115200),我尝试实现一个更快的控制台,并且使用netconsole收集了消息。
所描述的设置似乎证实了一个进程可以在不通过do_exit()函数的情况下终止。
但是因为我不确定我的消息不会在printk()基础架构上丢失,所以我决定重复相同的测试,但将printk()替换为ftrace_printk(),这应该是printk()的更精简的替代方案。
还是一样的结果,偶尔我看到进程没有通过do_exit(),并且验证PID当前是否正在运行,我不得不面对它没有运行的事实。
另请注意,我将钩子放在do_exit()内核函数中作为第一条指令,以确保函数流不会在被调用函数内终止。
我的问题如下:
Linux 进程可以在其流程不通过do_exit()函数的情况下终止吗?
如果是这样,有人可以告诉我这种情况可能是什么吗?