Tuesday, February 16, 2010

About IO_OPEN_TARGET_DIRECTORY

Прекрасный способ открытия папки по имени файла:
NTSTATUS OpenParentFolderByFileName(OUT PHANDLE pFileHandle,
IN ACCESS_MASK desiredAccess,
IN POBJECT_ATTRIBUTES pObjectAttributes,
OUT PIO_STATUS_BLOCK pIoStatusBlock,
IN ULONG options)
{
return IoCreateFile( pFileHandle,
desiredAccess,
pObjectAttributes,
pIoStatusBlock,
(PLARGE_INTEGER) NULL,
0,
FILE_SHARE_READ | FILE_SHARE_WRITE,
FILE_OPEN,
FILE_OPEN_FOR_BACKUP_INTENT,
(PVOID) NULL,
0L,
CreateFileTypeNone,
(PVOID) NULL,
options|IO_OPEN_TARGET_DIRECTORY);
}

void Test()
{
UNICODE_STRING fileName;
OBJECT_ATTRIBUTES objectAttributes;
IO_STATUS_BLOCK iosb;

RtlInitUnicodeString(&fileName, L"\\??\\c:\\hello.txt");

InitializeObjectAttributes(
&objectAttributes,
&fileName,
OBJ_CASE_INSENSITIVE|OBJ_KERNEL_HANDLE,
NULL,
NULL
);

HANDLE hFile = 0;
if (NT_SUCCESS(OpenParentFolderByFileName(&hFile, 0, &objectAttributes, &iosb, IO_NO_PARAMETER_CHECKING)))
{
// handle should point to --> \\??\\c:\\ :)
// ..
ZwClose(hFile);
}
}
_Winnie C++ Colorizer
Как видно из листинга, использование флага IO_OPEN_TARGET_DIRECTORY освобождает от унылого и бажного ручного парсинга имени файла и перекладывает эту задачу на файловую систему. Это решение от microsoft кажется мне логичным и прекрасным - кому, как не файловой системе знать о связи между файлом и папкой.
Чисто "black magic for kernel mode", жаль для user-mode это сделать невозможно.

No comments: