Windows 通过特定进程从事件跟踪(ETW)会话获取创建/修改/删除的文件

Windows 通过特定进程从事件跟踪(ETW)会话获取创建/修改/删除的文件,windows,events,etl,trace,etw,Windows,Events,Etl,Trace,Etw,我一直在寻找一种解决方案,通过特定流程从事件跟踪(ETW)会话中获取所有创建/修改和删除的文件(我将处理etl文件中的数据,而不是实时会话中的数据) 显然,完成这项工作的最简单解决方案是从类中获取FileCreate和FileDelete事件,并将它们映射到相应的事件。但是,此解决方案不适用于我,因为我没有收到相应FileDelete事件的任何DiskIo_TypeGroup1事件,因此我无法获取进程ID。此外,并非所有FileCreate事件都有关联的DiskIo_TypeGroup1事件(我

我一直在寻找一种解决方案,通过特定流程从事件跟踪(ETW)会话中获取所有创建/修改和删除的文件(我将处理etl文件中的数据,而不是实时会话中的数据)

显然,完成这项工作的最简单解决方案是从类中获取FileCreate和FileDelete事件,并将它们映射到相应的事件。但是,此解决方案不适用于我,因为我没有收到相应FileDelete事件的任何DiskIo_TypeGroup1事件,因此我无法获取进程ID。此外,并非所有FileCreate事件都有关联的DiskIo_TypeGroup1事件(我认为这种情况会发生在创建的空文件中,或者只发生在打开的文件中)

注意:我需要DiskIo_TypeGroup1映射,因为FileIo_Name事件没有填充ThreadId和ProcessId成员-它们被设置为(ULONG)-1。此外,在不知道“文件写入大小”的情况下,我无法确定刚刚打开或修改了哪些文件.DiskIo_TypeGroup1也没有填充ThreadId和ProcessId(在较新操作系统的事件头中)成员,但它有IssuingThreadId结构成员,我可以从中获得到Thread_TypeGroup1类事件的ProcessId映射

因此,我研究了FileIo\u Create类如何帮助我,并指出我可以获得CreateOptions成员,该成员可以具有以下标志:(FILE\u替换,FILE\u创建,FILE\u打开,FILE\u打开,IF,FILE\u覆盖,FILE\u覆盖,IF)。但最初的问题仍然存在。我如何检查文件是否是从头创建的,而不是刚刚打开的(例如,在文件被替换的情况下)

也许我可以使用FileIo\u ReadWrite类来获取写入事件。就像使用DiskIo\u TypeGroup1类一样。因此,如果某个文件被写入,那么我可以假设该文件是创建或修改的吗

要查找已删除的文件,我认为FileIo\u Info类和Delete事件是解决方案。我可以接收Delete事件并将它们映射到FileIo\u Name以获取文件名

注意:文件IO_创建文件IO_信息文件IO_读写包含有关进程id的信息


我的假设正确吗?我的问题的最佳解决方案是什么?

我将分享我实施的解决方案,如下所示:

  • 创建的文件:

    • 我已将所有FileIo_Create事件存储为挂起的创建操作,并等待接收关联的FileIo_OpEnd以确定文件是从ExtraInfo结构成员打开、创建、覆盖还是替换的
  • 修改的文件:

    • 对于FileIo\u ReadWrite中的每个写入事件,以及FileIo\u-SimpleOp中的InfoClass->FileEndOfFileInformation和InfoClass->FileValidDataLengthInformation中的每个SetInfo事件,我都将文件标记为脏文件。最后,对于FileIo\u-SimpleOp中的清理事件,验证文件是否标记为脏文件并存储为脏文件修改
  • 已删除的文件:

    • 如果使用FileIo\u Create中的CreateOptions->FILE\u DELETE\u ON\u CLOSE标志打开文件,或者如果出现FileIo\u Info中的删除事件,我将文件标记为已删除。最后,在FileIo\u SimpleOp中的清理事件中,文件存储为已删除

  • 另外,进程id和文件名是从文件IO_Create事件中获得的,更准确地说,是从OpenPath结构成员和ProcessId事件头成员中获得的。

    我将分享我的实现解决方案,如下所示:

  • 创建的文件:

    • 我已将所有FileIo_Create事件存储为挂起的创建操作,并等待接收关联的FileIo_OpEnd以确定文件是从ExtraInfo结构成员打开、创建、覆盖还是替换的
  • 修改的文件:

    • 对于FileIo\u ReadWrite中的每个写入事件,以及FileIo\u-SimpleOp中的InfoClass->FileEndOfFileInformation和InfoClass->FileValidDataLengthInformation中的每个SetInfo事件,我都将文件标记为脏文件。最后,对于FileIo\u-SimpleOp中的清理事件,验证文件是否标记为脏文件并存储为脏文件修改
  • 已删除的文件:

    • 如果使用FileIo\u Create中的CreateOptions->FILE\u DELETE\u ON\u CLOSE标志打开文件,或者如果出现FileIo\u Info中的删除事件,我将文件标记为已删除。最后,在FileIo\u SimpleOp中的清理事件中,文件存储为已删除

  • 进程id和文件名也是从创建的事件中获得的,更准确地说是从OpenPath结构成员和ProcessId事件头成员中获得的。

    您使用哪种语言?对于.net,您可以使用TraceeEvent()为了解析ETL,这里有关于KelnReraceEnviaPrServer类中所有Fielo和DISKIO事件的事件。HI @ MigICANDAN1981,我使用C++,但是已经查看了实现,不幸的是,这还没有解决我的问题,因为TraceEnter只对事件进行了解析和格式化,没有任何高级别的处理,比如我的例子。从特定进程中推断创建/修改/删除的文件。感谢您的评论。高级是什么意思?任何事件都有一个processid,processname属性Y是的,几乎所有事件都有一个processid,除了FileIo_名称(或至少我无法获得它们)和其他一些事件,如(请参阅底部的备注)。另一个相关问题可以在这里找到:我还使用提取ETL以查看结果。
    使用(_source=new ETWTraceEventSource(dataFi