总线驱动IRP的中止AbortIrp
2023-04-07
30
0
AbortIrp用于驱动即将卸载,但系统这时又下发了一个功能驱动过来。这时我们需要中止它,系统通过我们Abort它的状态也许不再下发功能IRP了。
对于总线驱动,IRP一般分为三类:
- 第一种是通用的功能IRP,如IRP_MJ_CLOSE\IRP_MJ_CREATE\IRP_MJ_DEVICE_CONTROL之类。
- 第二种是系统内部驱动,主要以IRP_MJ_PNP为代表的即插即用IRP.
- 第三种就是电源管理IRP,只有一个IRP_MJ_POWER。
AbortIrp一般IRP状态返回为STATUS_DELETE_PENDING,包括电源管理IRP.
如示例代码:
if (abortIrp)
{
status = irp->IoStatus.Status = STATUS_DELETE_PENDING;
if (majorFunction == IRP_MJ_POWER)
{
PoStartNextPowerIrp(irp);
}
IoCompleteRequest(irp, IO_NO_INCREMENT);
}
但是对于AbortIrp的原则一般有以下:
- 对于总线驱动FDO除过IRP_MJ_PNP和IRP_MJ_CLOSE之后的外有驱动都得Abort.
- 总线驱动创建的子设备PDO,除过IRP_MJ_PNP,IRP_MJ_CLOSE,IRP_MJ_POWER之外的外有驱动都得Abort。
if ((majorFunction != IRP_MJ_PNP) && (majorFunction != IRP_MJ_CLOSE))
{
enum deviceState state = (isParentFdo) ? parentFdoExt->state : functionPdoExt->state;
if (!isParentFdo && majorFunction == IRP_MJ_POWER)
{
/*
* Don't abort power IRP's on child function PDO's, even if
* state is STATE_REMOVING or STATE_REMOVED as this will veto
* a suspend request if the child function PDO is disabled.
*/
;
}
else if ((state == STATE_REMOVING) || (state == STATE_REMOVED))
{
abortIrp = TRUE;
}
}
AbortIrp的条件
AbortIpr适用于设备驱动处于已卸载或者正在卸载状态。
主要有IRP_MN_REMOVE_DEVICE