Windows NTFS文件系统的USN日志是否可以大于它';申报的尺寸是多少?

Windows NTFS文件系统的USN日志是否可以大于它';申报的尺寸是多少?,windows,ntfs,journaling,usn,Windows,Ntfs,Journaling,Usn,各位程序员好 我试图使用WinIoCtl函数转储NTFS分区的USN日志内容。我有一个*USN_JOURNAL_DATA*结构,它告诉我它的最大大小是512 MB。我已经将它与fsutil对它所说的进行了比较,它的值是相同的 现在,我必须将每个条目读入*USN_记录*结构。我在for循环中这样做,该循环从0开始,以4096(集群大小)的增量到达日志的最大大小。 我在相同大小的缓冲区中读取每个4096字节,并从中读取所有USN_记录结构 一切都很顺利,文件名正确,时间戳,原因,一切,除了我似乎丢失

各位程序员好

我试图使用WinIoCtl函数转储NTFS分区的USN日志内容。我有一个*USN_JOURNAL_DATA*结构,它告诉我它的最大大小是512 MB。我已经将它与fsutil对它所说的进行了比较,它的值是相同的

现在,我必须将每个条目读入*USN_记录*结构。我在for循环中这样做,该循环从0开始,以4096(集群大小)的增量到达日志的最大大小。 我在相同大小的缓冲区中读取每个4096字节,并从中读取所有USN_记录结构

一切都很顺利,文件名正确,时间戳,原因,一切,除了我似乎丢失了一些最近的记录。我在分区上创建一个新文件,在其中写入一些内容,然后删除该文件。我再次运行应用程序,但记录没有出现。我发现只有当我继续阅读超过日记的最大尺寸时,记录才会出现。这怎么可能

目前,我正在从日志的数据开始读取到最大大小+分配增量(两者都是存储在*USN_Journal_data*结构中的值),我认为这是不正确的,我很难找到与此相关的完整信息

有人能解释一下吗?USN日志周围是否有类似于MFT工作方式的缓冲区(即当其他文件需要磁盘空间时,缓冲区大小减半)


我做错了什么?

这是预期的行为:

最大尺寸

更改日志的目标最大大小,以字节为单位更改日志可能会增长到大于此值,但随后会在下一个NTFS文件系统检查点将其截断到小于此值

不要试图预先确定大小,而是循环直到到达数据的末尾

如果您使用的是
FSCTL\u ENUM\u USN\u数据
控制代码,则当
DeviceIoControl
中的错误代码为
error\u HANDLE\u EOF
时,您已到达数据末尾


如果您使用的是
FSCTL\u READ\u USN\u JOURNAL
控制代码,则当驱动程序返回的下一个USN(输出缓冲区开头的DWORDLONG)是您请求的USN(输入缓冲区中
StartUsn
的值)时,您已到达数据的末尾。您需要将输入参数
BytesToWaitFor
设置为零,否则驱动程序将等待指定数量的新数据添加到日志中。

谢谢。没有想到:)实际上,DeviceIoControl并没有返回LSTATUS,它返回一个BOOL,指示它是否失败。但是我一直循环,直到GetLastError()返回ERROR\u HANDLE\u EOF,但它没有返回该代码,它只是继续循环并显示USN日志的最新更改。有点像它会一遍又一遍地读取最后的X字节。因此,要停止循环,最终必须循环,直到返回的缓冲区不变,但这不能保证我们读取整个USN日志。循环直到偏移量达到MaximumSize+AllocationDelta为止似乎是可行的。您使用的是什么IO控制代码?我的代码使用
FSCTL_ENUM_USN_DATA
,在到达MFT末尾时,肯定会收到错误处理EOF。请参阅(注意,在处理Windows API时,“F返回错误代码X”通常是“F返回FALSE,GetLastError()返回错误代码X”的缩写;这只是理所当然的事情之一)。谢谢你的更新。我不断更新所请求的USN,以便获得所有USN条目,但我使用缓冲区中的USN记录号对其进行更新,因此将一次又一次地请求最后一个条目。我也未能区分FSCTL_READ_USN_日志和FSCTL_ENUM_USN_数据。谢谢你帮我澄清这一点。:)