ioSetCompletionRoutine 函数 (wdm.h)
IoSetCompletionRoutine 例程注册 IoCompletion 例程,该例程将在下一个较低级别的驱动程序完成给定 IRP 的请求操作时调用。
语法
void IoSetCompletionRoutine(
[in] PIRP Irp,
[in, optional] PIO_COMPLETION_ROUTINE CompletionRoutine,
[in, optional] __drv_aliasesMem PVOID Context,
[in] BOOLEAN InvokeOnSuccess,
[in] BOOLEAN InvokeOnError,
[in] BOOLEAN InvokeOnCancel
);
参数
[in] Irp
指向驱动程序正在处理的 IRP 的指针。
[in, optional] CompletionRoutine
指定驱动程序提供的 IoCompletion 例程的入口点,该例程在下一个较低级别的驱动程序完成数据包时调用。
[in, optional] Context
指向要传递给 IoCompletion 例程的驱动程序确定上下文的指针。 上下文信息必须存储在非分页内存中,因为 IoCompletion 例程是在 IRQL <= DISPATCH_LEVEL 调用的。
[in] InvokeOnSuccess
指定在 IRP 的 IO_STATUS_BLOCK 结构中以成功状态值完成 IRP 时是否调用完成例程,具体取决于 NT_SUCCESS 宏的结果 (请参阅 ) 使用 NTSTATUS 值 。
[in] InvokeOnError
指定在 IRP 的 IO_STATUS_BLOCK 结构中以非成功状态值完成 IRP 时,是否调用完成例程。
[in] InvokeOnCancel
指定在驱动程序或内核调用 IoCancelIrp 来取消 IRP 时是否调用完成例程。
返回值
无
备注
只有可以保证在完成例程完成之前不会卸载它的驱动程序才能使用 IoSetCompletionRoutine。 否则,驱动程序必须使用 IoSetCompletionRoutineEx,这会阻止驱动程序卸载,直到其完成例程执行。
此例程设置给定 IRP 中 IoCompletion 例程的传输地址。 分层驱动程序链中的最低级别驱动程序不能调用此例程。
IoSetCompletionRoutine 注册指定例程,该例程将在下一个较低级别的驱动程序以下列任何或所有方式完成请求的操作时调用:
具有成功状态值
具有 nonsuccess 状态值
通过取消 IRP
通常,I/O 状态块由基础设备驱动程序设置。 它将被读取,但不会被任何更高级别的驱动程序的 IoCompletion 例程更改。
使用 IoAllocateIrp 或 IoBuildAsynchronousFsdRequest 分配 IRP 的更高级别的驱动程序必须在将所有 InvokeOnXxx 参数设置为 TRUE 的情况下调用此例程,然后才能将驱动程序分配的 IRP 传递给 IoCallDriver。 使用此类 IRP 调用 IoCompletion 例程时,它必须释放驱动程序分配的 IRP 以及驱动程序为请求设置的任何其他资源,例如具有 IoBuildPartialMdl 的 MDL。 当此类驱动程序调用 IoFreeIrp 以阻止 I/O 管理器针对驱动程序分配的 IRP 完成处理时,应返回STATUS_MORE_PROCESSING_REQUIRED。
在 IoCompletion 例程运行之前可能卸载的非 PnP 驱动程序应改用 IoSetCompletionRoutineEx 。