阅读:5948回复:32
在Sfilter的mount例程中识别USB 存储设备?
我基于Sfilter的例子进行调试,在SfFsControlMountVolume例程中能够捕获磁盘的mount的消息,根据DeviceObject->DeviceType可以区分开光驱设备和磁盘设备,但是不能分辨出本地磁盘和USB磁盘,因为它们的类型都是0x00000008,即disk类型,请教各位高手,如何才能分辨出是本地磁盘还是USB磁盘?谢谢
|
|
最新喜欢:![]() |
沙发#
发布于:2010-04-08 17:11
这个 估计要判断下,总线类型 + 是否支持热插拔。。。+ 设备类型。。
应该综合判断。。 |
|
|
板凳#
发布于:2010-04-08 16:52
|
|
地板#
发布于:2008-08-08 15:51
引用第25楼yaolixing于2008-01-04 22:49发表的 : 我这样用没出什么问题啊! |
|
地下室#
发布于:2008-01-09 09:34
引用第25楼yaolixing于2008-01-04 22:49发表的 : StorageDeviceobject->NextDevice->Characteristics == FILE_REMOVABLE_MEDIA 为什么非要是NextDevice? |
|
|
5楼#
发布于:2008-01-09 09:27
0x00000007是usb
|
|
|
6楼#
发布于:2008-01-08 17:53
方法多多....
俺通过枚举设备堆栈判断disk是否是usbstor类型.,然后在枚举它的分区对象和对应的卷对象,然后在挂载 另外移动方式的u盘很好容易识别了。 |
|
7楼#
发布于:2008-01-05 23:15
判断一下instantpath应该也可以
|
|
8楼#
发布于:2008-01-04 22:49
irp_mj_write本来就运行在PASS_LEVEL上,之所以蓝屏的原因之一是因为在sfWrite()中
不能使用 Irp->IoStatus.Status = STATUS_ACCESS_DENIED; Irp->IoStatus.Information = 0; IoCompleteRequest( Irp, IO_NO_INCREMENT ); return Irp->IoStatus.Status; 来简单的废除一个IRP。你可以屏蔽掉其他语句,直接在sfWrite()中使用上面的程序,看你的机器挂不挂?关于如何在SfWrite中废除一个IRP,请搜索我以前发过的帖子。 判断是否是移动设备,没那么复杂吧?在mount中判断 StorageDeviceobject-> NextDeviceObject->Characteristics == FILE_REMOVABLE_MEDIA |
|
9楼#
发布于:2007-12-28 10:46
可以探讨这个问题。
|
|
|
10楼#
发布于:2007-03-14 19:21
就是以上代码我加入条件判断IRQL在PASIVE_LEVEL还是会出现一样的问题,我没试过在SfFsControlMountVolumeComplete中调用,但在SfFsControlMountVolume中调用还是出现一样的问题,我也知道在sfwrite中这样调用很消耗资源,我也是试试~~可老是出问题,都不知道为什么了!
|
|
11楼#
发布于:2007-03-14 08:50
IoBuildDeviceIoControlRequest必须在PASSIVE_LEVEL下运行,你的IRQL太高了,不应该在SfWrite时获取,而且每次都要发一遍IRP,多不经济啊。看看标题,说的是在mount的时候获取,所以在SfFsControlMountVolumeComplete里面调吧,然后把它作为DeviceExtension的一个成员属性记下来,SfWrite的时候判断一下就好了。
我也是新手,刚学了点就来现学现卖了,呵呵。 |
|
12楼#
发布于:2007-03-10 12:08
下面是我的代码:
NTSTATUS SfWrite(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { ULONG DeviceTypeNum; VALIDATE_IRQL(Irp); // // If this is for our control device object, fail the operation // if (IS_MY_CONTROL_DEVICE_OBJECT(DeviceObject)) { Irp->IoStatus.Status = STATUS_INVALID_DEVICE_REQUEST; Irp->IoStatus.Information = 0; IoCompleteRequest( Irp, IO_NO_INCREMENT ); return STATUS_INVALID_DEVICE_REQUEST; } ASSERT(IS_MY_DEVICE_OBJECT( DeviceObject )); // // Get this driver out of the driver stack and get to the next driver as // quickly as possible. // KdPrint(("SFPASSTHROUGH")); if(USBFlag == READONLY) { DeviceTypeNum = GetStorageDeviceBusType( ((PSFILTER_DEVICE_EXTENSION) DeviceObject->DeviceExtension)->AttachedToDeviceObject); if(DeviceTypeNum == 7) { Irp->IoStatus.Status = STATUS_ACCESS_DENIED; Irp->IoStatus.Information = 0; IoCompleteRequest( Irp, IO_NO_INCREMENT ); return Irp->IoStatus.Status; } } IoSkipCurrentIrpStackLocation( Irp ); // // Call the appropriate file system driver with the request. // return IoCallDriver( ((PSFILTER_DEVICE_EXTENSION) DeviceObject->DeviceExtension)->AttachedToDeviceObject, Irp ); } ///////////////////////////////////////////////////////////////// ////////////////////////GetStorageDeviceBusType///////////////////////// ///////////////////////////////////////////////////////////////// ULONG GetStorageDeviceBusType(IN PDEVICE_OBJECT DeviceObject) { PIRP NewIrp; PSTORAGE_DEVICE_DESCRIPTOR Descriptor; STORAGE_PROPERTY_QUERY Query; UCHAR Buffer[sizeof(STORAGE_DEVICE_DESCRIPTOR)]; KEVENT WaitEvent; NTSTATUS Status; IO_STATUS_BLOCK IoStatus; // first set the query properties Query.PropertyId = StorageDeviceProperty; Query.QueryType = PropertyStandardQuery; // initialize the waitable event KeInitializeEvent(&WaitEvent, NotificationEvent, FALSE); // we should build the query irp ourselves NewIrp = IoBuildDeviceIoControlRequest(IOCTL_STORAGE_QUERY_PROPERTY, DeviceObject, (PVOID)&Query, sizeof(Query), (PVOID)Buffer, sizeof(Buffer), FALSE, &WaitEvent, &IoStatus); if (NULL == NewIrp) // can't create new irp { DbgPrint("[%s] [%u] I can't create a new irp to query the property of device (%p)!\n", __FILE__, __LINE__, DeviceObject); return BusTypeUnknown; } // send this irp to the storage device Status = IoCallDriver(DeviceObject, NewIrp); if (Status == STATUS_PENDING) { Status = KeWaitForSingleObject(&WaitEvent, Executive, KernelMode, FALSE, NULL); Status = IoStatus.Status; } if (!NT_SUCCESS(Status)) { DbgPrint("[%s] [%u] Query IOCTL_STORAGE_QUERY_PROPERTY of device (%p) failed, Status=0x%08X!\n", __FILE__, __LINE__, DeviceObject, Status); return BusTypeUnknown; } Descriptor = (PSTORAGE_DEVICE_DESCRIPTOR)Buffer; return Descriptor->BusType; } 为什么我用以上的代码,softice就会在IoCallDriver(DeviceObject, NewIrp);后说什么缺页错误?请高手指点一下. |
|
13楼#
发布于:2007-03-09 14:58
为什么我在irp-mj-write的例成里面使用上面的函数一到iocalldriver时就会蓝屏?
|
|
14楼#
发布于:2007-03-06 23:21
不错, 不错!
![]() ![]() |
|
|
15楼#
发布于:2007-03-05 20:10
顺便说一下,BusType=3是一般硬盘,BusType=7是USB接口设备,不过在VMWare下测试的时候获得的U盘总线类型是很奇怪的大数,让我一度以为代码哪里出错了。
|
|
16楼#
发布于:2007-03-05 20:05
试了一下,用IoBuildDeviceIoControlRequest向下层存储设备的DeviceObject发送一个代码为IOCTL_STORAGE_QUERY_PROPERTY的IRP_MJ_DEVICE_IO_CONTROL的Irp能获取到。
代码示例: ULONG GetStorageDeviceBusType(IN PDEVICE_OBJECT DeviceObject) { PIRP NewIrp; PSTORAGE_DEVICE_DESCRIPTOR Descriptor; STORAGE_PROPERTY_QUERY Query; CHAR Buffer[BUFFER_SIZE]; KEVENT WaitEvent; NTSTATUS Status; IO_STATUS_BLOCK IoStatus; // first set the query properties Query.PropertyId = StorageDeviceProperty; Query.QueryType = PropertyStandardQuery; // initialize the waitable event KeInitializeEvent(&WaitEvent, NotificationEvent, FALSE); // we should build the query irp ourselves NewIrp = IoBuildDeviceIoControlRequest(IOCTL_STORAGE_QUERY_PROPERTY, DeviceObject, (PVOID)&Query, sizeof(Query), (PVOID)Buffer, NAME_BUFFER_SIZE, FALSE, &WaitEvent, &IoStatus); if (NULL == NewIrp) // can't create new irp { DbgPrint("[%s] [%u] I can't create a new irp to query the property of device (%p)!\n", __FILE__, __LINE__, DeviceObject); return BusTypeUnknown; } // send this irp to the storage device Status = IoCallDriver(DeviceObject, NewIrp); if (Status == STATUS_PENDING) { Status = KeWaitForSingleObject(&WaitEvent, Executive, KernelMode, FALSE, NULL); Status = IoStatus.Status; } if (!NT_SUCCESS(Status)) { DbgPrint("[%s] [%u] Query IOCTL_STORAGE_QUERY_PROPERTY of device (%p) failed, Status=0x%08X!\n", __FILE__, __LINE__, DeviceObject, Status); return BusTypeUnknown; } Descriptor = (PSTORAGE_DEVICE_DESCRIPTOR)Buffer; return Descriptor->BusType; } |
|
17楼#
发布于:2007-03-02 10:51
我在本版帖过应用层的代码,判断总经理类型.
其实给设备发一个ioctl就可以知道总线类型 |
|
|
18楼#
发布于:2007-03-02 10:34
我在应用层上用判断总线的方法搞定了,然后就进行了一次能信,写到了动里。没有在驱动里直接做,如果需要的话,我有代码,不过,不是原创的。。。。
|
|
|
19楼#
发布于:2007-02-28 11:06
各位老大, 说下判断总线类型的嘛??
|
|
|
上一页
下一页