I/O 验证

驱动程序验证程序具有两个级别的 I/O 验证:

  • 每当选择 I/O 验证时,级别 1 I/O 验证始终处于活动状态。

  • 每当在 Windows XP 及更高版本中选择 I/O 验证时,级别 2 I/O 验证始终处于活动状态。

另请参阅:增强型 I/O 验证 在 Windows 7 及更高版本的 Windows 操作系统中,选择“I/O 验证”时,会自动激活增强的 I/O 验证。 它不可用,也没有必要将其作为单独的选项进行选择。

级别 1 I/O 验证

启用级别 1 I/O 验证后,将从特殊池分配通过 IoAllocateIrp 获取的所有 IRP,并跟踪其使用情况。

此外,驱动程序验证程序会检查无效的 I/O 调用,包括:

  • 尝试释放其类型不是IO_TYPE_IRP

  • 将无效设备对象传递到 IoCallDriver

  • 将 IRP 传递到 IoCompleteRequest,该 IoCompleteRequest 包含无效状态或仍设置了取消例程

  • 通过调用驱动程序调度例程更改 IRQL

  • 尝试释放仍与线程关联的 IRP

  • 将设备对象传递到 IoInitializeTimer,该 IoInitializeTimer 已包含初始化的计时器

  • 将无效缓冲区传递到 IoBuildAsynchronousFsdRequestIoBuildDeviceIoControlRequest

  • 当此 I/O 状态块在已撤消太远的堆栈上分配时,将 I/O 状态块传递给 IRP

  • 当此事件对象在已取消转换太远的堆栈上分配时,将事件对象传递给 IRP

由于特殊 IRP 池的大小有限,因此一次仅对一个驱动程序使用 I/O 验证最为有效。

I/O 验证级别 1 失败会导致发出 bug 检查 0xC9。 此 bug 检查 的第一个参数指示发生了哪些冲突。 有关完整的参数列表 ,请参阅 bug 检查0xC9 (DRIVER_VERIFIER_IOMANAGER_VIOLATION) 。

级别 2 I/O 验证

I/O 验证级别 2 错误以不同的方式显示:在蓝屏上、故障转储文件和内核调试器中。

在蓝屏上,这些错误由消息 IO 系统验证错误 和字符串 WDM DRIVER ERRORXXX(其中 XXX 是 I/O 错误代码)记录。

在故障转储文件中,大多数错误都由 消息 BugCheck 0xC9 (DRIVER_VERIFIER_IOMANAGER_VIOLATION) 以及 I/O 错误代码进行记录。 在这种情况下,I/O 错误代码显示为 bug 检查 0xC9的第一个参数。 其余部分由消息 Bug 检查0xC4 (DRIVER_VERIFIER_DETECTED_VIOLATION) 以及驱动程序验证程序错误代码进行记录。 在这种情况下,驱动程序验证程序错误代码显示为 bug 检查 0xC4的第一个参数。

在 (KD 或 WinDbg) 的内核调试器中,这些错误由消息 WDM DRIVER ERROR 和描述性文本字符串记录。 当内核调试器处于活动状态时,可以忽略级别 2 错误并恢复系统操作。 (任何其他 bug 检查都无法执行此操作。)

蓝屏、故障转储文件和内核调试器都显示其他信息。 有关大多数 I/O 验证级别 2 错误消息的完整说明,请参阅 bug 检查0xC9。 有关其余部分,请参阅 bug 检查0xC4

从 Window Vista 开始,I/O 验证选项会检查以下驱动程序错误:

从 Windows 7 开始,I/O 验证选项会检查以下驱动程序错误:

此外,可以使用此选项来检测另一个常见的驱动程序 bug - 重新初始化删除锁。 删除锁应在设备扩展内分配数据结构。 这可确保 I/O 管理器仅在删除设备对象时释放保存IO_REMOVE_LOCK结构的内存。 如果驱动程序执行以下三个步骤,则可能在步骤 2 之后,应用程序或驱动程序仍保留对 Device1 的引用:

  • 分配对应于 Device1 的IO_REMOVE_LOCK结构,但在 Device1 的扩展之外执行分配。
  • 删除 Device1 时调用 IoReleaseRemoveLockAndWait
  • 调用同一锁的 IoInitializeRemoveLock ,将其作为 Device2 的删除锁重复使用。

在步骤 2 之后,应用程序或驱动程序可能仍保留对 Device1 的引用。 即使删除了此设备,应用程序或驱动程序仍可将请求发送到 Device1。 因此,在 I/O 管理器删除 Device1 之前,重复使用与新删除锁相同的内存是不安全的。 在另一个线程尝试获取锁时重新初始化同一锁可能会导致锁损坏,导致驱动程序和整个系统产生不可预知的结果。

在 Windows 7 及更高版本的 Windows 操作系统中,选择 “I/O 验证 ”时,将自动激活增强型 I/O 验证。

激活此选项

可以使用驱动程序验证程序管理器或Verifier.exe命令行激活一个或多个驱动程序的 I/O 验证功能。 有关详细信息,请参阅 选择驱动程序验证程序选项

  • 在命令行。

    在命令行中,I/O 验证选项由 位 4 (0x10) 表示。 若要激活 I/O 验证,请使用标志值0x10或向标志值添加0x10。 例如:

    verifier /flags 0x10 /driver MyDriver.sys
    

    下次启动后,该功能将处于活动状态。

    还可以通过将 /volatile 参数添加到 命令来激活和停用 I/O 验证,而无需重启计算机。 例如:

    verifier /volatile /flags 0x10 /adddriver MyDriver.sys
    

    此设置会立即生效,但在关闭或重启计算机时会丢失。 有关详细信息,请参阅 使用易失性设置

    I/O 验证功能也包含在标准设置中。 例如:

    verifier /standard /driver MyDriver.sys
    
  • 使用驱动程序验证程序管理器

    1. 选择“ 为代码开发人员) 创建自定义设置 ( ”,然后单击“ 下一步”。
    2. 从完整列表中选择“选择单个设置”。
    3. 选择“ (检查) I/O 验证”。

    I/O 验证功能也包含在标准设置中。 若要使用此功能,请在驱动程序验证程序管理器中单击“创建标准设置”。