NtQueryDirectoryFileEx 函数 (ntifs.h)
NtQueryDirectoryFileEx 例程返回有关给定文件句柄指定的目录中文件的各种信息。
语法
__kernel_entry NTSYSCALLAPI NTSTATUS NtQueryDirectoryFileEx(
[in] HANDLE FileHandle,
[in, optional] HANDLE Event,
[in, optional] PIO_APC_ROUTINE ApcRoutine,
[in, optional] PVOID ApcContext,
[out] PIO_STATUS_BLOCK IoStatusBlock,
[out] PVOID FileInformation,
[in] ULONG Length,
FILE_INFORMATION_CLASS FileInformationClass,
[in] ULONG QueryFlags,
[in, optional] PUNICODE_STRING FileName
);
参数
[in] FileHandle
NtCreateFile 或 NtOpenFile 返回的文件对象的句柄,该对象表示要为其请求信息的目录。 如果调用方为 事件 或 ApcRoutine指定非 NULL 值,则必须为异步 I/O 打开文件对象。
[in, optional] Event
调用方创建的事件的可选句柄。 如果提供了此参数,则调用方将进入等待状态,直到请求的作完成并且给定的事件设置为 Signaled 状态。 此参数是可选的,可以是 NULL。 如果调用方将等待 FileHandle 设置为 Signaled 状态,则该参数必须为 NULL。
[in, optional] ApcRoutine
请求的作完成时要调用的可选调用方提供的 APC 例程的地址。 此参数是可选的,可以是 NULL。 如果存在与文件对象关联的 I/O 完成对象,此参数必须为 NULL。
[in, optional] ApcContext
如果调用方提供 APC 或 I/O 完成对象与文件对象关联,则为调用方确定的上下文区域的可选指针。 作完成后,如果指定了上下文,或作为 I/O 管理器发布到关联的 I/O 完成对象的完成消息的一部分,则此上下文将传递到 APC。
此参数是可选的,可以是 NULL。 如果 ApcRoutine 为 NULL,并且没有与文件对象关联的 I/O 完成对象,则该参数必须为 NULL。
[out] IoStatusBlock
指向 IO_STATUS_BLOCK 结构的指针,该结构接收最终完成状态和有关作的信息。 对于返回数据的成功调用,在结构的 信息 成员中返回写入 FileInformation 缓冲区的字节数。
[out] FileInformation
指向接收有关文件的所需信息的输出缓冲区的指针。 缓冲区中返回的信息的结构由 FileInformationClass 参数定义。
[in] Length
FileInformation指向的缓冲区的大小(以字节为单位)。 调用方应根据给定 FileInformationClass设置此参数。
FileInformationClass
要返回的有关目录中文件的信息类型。 要返回的有关目录中文件的信息类型。 FileInformationClass 可以是以下 FILE_INFORMATION_CLASS 值之一。
价值 | 意义 |
---|---|
FileDirectoryInformation (1) | 返回每个文件的 FILE_DIRECTORY_INFORMATION 结构。 |
FileFullDirectoryInformation (2) | 返回每个文件的 FILE_FULL_DIR_INFORMATION 结构。 |
FileBothDirectoryInformation (3) | 返回每个文件的 FILE_BOTH_DIR_INFORMATION 结构。 |
FileNamesInformation (12) | 返回每个文件的 FILE_NAMES_INFORMATION 结构。 |
FileObjectIdInformation (29) | 为卷上具有对象 ID 的每个文件返回 FILE_OBJECTID_INFORMATION 结构。 此信息类仅适用于 NTFS 卷上的特殊目录“\$Extend\$ObjId:$O:$INDEX_ALLOCATION”。 |
FileQuotaInformation (32) | 为应用配额的卷上的每个用户返回单个 FILE_QUOTA_INFORMATION 结构。 此信息类仅适用于 NTFS 卷上的特殊目录“\$Extend\$Quota:$Q:$INDEX_ALLOCATION”。 |
FileReparsePointInformation (33) | 为卷上具有重新分析点的每个文件返回单个 FILE_REPARSE_POINT_INFORMATION 结构。 此信息类仅适用于 NTFS 和 ReFS 卷上的特殊目录“\$Extend\$Reparse:$R:$INDEX_ALLOCATION”。 |
FileIdBothDirectoryInformation (37) | 返回每个文件的 FILE_ID_BOTH_DIR_INFORMATION 结构。 |
FileIdFullDirectoryInformation (38) | 返回每个文件的 FILE_ID_FULL_DIR_INFORMATION 结构。 |
FileIdGlobalTxDirectoryInformation (50) | 返回每个文件的 FILE_ID_GLOBAL_TX_DIR_INFORMATION 结构。 |
FileIdExtdDirectoryInformation (60) | 返回每个文件的 FILE_ID_EXTD_DIR_INFORMATION 结构。 |
FileIdExtdBothDirectoryInformation (63) | 返回每个文件的 FILE_ID_EXTD_BOTH_DIR_INFORMATION 结构。 |
[in] QueryFlags
SL_QUERY_DIRECTORY_MASK中包含的一个或多个标志。 下表中指定了可能的值。
价值 | 意义 |
---|---|
SL_RESTART_SCAN(0x00000001) | 扫描将从目录中的第一个条目开始。 如果未设置此标志,扫描将从最后一个查询结束的位置恢复。 |
SL_RETURN_SINGLE_ENTRY(0x00000002) | 通常,返回缓冲区打包了任意数量的匹配目录条目。 如果设置了此标志,则文件系统一次只返回一个目录条目。 这会使作效率更低。 |
SL_INDEX_SPECIFIED (0x00000004) | 扫描应从目录中的指定索引位置开始。 仅当生成自己的IRP_MJ_DIRECTORY_CONTROL IRP 时,才能设置此标志;索引在 IRP 中指定。 指定位置的方式因文件系统而异。 |
SL_RETURN_ON_DISK_ENTRIES_ONLY(0x00000008) | 执行目录虚拟化或实时扩展的任何文件系统筛选器都应将请求传递到文件系统,并返回当前位于磁盘上的条目。 并非所有文件系统都支持此标志。 |
SL_NO_CURSOR_UPDATE_QUERY(0x00000010) | 文件系统维护每个 FileObject 目录游标信息。 当多个线程使用相同的 FileObject 执行查询时,将单线程访问 per-FileObject 结构,以防止游标状态损坏。 此标志告知文件系统不要更新每个 FileObject 游标状态信息,从而允许多个线程使用相同的句柄并行查询。 它的行为就像在每个调用中指定SL_RESTART_SCAN一样。 如果下一次调用中提供了通配符模式,则作将不会选取最后一个查询结束的位置。 这允许真正的异步目录查询支持。 如果在 TxF 事务中使用此标志,作将失败。 并非所有文件系统都支持此标志。 |
[in, optional] FileName
一个可选指针,指向调用方分配的 Unicode 字符串的可选指针,该字符串包含文件的名称(或使用多个文件(如果使用通配符),FileHandle指定的目录中。 此参数是可选的:
- 如果 FileName 不为 NULL,则目录扫描中仅包含名称与 FileName 字符串匹配的文件。
- 如果 FileName 为 NULL:
- 如果未在 QueryFlags中设置SL_RETURN_SINGLE_ENTRY,则包括所有文件。
- 如果设置了SL_RETURN_SINGLE_ENTRY,则仅包含一个文件。
FileName 用作搜索表达式,并在首次调用给定句柄时捕获 NtQueryDirectoryFileEx。 对 NtQueryDirectoryFileEx 的后续调用将使用第一次调用中设置的搜索表达式。 将忽略传递给后续调用的 FileName 参数。
返回值
NtQueryDirectoryFileEx 返回STATUS_SUCCESS或适当的错误状态。 可以返回的错误状态值集特定于文件系统。 NtQueryDirectoryFileEx 还返回实际写入到 IoStatusBlock信息 成员中给定 FileInformation 缓冲区的字节数。 一些可能的错误代码和原因可能是:
返回代码 | 意义 |
---|---|
STATUS_BUFFER_OVERFLOW | 输出缓冲区不够大,无法返回完整文件名。 |
STATUS_BUFFER_TOO_SMALL | 输出缓冲区不够大,至少对于由 fileInformationClass 标识的基本结构。 |
STATUS_INVALID_INFO_CLASS | 指定了无效 FileInformationClass,或者信息类仅对特殊条件有效(例如,仅对特殊目录有效)。 |
STATUS_INVALID_PARAMETER | 其中一个参数对文件系统无效。 |
言论
NtQueryDirectoryFileEx 返回 FileHandle所表示目录中的文件的相关信息。
如果提供,则 FileName 确定目录扫描中包括的条目,以扫描给定 FileHandle的所有后续调用 NtQueryDirectoryFileEx。
如果至少有一个匹配项,NtQueryDirectoryFileEx 为每个条目创建 FILE_XXX_INFORMATION 结构,并将其存储在缓冲区中。
假设找到至少一个匹配的目录项,则返回信息的条目数是以下 最小:
- 如果 QueryFlags 中设置了SL_RETURN_SINGLE_ENTRY,FileName 为 NULL,则为一个条目。
- 如果 FileName 不是 NULL,则与 FileName 字符串匹配的条目数。 如果字符串不包含通配符,则最多可以有一个匹配项。
- 其信息适合指定缓冲区的条目数。
- 目录中包含的条目数。
在首次调用 NtQueryDirectoryFileEx时,如果为找到的第一个条目创建的结构太大而无法容纳到输出缓冲区中,此例程将执行以下作:
- 将结构的固定部分写入 FileInformation的输出缓冲区。 固定部分包含除最终 FileName 字符串以外的所有字段。 在第一次调用(而不是后续调用时)时,I/O 系统可确保缓冲区足够大,足以容纳相应 FILE_XXX_INFORMATION 结构的固定部分。
- 写入输出缓冲区,FileName 字符串的很大一样适合。
- 返回适当的状态值,例如STATUS_BUFFER_OVERFLOW。
每次调用时,NtQueryDirectoryFileEx 返回多达 FILE_XXX_INFORMATION 结构(每个目录条目一个),就像 FileInformation指向的缓冲区中一样:
- 在第一次调用中,仅当输出缓冲区包含至少一个完整结构时,NtQueryDirectoryFileEx 才会返回STATUS_SUCCESS。
- 在后续调用中,如果输出缓冲区不包含任何结构,NtQueryDirectoryFileEx 将返回STATUS_SUCCESS,但设置 IoStatusBlock->Information = 0 以通知调用方此条件。 在这种情况下,调用方应分配更大的缓冲区,并再次调用 NtQueryDirectoryFileEx。 不会报告任何剩余条目的相关信息。 因此,除了上面列出的只返回一个条目的情况下,NtQueryDirectoryFileEx 必须至少调用两次才能枚举整个目录的内容。
调用 NtQueryDirectoryFileEx时,你可能会看到对与 NtQueryDirectoryFileEx 调用并行发生的目录所做的更改。 此行为取决于基础文件系统的实现。
NtQueryDirectoryFileEx 的最终调用 返回空输出缓冲区,并报告相应的状态值,例如STATUS_NO_MORE_FILES。
如果在同一目录中多次调用 NtQueryDirectoryFileEx,而其他一些作会更改该目录的内容,则任何更改都可能会或可能不会看到,具体取决于作的时间。
NtQueryDirectoryFileEx 在文件系统不支持的 FILE_XXX_INFORMATION 结构的任何成员中返回零。
NtQueryDirectoryFileEx 的调用方必须在 IRQL = PASSIVE_LEVEL上运行,启用了特殊内核 APC。
有关其他文件信息查询例程的信息,请参阅 文件对象。
注意
如果在内核模式下调用 NtQueryDirectoryFileEx 函数,则应使用名称“ZwQueryDirectoryFileEx”而不是“NtQueryDirectoryFileEx”。
对于内核模式驱动程序的调用,NtXxx 和 ZwXxx 版本的 Windows 本机系统服务例程的行为方式可能以不同的方式处理和解释输入参数。 有关 NtXxx 与 ZwXxx 例程之间的关系的详细信息,请参阅 使用 Nt 和 Zw 版本的本机系统服务例程。
要求
要求 | 价值 |
---|---|
最低支持的客户端 | Windows 10 版本 1709 |
标头 | ntifs.h |
库 | NtosKrnl.lib |
DLL | NtosKrnl.exe |
IRQL | PASSIVE_LEVEL(请参阅“备注”部分) |