释放驱动程序分配的资源

驱动程序如何使用注册表、在其设备扩展、控制器扩展或驱动程序分配的非分页池中设置系统对象和资源的具体信息因驱动程序而异。 但是, 任何 Unload 例程都必须分步释放驱动程序使用的资源。

任何驱动程序的 Unload 例程都必须确保在释放该资源之前,其他驱动程序例程当前没有使用或可能不久使用特定资源。

通常, Unload 例程会释放以下阶段中所有驱动程序分配的资源:

  1. 如果驱动程序尚未这样做,请尽可能在任何物理设备上禁用中断,然后在禁用中断后立即调用 IoDisconnectInterrupt

  2. 确保没有任何其他驱动程序例程可以引用 Unload 例程要释放的资源。

    例如,如果当前为特定设备对象启用了驱动程序的 IoTimer 例程,则 Unload 例程必须调用 IoStopTimer。 它必须确保没有线程等待驱动程序的任何调度程序对象,并且其计时器对象在释放其调度程序对象的存储之前不会排队等待对 CustomTimerDpc 例程的调用。 如果它具有 ISR 可能排队的 CustomDpc 例程,则必须调用 KeRemoveQueueDpc,等等。

    如果驱动程序名为 IoQueueWorkItem,则必须确保工作项已完成。 IoQueueWorkItem 对关联的设备对象执行引用;如果保留任何此类引用,则不能卸载驱动程序。

    如果驱动程序名为 PsCreateSystemThread则 Unload 例程还必须使驱动程序创建的线程运行,以便线程本身可以在卸载驱动程序之前调用 PsTerminateSystemThread 。 驱动程序无法通过使用 PsCreateSystemThread 返回的 ThreadHandle 调用 ZwClose 来释放驱动程序创建的系统线程。

  3. 释放驱动程序分配的任何特定于设备的资源。 这样做可能涉及调用以下系统支持例程:

  4. 释放 DriverEntryReinitialize 例程在设备对象的设备扩展或控制器对象的控制器扩展中设置的系统对象和资源 (如果它创建了一个) 。 具体而言,驱动程序在尝试删除设备对象 (IoDeleteContro) ller) 或控制器对象之前 (执行以下操作

  5. \Registry\Machine\Hardware\ResourceMap 树下的注册表中释放 DriverEntryReinitialize 例程为驱动程序的物理设备声明的硬件资源(如果有)。

  6. 删除 DriverEntryReinitialize 例程存储在 注册表中的 \Registry 下的任何设备名称。\DeviceMap 树。

驱动程序释放设备、系统和硬件资源后,可以删除其设备和控制器对象,如释放设备和控制器 对象中所述