阅读:1587回复:7
我的有问题switch代码,请大家给我说说为什么会蓝屏
switch(WY_CtrCode)
{ case IO_REFERENCE_EVENT: WY_Evt = (HANDLE)WY_irpStack->Parameters.DeviceIoControl.Type3InputBuffer;//获得号句柄 WY_status = ObReferenceObjectByHandle(WY_Evt, GENERIC_ALL, NULL, KernelMode, &WY_GbEvt, &WY_OBJ_HandleInfo);//转化为核心信号量句柄 if(WY_status != STATUS_SUCCESS){ WY_DBGPRN("ObReferenceObjectByHandle Faild"); WY_DBGPRNEX("Error Code = %d",WY_status); } WY_DBGPRN("ObReferenceObjectByHandle Sucessful"); break; case IO_DEREFERENCE_EVENT: if(WY_GbEvt) ObDereferenceObject(WY_GbEvt);//移除信号量 WY_DBGPRN("ObDereferenceObject Successful"); break; case IO_SET_EVENT: KeSetEvent(WY_GbEvt,0,FALSE); WY_DBGPRN("KeSetEvent Successful"); break; case IO_CLEAR_EVENT: KeClearEvent(WY_GbEvt); WY_DBGPRN("KeClearEvent Successful"); break; case IO_QUERY_EVENT_STATE: WY_DBGPRN("KeReadStateEvent"); WY_OutBuf = (LONG *)WY_Irp->UserBuffer;//获得应用层缓冲区地址 *WY_OutBuf = KeReadStateEvent(WY_GbEvt); WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = sizeof(LONG); IoCompleteRequest(WY_Irp,IO_NO_INCREMENT); WY_DBGPRN("KeReadStateEvent Successful"); return WY_status;//一但改成break就出问题 case IO_GET_USER_ADDRESS: WY_DBGPRN("Converting SysAddr to UserAddr"); try { WY_UserVirtualAddress = MmMapLockedPages(WY_MDL,UserMode);//转化核心地址到用户态 *((PVOID *)(WY_Irp->AssociatedIrp.SystemBuffer)) = WY_UserVirtualAddress; WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = sizeof(PVOID); } except(EXCEPTION_EXECUTE_HANDLER){} WY_DBGPRN("Convert Successful!"); break; default: break; } |
|
|
沙发#
发布于:2004-10-20 13:44
case IO_QUERY_EVENT_STATE:
最后的return 改为break;时应用层一传递Irp就会蓝屏 为什么啊 |
|
|
板凳#
发布于:2004-10-20 15:47
代码不全,问题不一定是出在这里的,可能是switch
后面的代码,因为return 之后就直接堆栈返回了,switch 后面的代码执行不到了. |
|
|
地板#
发布于:2004-10-20 15:56
别的都测试过,没问题。应用层是这样进行IRP的
DWORD WY_dwReturn; ULONG WY_dwState; if(WY_hDev){ //获得信号量状态 DeviceIoControl(WY_hDev,IO_QUERY_EVENT_STATE,NULL,0,(LPVOID)&WY_dwState,sizeof(WY_dwState),&WY_dwReturn,NULL); } 以下该驱动的完整代码 #include <ntddk.h> #include "MinDriver.h" PVOID WY_GbEvt = NULL; //全局信号量 PVOID WY_SysVirtualAddress,WY_UserVirtualAddress; //共享内存核心地址,用户地址 PMDL WY_MDL; //MDL NTSTATUS DriverEntry(IN PDRIVER_OBJECT WY_DriverObject, IN PUNICODE_STRING WY_RegistryPath) { NTSTATUS WY_status = STATUS_SUCCESS; UNICODE_STRING WY_DEV_Name; //设备名 UNICODE_STRING WY_SymbolicName; //连接名 WY_DBGPRN("Hello 王艳"); WY_DBGPRN("MinDriver Beta"); WY_DBGPRN("WY_Driver Entry Loading ..."); WY_DriverObject->DriverUnload = PacketUnload; //卸栽函数 WY_DriverObject->MajorFunction[IRP_MJ_CREATE] = MinDrv_Create;//定义Dispatch例程响应CreateFile WY_DriverObject->MajorFunction[IRP_MJ_CLOSE] = MinDrv_Close;//定义Dispatch例程响应CloseHandle WY_DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = MinDrv_IoControl;//定义Dispatch例程响应DeviceIoControl RtlInitUnicodeString(&WY_DEV_Name,MIN_DRIVER_DEV_NAME); //注册设备 RtlInitUnicodeString(&WY_SymbolicName,MIN_DRIVER_WIN32_DEV_NAME);//注册设备 WY_status = IoCreateDevice(WY_DriverObject, sizeof(MIN_DRIVER_EXT), &WY_DEV_Name, FILE_DEVICE_UNKNOWN, 0, TRUE, &WY_DriverObject->DeviceObject); if(WY_status != STATUS_SUCCESS){ WY_DBGPRN("IoCreateDevice Failed"); WY_DBGPRNEX("Error Code = %d",WY_status); } WY_status = IoCreateSymbolicLink(&WY_SymbolicName,&WY_DEV_Name);//创建设备连接,共应用层通讯 if(WY_status != STATUS_SUCCESS){ WY_DBGPRN("IoCreateSymbolicLink Failed"); WY_DBGPRNEX("Error Code = %d",WY_status); } WY_SysVirtualAddress = ExAllocatePool(NonPagedPool,1024);//申请非分页缓冲池 WY_MDL = IoAllocateMdl(WY_SysVirtualAddress,1024,FALSE,FALSE,NULL);//建立MDL MmBuildMdlForNonPagedPool(WY_MDL);//为非分页缓冲池建立MDL return WY_status; } VOID PacketUnload(IN PDRIVER_OBJECT WY_DriverObject) { PDEVICE_OBJECT WY_DeviceObject; PDEVICE_OBJECT WY_OldDeviceObject; WY_DBGPRN("WY_Driver unLoading ..."); WY_DeviceObject = WY_DriverObject->DeviceObject; while(WY_DeviceObject != NULL){//删除建立的设备 WY_OldDeviceObject = WY_DeviceObject; WY_DeviceObject = WY_DeviceObject->NextDevice; IoDeleteDevice(WY_OldDeviceObject); } WY_DBGPRN("王艳 GoodBye"); } NTSTATUS MinDrv_Create(IN PDEVICE_OBJECT WY_DEV_Object, IN PIRP WY_Irp)//Dispatch例程 { NTSTATUS WY_status = STATUS_SUCCESS; WY_DBGPRN("Create Device--New"); WY_Irp->IoStatus.Status = STATUS_SUCCESS;//返回成功 WY_Irp->IoStatus.Information = 0; IoCompleteRequest(WY_Irp,IO_NO_INCREMENT);//完成例程 return WY_status; } NTSTATUS MinDrv_Close(IN PDEVICE_OBJECT WY_DEV_Object, IN PIRP WY_Irp)//Dispatch例程 { NTSTATUS WY_status = STATUS_SUCCESS; WY_DBGPRN("Close Device"); WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = 0; IoCompleteRequest(WY_Irp,IO_NO_INCREMENT); return WY_status; } NTSTATUS MinDrv_IoControl(IN PDEVICE_OBJECT WY_DEV_Object, IN PIRP WY_Irp)//Dispatch例程 { NTSTATUS WY_status = STATUS_SUCCESS; ULONG WY_CtrCode;//控制代码 PIO_STACK_LOCATION WY_irpStack;//IRP堆栈 HANDLE WY_Evt;//信号量 OBJECT_HANDLE_INFORMATION WY_OBJ_HandleInfo; LONG *WY_OutBuf;//应用层缓冲区 WY_irpStack = IoGetCurrentIrpStackLocation(WY_Irp);//获得当前IRP堆栈 WY_CtrCode = WY_irpStack->Parameters.DeviceIoControl.IoControlCode;//获得控制代码 switch(WY_CtrCode) { case IO_REFERENCE_EVENT: WY_Evt = (HANDLE)WY_irpStack->Parameters.DeviceIoControl.Type3InputBuffer;//获得号句柄 WY_status = ObReferenceObjectByHandle(WY_Evt, GENERIC_ALL, NULL, KernelMode, &WY_GbEvt, &WY_OBJ_HandleInfo);//转化为核心信号量句柄 if(WY_status != STATUS_SUCCESS){ WY_DBGPRN("ObReferenceObjectByHandle Faild"); WY_DBGPRNEX("Error Code = %d",WY_status); } WY_DBGPRN("ObReferenceObjectByHandle Sucessful"); break; case IO_DEREFERENCE_EVENT: if(WY_GbEvt) ObDereferenceObject(WY_GbEvt);//移除信号量 WY_DBGPRN("ObDereferenceObject Successful"); break; case IO_SET_EVENT: KeSetEvent(WY_GbEvt,0,FALSE); WY_DBGPRN("KeSetEvent Successful"); break; case IO_CLEAR_EVENT: KeClearEvent(WY_GbEvt); WY_DBGPRN("KeClearEvent Successful"); break; case IO_QUERY_EVENT_STATE: WY_DBGPRN("KeReadStateEvent"); WY_OutBuf = (LONG *)WY_Irp->UserBuffer;//获得应用层缓冲区地址 *WY_OutBuf = KeReadStateEvent(WY_GbEvt); WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = sizeof(LONG); IoCompleteRequest(WY_Irp,IO_NO_INCREMENT); WY_DBGPRN("KeReadStateEvent Successful"); return WY_status; case IO_GET_USER_ADDRESS: WY_DBGPRN("Converting SysAddr to UserAddr"); try { WY_UserVirtualAddress = MmMapLockedPages(WY_MDL,UserMode);//转化核心地址到用户态 *((PVOID *)(WY_Irp->AssociatedIrp.SystemBuffer)) = WY_UserVirtualAddress; WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = sizeof(PVOID); } except(EXCEPTION_EXECUTE_HANDLER){} WY_DBGPRN("Convert Successful!"); break; default: break; } WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = 0; IoCompleteRequest(WY_Irp,IO_NO_INCREMENT); return WY_status; } |
|
|
地下室#
发布于:2004-10-20 16:36
老总,
看看你代码的最后了, WY_Irp->IoStatus.Status = STATUS_SUCCESS; WY_Irp->IoStatus.Information = 0; IoCompleteRequest(WY_Irp,IO_NO_INCREMENT); 这里的WY_Irp->IoStatus.Information怎么能等于0呢, 肯定的是sizeof(ULONG)了。 |
|
|
5楼#
发布于:2004-10-20 19:55
那我的前两个例程中的WY_Irp->IoStatus.Information = 0;
怎么不会出错呢? :( |
|
|
6楼#
发布于:2004-10-22 09:44
WY.lslrt 女孩?
information取值看irp是成功还是失败。 一般irp完成失败,information为0; 成功的传输数据,设成传输的字节量。如果设成0,会造成资源丢失。 |
|
|
7楼#
发布于:2004-10-22 12:34
哦。谢谢,不过分我已经给过了,不知道还能不能在给。
不过我很疑问,我怎么会是女孩呢?我的名字很女性化吗? |
|
|