Объекты файлов платформы

Когда приложение или драйвер пытается получить доступ к устройству, обычно путем создания или открытия файла, операционная система отправляет запрос на создание файла в стек драйверов. Когда приложение или драйвер завершит работу с устройством, система отправляет запросы на очистку и закрытие файлов в стек драйверов. Типы запросов этих трех запросов: WdfRequestTypeCreate, WdfRequestTypeCleanup и WdfRequestTypeClose соответственно.

Как правило, если драйвер не вызывает WdfDeviceInitSetExclusive, драйвер должен выполнять операции, связанные с конкретными файлами или другими операциями доступа, когда получает запросы на создание, очистку и закрытие файла, так как несколько файлов могут быть открыты одновременно или несколько приложений могут получить доступ к устройству одновременно. Поэтому драйвер должен отслеживать запросы ввода-вывода, связанные с каждым файлом или приложением.

Платформа определяет объекты файлов платформы, которые представляют собой средства приложения или драйвера для доступа к устройству, например к файлу, каталогу, тому, почтовому слоту, именованным каналом или ко всему устройству. Имя файла может быть связано с объектом файла, но значение имени файла зависит от драйвера. Дополнительные сведения об именах файлов см. в разделе Управление доступом к пространству имен устройств.

Если драйвер должен обрабатывать операции с файлами, он должен вызывать WdfDeviceInitSetFileObjectConfig из функции обратного вызова EvtDriverDeviceAdd . Метод WdfDeviceInitSetFileObjectConfig получает WDF_FILEOBJECT_CONFIG структуру в качестве входных данных. Драйвер использует эту структуру для регистрации функций обратного вызова EvtDeviceFileCreate, EvtFileCleanup и EvtFileClose и, при необходимости, для указания того, должна ли платформа создавать объект файла платформы каждый раз, когда драйвер получает запрос на создание файла.

Большинство драйверов, обрабатывающих операции с файлами, хранят сведения о файлах в контекстном пространстве файлового объекта платформы. Если драйвер обрабатывает операции с файлами, но ей не нужно хранить сведения в контекстном пространстве файлового объекта, платформе не нужно создавать объекты файлов платформы для драйвера.

Создание или открытие файла

Когда платформа получает запрос на создание файла для драйвера функции, он:

  1. Создает объект файла платформы, представляющий файл, если драйвер ранее не указал, что ему не нужно использовать объекты файлов платформы.

  2. Вызывает функцию обратного вызова EvtDeviceFileCreate драйвера, если драйвер зарегистрировал функцию обратного вызова.

Функция обратного вызова EvtDeviceFileCreate обычно получает сведения о файле, такие как его имя и флаги файлового объекта. Драйвер обычно сохраняет эти сведения в контекстном пространстве объекта файла платформы.

Вместо предоставления функции обратного вызова EvtDeviceFileCreate драйвер может вызвать WdfDeviceConfigureRequestDispatching , чтобы настроить очередь ввода-вывода для получения всех запросов на создание файлов (тип запроса WdfRequestTypeCreate ). Впоследствии драйвер будет получать запросы на создание файлов в обработчике запросов EvtIoDefault очереди. (Очередь ввода-вывода не может получать запросы на создание файлов, если для элемента DefaultQueue WDF_IO_QUEUE_CONFIG структуры очереди задано значение TRUE.)

Если драйвер не предоставляет функцию обратного вызова EvtDeviceFileCreate и не настраивает очередь ввода-вывода для обработки запросов ввода-вывода wdfRequestTypeCreate с типизированным типом, платформа:

  • Завершает все запросы на создание файлов для драйвера со значением состояния STATUS_SUCCESS, если драйвер является драйвером-функцией.

  • Пересылает все запросы на создание файлов в драйвер следующего уровня, если драйвер является драйвером фильтра.

(Чтобы узнать, как изменить это поведение, см. элемент AutoForwardCleanupClose структуры WDF_FILEOBJECT_CONFIG .)

Примечание Если драйвер функции не предоставляет интерфейсы устройств , которые приложения могут использовать для доступа к устройствам драйвера, драйвер должен предоставить функцию обратного вызова EvtDeviceFileCreate , которая завершает все запросы на создание файлов со значением состояния, для которого NT_SUCCESS(status) равно FALSE. В противном случае вредоносное приложение может попытаться получить доступ к устройству, используя имя физического объекта устройства (PDO). (Все PDO имеют имена.)

