检测进程使用/修改/创建/删除哪些文件的最佳方法是什么?

时间:2015-09-22 14:04:37

标签: c linux macos strace dtruss

我想编写一个软件,在执行进程(及其子进程)期间检测所有已使用/创建/修改/删除的文件。该进程尚未运行 - 用户提供了一个命令行,稍后将通过bash对其进行子处理,因此我们可以在执行前后执行操作,并控制运行命令的环境。

到目前为止,我已经考虑过四种可能有用的方法:

  • 解析命令行以识别提到的文件和目录。假设使用了明确提到的所有文件。检查创建/删除文件之前/之后的目录。 MD5现有文件之前/之后可以看到任何修改过的文件。这适用于所有操作系统和环境,但显然有严重的局限性(当命令为" ./ script.sh"时不起作用)
  • 通过另一个进程运行该进程,例如strace(用于OSX的dtruss,以及有等效的Windows程序),它监听系统调用。解析输出文件以查找使用/修改/删除/创建的文件。优点是它比MD5方法更敏感并且可以处理script.sh。缺点是它的操作系统特定(即使正在运行的进程没有,因此dtruss需要root权限 - 工具的输出都不同)。如果有大量的读/写操作,也可以创建巨大的日志文件,并且肯定会减慢速度。
  • 将与上述类似的内容集成到内核中。显然仍然是特定于操作系统,但至少现在我们正在做主,为所有操作系统创建通用输出格式。不会创建巨大的日志文件,甚至可以在进程请求对文件的第一次read()之后停止将syscall挂钩到read()。我认为这是inotify工具正在做的事情,但我根本不熟悉它,也没有内核编程!
  • 使用LD_PRELOAD技巧(在OSX上称为DYLD_INSERT_LIBRARIES,不确定它是否存在于Windows中)运行该进程,该进程基本上覆盖了使用我们自己的open()版本的进程对open()的任何调用,该版本记录了我们的&#39重新开放。写入,阅读等也是如此。它非常简单,并且非常高效,因为您基本上是在教导该过程进行自我记录。缺点是它只适用于动态链接的进程,我不知道动态/静态链接程序的普遍性。我甚至不知道在执行之前是否有可能判断进程是动态链接还是静态链接(默认情况下使用此方法,但如果不可能则返回性能较低的方法)。

我需要帮助选择最佳路径。我已经实现了第一种方法,因为它很简单并且给了我一种方法来处理日志记录后端(http://ac.gt/log),但实际上我需要升级到其他方法之一。你的建议是非常宝贵的:)

1 个答案:

答案 0 :(得分:2)

查看“strace”的源代码(及其-f跟踪子代)。它基本上是你想要做的。它捕获进程(或其子进程)的所有系统调用,以便您可以执行“open”等操作。

以下链接提供了一些使用ptrace系统调用实现自己的strace的示例:

https://blog.nelhage.com/2010/08/write-yourself-an-strace-in-70-lines-of-code/