我是Windows设备驱动程序编程的新手。我知道某些操作只能在IRQL PASSIVE_LEVEL上执行。例如,Microsoft提供了以下示例代码,说明如何从内核驱动程序写入文件:

if (KeGetCurrentIrql() != PASSIVE_LEVEL)
    return STATUS_INVALID_DEVICE_STATE;

Status = ZwCreateFile(...);

我的问题是:是什么原因阻止了上面的KeGetCurrentIrql()检查之后引发IRQL?假设发生上下文或线程切换,当IRQL返回我的驱动程序时,IRQL不会突然变成DISPATCH_LEVEL,这将导致系统崩溃吗?

如果无法做到这一点,那为什么不只检查DriverEntry函数中的IRQL并全部完成一次呢?

最佳答案

线程的irql只能自己提高。

因为您是从上层/下层驱动程序调用的,所以当前运行上下文的irql可能不同。并且有几个函数可以提高/降低irql。

几个例子:

IRP_MJ_READ

   NTSTATUS DispatchRead(
    __in struct _DEVICE_OBJECT  *DeviceObject,
    __in struct _IRP  *Irp
    )
  {
     // this will be called at irql == PASSIVE_LEVEL
     ...
     // we have acquire a spinlock
     KSSPIN_LOCK lck;
     KeInititializeSpinLock( &lck );
     KIRQL prev_irql;
     KeAcquireSpinLock( &lck,&prev_irql );

     // KeGetCurrentIrql() == DISPATCH_LEVEL

     KeReleaseSpinLock( &lck, prev_irql );
     // KeGetCurrentIrql() == PASSIVE_LEVEL
     ...
  }

(Io-)完成例程可以在DISPATCH_LEVEL处调用,因此应相应地执行。
NTSTATUS CompleteSth(IN PDEVICE_OBJECT DeviceObject,IN PIRP Irp,IN PVOID Context)
{
    // KeGetCurrentIrql() >= PASSIVE_LEVEL
}

关于windows - 设备驱动程序IRQL和线程/上下文切换,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/2311040/

10-10 20:36