一般设置IRP取消例程很简单,大致代码如下
{
......
IoSetCancelRoutine(pIrp, LogIRPCancelRoutine);
pIrp->IoStatus.Status = STATUS_PENDING;
return STATUS_PENDING;
......
}
先调用 IoSetCancelRoutine设置取消例程为自定义函数。
接着把 IRP状态设置为 STATUS_PENDING, 再返回 STATUS_PENDING。
然后看一个不完善的取消例程:
VOID LogIRPCancelRoutine(PDEVICE_OBJECT pDeviceObject, PIRP pIrp)
{
UNREFERENCED_PARAMETER(pDeviceObject);
pIrp->IoStatus.Status = STATUS_CANCELLED;
pIrp->IoStatus.Information = 0;
IoCompleteRequest(pIrp, IO_NO_INCREMENT);
}
这种取消函数会引起问题,在XP上表现为系统假死,在WIn7 x64上直接崩溃,如图
原因是取消例程的自旋锁的问题, 代码中要加上
IoReleaseCancelSpinLock(pIrp->CancelIrql);
完整代码如下:
VOID LogIRPCancelRoutine(PDEVICE_OBJECT pDeviceObject, PIRP pIrp)
{
UNREFERENCED_PARAMETER(pDeviceObject);
pIrp->IoStatus.Status = STATUS_CANCELLED;
pIrp->IoStatus.Information = 0;
IoCompleteRequest(pIrp, IO_NO_INCREMENT);
IoReleaseCancelSpinLock(pIrp->CancelIrql);
}
标签:STATUS,IRP,例程,Windows,pDeviceObject,IoStatus,PENDING,pIrp From: https://www.cnblogs.com/ImprisonedSoul/p/17160487.html