本帖最后由 YFSafe 于 2022-8-10 18:39 编辑
现在已经可以开始实现在驱动程序里面定义的三个分发例程了.到目前为止最简单的是CREATE和CLOSE分发例程,它们要做的只是用一个成功状态完成请求.
先上代码,再讲解:
[C++] 纯文本查看 复制代码 NTSTATUS SetPriorityCreateClose(PDEVICE_OBJECT DeviceObject,PIRP Irp)
{
Irp->IoStatus.Status = STATUS_SUCCESS;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp,IO_NO_INCREMENT);
return STATUS_SUCCESS;
}
每一个分发例程都接受一个目标设备对象和一个IO请求包(也就是我们的第二个传入参数-----IRP)作为参数.对设备对象我们不用作家关注,因为只有一个,只能是我们在DriverEntry里边用IoCreateDevice创造的那个.相反,IRP就特别重要了.
由于IRP结构十分庞大,在这里我们就快速的对它进行一些了解.
IRP是一个半文档化的结构,用来表示一个请求.驱动程序的目的就是处理这个IRP.无论它是CREATE;CLOSE;READ;WRITE或者是别的,我们都能够通过IRP的成员来分辨出来类型以及请求的信息.重要的是:IRP从不单独到来,它总会有一个或者多个IO_STACK_LOCATION结构的东西相伴.在像我们这样的驱动程序这种简单的情形中,只会有一个IO_STACK_LOACTION.简而言之,我们需要的信息部分位于基础的IRP结构中,部分位于设备栈中的IO_STACK_LOCATION结构中.
对于CREATE/CLOSE请求,我们不需要检查任何结构成员,只需要在IRP的IoStatus中设置状态值.IoStatus拥有两个成员值:
1.Status————————指明使用什么状态来完成当前请求.
2.Information——————这个值对不同的请求有着不同的含义.在CREATE/CLOSE分发例程中一般设置为0.
我们还需要调用IoCompleteRequest来完成这个IRP.这个函数会做很多事情.但是最基本的,它会把IRP送还给IRP的创造者(一般是IO管理器),然后由管理器通知程序工作已完成.函数的一二个参数是驱动程序提供给客户程序的优先级临时提升数值,大部分的时候0就是一个最好的值.因为请求是同步完成的,调用者没有理由需要得到一个优先级提升.
最后一件事是返回状态值.这个值需要跟放到IRP中的值一样.这看上去是在做无用功,但其实这是必要的.
|