Если драйвер перенаправит запрос на создание целевому объекту ввода-вывода, драйвер не должен впоследствии завершить запрос со значением состояния сбоя, если драйвер не получит значение состояния сбоя от целевого объекта ввода-вывода. В противном случае более низкие драйверы не будут получать уведомления о том, что запрос на создание завершился сбоем, и могут попытаться работать так, как если бы файл был открыт.

Если драйвер пересылает запрос на создание целевому объекту ввода-вывода, драйвер не может задать флаг WDF_REQUEST_SEND_OPTION_SEND_AND_FORGET , если платформа создала объект файла платформы для запроса на создание. Таким образом, драйвер не может задать флаг WDF_REQUEST_SEND_OPTION_SEND_AND_FORGET для запроса на создание, если он также не устанавливает флаг WdfFileObjectNotRequired , так как драйвер не сможет очистить WDFFILEOBJECT в случае, если драйвер ниже в стеке не сможет выполнить запрос на создание. Вместо этого драйвер может использовать любые другие параметры отправки, например отправить асинхронно с помощью подпрограммы завершения или синхронно. В обоих случаях драйвер должен вызвать WdfRequestComplete при восстановлении управления.

Обратите внимание, что если драйвер завершает запрос на создание с состоянием ошибки, платформа удаляет объект файла платформы, но не вызывает функции обратного вызова EvtFileCleanup или EvtFileClose драйвера. Таким образом, если драйвер выделяет дополнительную память для конкретного объекта за пределами контекстного пространства объекта файла, он должен предоставить функцию обратного вызова EvtCleanupCallback или EvtDegradCallback , которая удаляет выделенную память.

В Windows Vista и более поздних версиях запросы на создание файлов можно отменить. Более ранние версии операционной системы Windows не поддерживают отмену запросов на создание файлов.

Система всегда создает объект файла модели драйвера Windows (WDM) для каждого запроса на создание, который поступает от пользовательского приложения. Если драйвер отправляет запрос на создание, он может не создать объект файла WDM для запроса. Как правило, платформа не создает объект файла платформы, если объект файла WDM отсутствует. Однако если драйвер вызвал WdfDeviceInitSetExclusive и если драйвер задал WdfFileObjectWdfCannotUseFsContexts в элементе FileObjectClassструктуры WDF_FILEOBJECT_CONFIG , платформа создаст объект файла платформы, даже если объект файла WDM не существует.

Получение сведений о файле

Функция обратного вызова EvtDeviceFileCreate драйвера может вызывать один или несколько следующих методов объекта для получения сведений о доступе приложения или драйвера к устройству:

WdfFileObjectGetFileName
Возвращает имя файла, содержащегося в объекте файла платформы.

WdfFileObjectGetFlags
Возвращает флаги, содержащиеся в объекте файла платформы.

WdfFileObjectWdmGetFileObject
Возвращает объект файла WDM, связанный с объектом файла платформы.

WdfRequestGetParameters
Извлекает параметры, связанные с объектом запроса платформы. Если тип запросаWdfRequestTypeCreate, элемент Parameters.Create структуры WDF_REQUEST_PARAMETERS содержит сведения о запросе на создание файла.

Как правило, драйвер сохраняет сведения о файле в контекстном пространстве файлового объекта платформы. Когда драйвер получает запрос ввода-вывода из одного из его очередей ввода-вывода, драйвер может вызвать WdfRequestGetFileObject , чтобы получить дескриптор объекта файла платформы, связанного с запросом. Затем драйвер может получить сведения о файле, которые он сохранил в контекстном пространстве объекта файла платформы.

Драйвер может искать в очереди ввода-вывода запросы, связанные с определенным файлом, путем вызова WdfIoQueueRetrieveRequestByFileObject.

Если драйвер имеет указатель на структуру WDM DEVICE_OBJECT , драйвер может вызвать WdfDeviceGetFileObject , чтобы получить дескриптор объекта файла платформы, связанного с объектом устройства WDM.

Закрытие файла

Когда приложение или другой драйвер закрывает файл, платформа получает запрос на очистку и закрытие вашего драйвера. Платформа:

  1. Вызывает функции обратного вызова EvtFileCleanup и EvtFileClose драйвера, если драйвер зарегистрировал эти функции обратного вызова.

  2. Удаляет объект файла платформы, представляющий файл.

Функции обратного вызова EvtFileCleanup и EvtFileClose драйвера получают дескриптор объекта файла платформы. Драйвер может вызвать WdfFileObjectGetDevice , чтобы определить, какой объект устройства платформы связан с объектом файла платформы.