Дескрипторы объектов

Драйверы и компоненты пользовательского режима получают доступ к большинству системных объектов через дескрипторы. Дескрипторы представлены непрозрачным типом данных HANDLE. (Обратите внимание, что дескрипторы не используются для доступа к объектам устройств или объектам драйвера.)

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

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

Тип объекта Соответствующая процедура создания и открытия

File

IoCreateFile, ZwCreateFile, ZwOpenFile

Разделы реестра

IoOpenDeviceInterfaceRegistryKey, IoOpenDeviceRegistryKey, ZwCreateKey, ZwOpenKey

Потоки

PsCreateSystemThread

События

IoCreateSynchronizationEvent, IoCreateNotificationEvent

Символические связи

ZwOpenSymbolicLinkObject

Объекты каталога

ZwCreateDirectoryObject

Объекты Section

ZwOpenSection

Когда драйверу больше не требуется доступ к объекту, он вызывает подпрограмму ZwClose , чтобы закрыть дескриптор. Это подходит для всех типов объектов, перечисленных в таблице выше.

Большинство подпрограмм, предоставляющих дескрипторы, принимают в качестве параметра структуру OBJECT_ATTRIBUTES . Эту структуру можно использовать для указания атрибутов дескриптора.

Драйверы могут указывать следующие атрибуты дескриптора:

  • OBJ_KERNEL_HANDLE

    Доступ к дескриптором можно получить только из режима ядра.

  • OBJ_INHERIT

    Все дочерние элементы текущего процесса получают копию дескриптора при их создании.

  • OBJ_FORCE_ACCESS_CHECK

    Этот атрибут указывает, что система выполняет все проверки доступа к дескриптором. По умолчанию система обходит все проверки доступа для дескрипторов, созданных в режиме ядра.

Используйте подпрограмму InitializeObjectAttributes , чтобы задать эти атрибуты в OBJECT_ATTRIBUTES структуре.

Сведения о проверке дескрипторов объектов см. в разделе Сбой проверки дескрипторов объектов.

Дескрипторы частных объектов

Всякий раз, когда драйвер создает дескриптор объекта для частного использования, драйвер должен указать атрибут OBJ_KERNEL_HANDLE. Это гарантирует, что дескриптор будет недоступен для приложений в пользовательском режиме.

Дескрипторы общих объектов

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

  1. Создайте дескриптор в режиме ядра и передайте их в пользовательский режим, а не наоборот. Дескрипторам, созданным компонентом пользовательского режима и переданным драйверу, не следует доверять.

  2. Если драйвер должен управлять дескрипторами от имени приложений в пользовательском режиме, используйте атрибут OBJ_FORCE_ACCESS_CHECK, чтобы убедиться, что приложение имеет необходимый доступ.

  3. Используйте ObReferenceObjectByPointer , чтобы сохранить ссылку на режим ядра в общем дескрипторе. В противном случае, если компонент пользовательского режима закроет дескриптор, количество ссылок будет равно нулю, а если драйвер попытается использовать или закрыть дескриптор, система аварийно завершит работу.

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