Прежде всего давайте посмотрим, как FindFirstFileExW
использует первый параметр lpFileName
- это не окончательный, а именно путь к файлу, который использовался для открытия.api - это разбор и разбиение этой строки.он ищет последнюю косую черту \
в этой строке и разделяет ее на 2 строки.затем это первая часть lpFileName
(до последней обратной косой черты), если она используется как путь к папке, которую система пытается открыть с доступом FILE_READ_DATA | SYNCHRONIZE
.и вторая часть lpFileName
используется (после переноса в UNICODE_STRING
) при вызове NtQueryDirectoryFile
вместо FileName
параметр - Необязательный указатель на выделенную вызывающей стороной строку Unicode, содержащую имяфайла (или нескольких файлов, если используются символы подстановки) в каталоге, указанном FileHandle.
, например, если вы вызываете FindFirstFileExW(L"C:\\TEMP\\Dir1\\Dir2", ..)
, то C:\TEMP\Dir1\Dir2
разделяется на C:\TEMP\Dir1
и Dir2
,и система пытается открыть C:\TEMP\Dir1
(и получил здесь доступ запрещен), а затем (если открыто нормально) будет искать Dir2
(точно) файл в папке - не большой смысл вообще - обычно мы используем символы подстановки, например,C:\TEMP\Dir1\*
.
напротив GetFileAttributesEx
используется lpFileName
в качестве точного имени файла.
, поэтому при вызове
FindFirstFileExW(L"C:\\TEMP\\Dir1\\Dir2", ..);
GetFileAttributesEx(L"C:\\TEMP\\Dir1\\Dir2", ..);
вы тестируете 2 разных папок:
C:\TEMP\Dir1
(для 1 строки) и C:\TEMP\Dir1\Dir2
(для второй строки) - неудивительно, что результаты доступа могут отличаться.во-вторых - этот API использует другой доступ к папкам - FindFirstFileExW
требуют FILE_READ_DATA
, когда GetFileAttributesEx
требуют только FILE_READ_ATTRIBUTES
доступа.поэтому к этому также могут быть разные результаты.Также обратите внимание, что FILE_READ_ATTRIBUTES
- это специальный доступ для файловых систем.ntfs (например) предоставляет FILE_READ_ATTRIBUTES
доступ к вызывающей стороне в 2 случаях - если у прямой вызывающей стороны есть FILE_READ_ATTRIBUTES
доступ к файлу, или если у вызывающей стороны есть FILE_LIST_DIRECTORY
доступ к папке parent (как примечание стороны)- та же ситуация с доступом DELETE
- мы можем получить его, если у нас есть явный доступ к файлу или (если нет), если у нас есть FILE_DELETE_CHILD
доступ к родительской папке).
, если case вызывает C:\TEMP\Dir1
- GetFileAttributesEx
не ошибка, потому что у вас есть доступ FILE_LIST_DIRECTORY
к родительской папке C:\TEMP
.FindFirstFileExW
не сбой, потому что он действительно открывает C:\TEMP
, к которому у вас есть FILE_READ_DATA
доступ (также обратите внимание, что FILE_READ_DATA == FILE_LIST_DIRECTORY == 1
)
C:\TEMP\DIRX
GetFileAttributesExW
иFindFirstFileExW
хорошо, потому что у пользователя FILE_READ_DATA
(так же, как FILE_LIST_DIRECTORY
) на C:\TEMP
C:\TEMP\DIRX\DIRY
GetFileAttributesExW
сбой, потому что у пользователя нет FILE_READ_ATTRIBUTES
на DirY
и не FILE_LIST_DIRECTORY
на DirX
.FindFirstFileExW
ошибка, потому что у пользователя нет FILE_READ_DATA
в DirX
C:\TEMP\DIRX\DIRY\DIRZ
GetFileAttributesExW
нормально - у пользователя есть FILE_READ_ATTRIBUTES
доступ для DirZ
.FindFirstFileExW
сбой, потому что у пользователя нет FILE_READ_DATA
на DirY