Программирование драйверов Windows

Процедура Unload


Как правило, однажды загруженный драйвер остается в системе до перезагрузки. Для того чтобы сделать драйвер выгружаемым, необходимо написать и зарегистрировать процедуру выгрузки Unload. Диспетчер ввода/вывода затем производит вызов этой процедуры в момент ручной либо автоматической выгрузки драйвера &#8212 как раз перед удалением драйвера из памяти.

Таблица 8.4. Описание прототипа функции Unload



VOID Unload IRQL == PASSIVE_LEVEL
Параметры Выполняет завершающие действия
IN PDRIVER_OBJECT pDriverObject Указатель на объект драйвера
Возвращаемое значение void

Хотя действия процедуры Unload могут меняться от драйвера к драйверу, общими являются следующие шаги, характерные более для драйверов "в-стиле-NT".

  • Для некоторых типов аппаратуры необходимо сохранить ее состояние в Системном Реестре. При последующей загрузке драйвера эти данные могут быть использованы в процедуре DriverEntry. Скажем, драйвер принтера может сохранить последнее значение разрешения печати.
  • Если прерывания разрешены для обслуживаемого устройства, то процедура выгрузки должна запретить их и произвести отключение от объекта прерываний. Ситуация, когда устройство будет порождать запросы на прерывание в то время, как объект прерываний не существует, неминуемо приведет к краху системы.
  • Символьная ссылка должна быть удалена из пространства имен, видимого пользовательскими приложениями. Это выполняется при помощи вызова IoDeleteSymbolicLink.
  • Объект устройства должен быть удален вызовом IoDeleteDevice.
  • В случае, если драйвер управляет многокомпонентным (multiunit) контроллером, необходимо повторить шаги 3 и 4 для каждого устройства, подключенного к контроллеру, а затем необходимо удалить сам объект контроллера при помощи вызова IoDeleteController.
  • Следует выполнить освобождение памяти, выделенной драйверу, во всех типах оперативной памяти.
  • Драйверы WDM модели выполняют практически все из описанных выше действий в обработчике IRP_MJ_PNP запросов с субкодом IRP_MN_REMOVE (то есть посвященном удалению устройства из системы).


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

    Процедура выгрузки драйвера Unload не вызывается в момент отката системы, и если существует необходимость выполнять какую-либо работу при откате системы, то это следует сделать в специально предназначенной на то процедуре драйвера, зарегистрированной для обработки IRP пакетов с кодом IRP_MJ_SHUTDOWN. Объект устройства должен быть с помощью вызова IoRegisterShutdownNotification занесен в очередь объектов, получающих уведомление о перезагрузке, &#8212 только при этом условии будет вызвана процедура, зарегистрированная для обработки пакетов с кодом IRP_MJ_SHUTDOWN.

    Содержание раздела