之前是用ZwCreateFile再 ZwReadFile来调用其它驱动,
这里我们自己构造irp传递给被测试驱动程序的派遣函数...
每个内核中的句柄都会和一个内核对象的指针联系起来...
UNICODE_STRING ustrDeviceName;
RtlInitUnicodeString(&ustrDeviceName,L"\\Device\\DRIVERTEST_DeviceName");
DEVICE_OBJECT *pDeviceObject;
FILE_OBJECT *pFileObject;
NTSTATUS status2=IoGetDeviceObjectPointer(&ustrDeviceName,FILE_ALL_ACCESS,&pFileObject,&pDeviceObject);
KdPrint(("pDeviceObject %X",pDeviceObject));
KdPrint(("pFileObject %X",pFileObject));
if(!NT_SUCCESS(status2)){
KdPrint(("!NT_SUCCESS(IoGetDeviceObjectPointer)"));
return STATUS_SUCCESS;
}
KEVENT kEvent;
KeInitializeEvent(&kEvent,NotificationEvent,FALSE);
IO_STATUS_BLOCK IoStatusBlock;
LARGE_INTEGER liOffset=RtlConvertLongToLargeInteger(0);
IRP *pIrp=IoBuildSynchronousFsdRequest(IRP_MJ_READ,pDeviceObject,NULL,0,&liOffset,&kEvent,&IoStatusBlock);
//IRP *pIrp=IoBuildAsynchronousFsdRequest(IRP_MJ_READ,pDeviceObject,NULL,0,&liOffset,&IoStatusBlock);//注意参数,没&kEvent
KdPrint(("pIrp->UserEvent %X",pIrp->UserEvent));
//设置pIrp->UserEvent,当IRP完成后可以通知该事件
pIrp->UserEvent=&kEvent;//如果用IoBuildAsynchronousFsdRequest,请记得要设置,否则KeWaitForSingleObject会卡着不动
KdPrint(("new IRP %X",pIrp));
IO_STACK_LOCATION *pISL=IoGetNextIrpStackLocation(pIrp);
pISL->FileObject=pFileObject;
status2=IoCallDriver(pDeviceObject,pIrp);
if (status2==STATUS_PENDING)
{
KdPrint(("KeWaitForSingleObject 开始"));
KeWaitForSingleObject(&kEvent,Executive,KernelMode,FALSE,NULL);
KdPrint(("KeWaitForSingleObject 结束"));
}
ObDereferenceObject(pFileObject);
KdPrint(("Call Finished!"));