函数或筛选器驱动程序中的 AddDevice 例程
函数或筛选器驱动程序中的 AddDevice 例程应执行以下步骤:
调用 IoCreateDevice 以 (FDO 或筛选器 DO) 为要添加的设备创建功能或筛选器设备对象。
不要为设备对象指定 DeviceName ,因为这样做会绕过 PnP 管理器的安全性。 如果用户模式组件需要指向设备的符号链接,请注册设备接口 (请参阅下面的下一步) 。 如果内核模式组件需要旧设备名称,驱动程序必须命名设备对象,但不建议命名。
在 DeviceCharacteristics 参数中包含FILE_DEVICE_SECURE_OPEN。 此特征指示 I/O 管理器针对所有打开的请求(包括相对打开和尾随文件名打开)的设备对象执行安全检查。
[可选]创建一个或多个指向设备的符号链接。
调用 IoRegisterDeviceInterface 来注册设备功能,并创建应用程序或系统组件可用于打开设备的符号链接。 驱动程序应在处理IRP_MN_START_DEVICE请求时通过调用 IoSetDeviceInterfaceState 来启用 接口 。 有关详细信息,请参阅 设备接口类。
将指向设备 PDO 的指针存储在设备扩展中。
PnP 管理器提供指向 PDO 的指针,作为 AddDevice 的 PhysicalDeviceObject 参数。 驱动程序在调用 IoGetDeviceProperty 等例程时使用 PDO 指针。
在设备扩展中定义标志以跟踪设备的某些 PnP 状态,例如设备暂停、删除和意外删除。
例如,定义一个标志以指示在设备处于暂停状态时应保留传入的 IRP。 如果驱动程序还没有排队 IRP 的机制,请创建一个队列来存放 IRP。 有关详细信息 ,请参阅排队和取消排队 IRP 。
此外,在设备扩展中分配 IO_REMOVE_LOCK 结构,并调用 IoInitializeRemoveLock 来初始化此结构。 有关详细信息,请参阅 使用删除锁。
在设备对象中设置DO_BUFFERED_IO或DO_DIRECT_IO标志位,以指定 I/O 管理器用于发送到设备堆栈的 I/O 请求的缓冲类型。 较高级别的驱动程序 或此成员,其值与堆栈中下一个较低级别的驱动程序相同,但可能最高级别驱动程序除外。 有关详细信息,请参阅 初始化设备对象。
如有必要,请设置电源管理的DO_POWER_INRUSH或DO_POWER_PAGABLE标志。 可分页的驱动程序必须设置DO_POWER_PAGABLE标志。 设备对象标志通常由总线驱动程序在为设备创建 PDO 时设置。 但是,较高级别的驱动程序在创建 FDO 或筛选器 DO 时,有时可能需要在其 AddDevice 例程中更改这些标志的值。 有关详细信息 ,请参阅为电源管理设置设备对象标志 。
创建和/或初始化驱动程序用于管理此设备的任何其他软件资源,例如事件、旋转锁或其他对象。 (硬件资源(如 I/O 端口)稍后配置,以响应 IRP_MN_START_DEVICE 请求。)
由于 AddDevice 例程在 IRQL = PASSIVE_LEVEL 的系统线程上下文中运行,因此,只要驱动程序不控制保存系统页文件的设备,使用 ExAllocatePoolWithTag 在初始化期间专门使用的任何内存都可以来自分页池。 在 AddDevice 返回控制权之前,必须使用 ExFreePool 释放此类内存分配。
将设备对象附加到设备堆栈 (IoAttachDeviceToDeviceStack) 。
在 TargetDevice 参数中指定指向设备的 PDO 的指针。
存储 IoAttachDeviceToDeviceStack 返回的指针。 此指针指向设备下一低级驱动程序的设备对象,是向设备堆栈传递 IRP 时 IoCallDriver 和 PoCallDriver 的必需参数。
使用如下所示的语句清除 FDO 或筛选器 DO 中的DO_DEVICE_INITIALIZING标志:
FunctionalDeviceObject->Flags &= ~DO_DEVICE_INITIALIZING;
准备好处理设备 (的 PnP IRP,例如 IRP_MN_QUERY_RESOURCE_REQUIREMENTS 和 IRP_MN_START_DEVICE) 。
驱动程序在收到包含 PnP 管理器分配给设备的硬件资源列表 的IRP_MN_START_DEVICE 之前,不得开始控制设备。