【windows内核驱动开发】文件系统微过滤驱动Minifilter——绑定指定的卷(磁盘分区)

来源:互联网 发布:东北大学网络教育查询 编辑:程序博客网 时间:2024/05/29 03:15

【我的】文件系统微过滤驱动Minifilter——绑定指定的卷(磁盘分区)

作者:zcr214 时间:2016/4/21

 

在编写文件系统微过滤驱动minifilter的时候,很有可能我们只对某一个特定的磁盘分区感兴趣,而其他的如系统盘的很多IRP对于我们要编写的驱动可能是不关注的,所以有必要使得我们的驱动只绑定指定的这个卷,从而减少其他的IRP带来的干扰,节省很多处理流程,比如系统盘的很多I/O请求。

1.    InstanceSetup回调函数

InstanceSetup回调函数的作用就是来决定是否绑定卷的。它在以下情况被调用:

(1)   当minifilter初次加载时,每个已存在的卷都会导致这个调用。

(2)   当一个新的卷被挂载时。

(3)   当FltAttachVolume被调用(内核模式)时。

(4)   当FltAttachVolumeAtAltitude被调用(内核模式)时。

(5)   当FilterAttach被调用(用户模式)时。

(6)   当FilterAttach被调用(用户模式)时。

在这个过程中,minifilter决定是否在这个卷上生成实例。函数原型为:

NTSTATUS

InstanceSetup(

    _In_PCFLT_RELATED_OBJECTS FltObjects,

    _In_FLT_INSTANCE_SETUP_FLAGS Flags,

    _In_DEVICE_TYPE VolumeDeviceType,

    _In_FLT_FILESYSTEM_TYPE VolumeFilesystemType

   );

 

这个回调函数的返回值为一个NTSTATUS状态值,表示绑定或者不绑定。

如果确认绑定,则返回STATUS_SUCCESS

如果不绑定,则返回STATUS_FLT_DO_NOT_ATTACH ,或者有警告或者错误,返回其他相应的状态,也是不绑定的。

 

参数解释:

(1)_In_PCFLT_RELATED_OBJECTS FltObjects 结构中含有指向minifilter,卷和实例的指针,这个实例是即将在此回调函数中生成的实例。定义为:

typedefstruct_FLT_RELATED_OBJECTS{

    USHORTCONSTSize;

    USHORTCONSTTransactionContext; //TxFmini-version

    PFLT_FILTERCONSTFilter;

    PFLT_VOLUMECONSTVolume;

    PFLT_INSTANCECONSTInstance;

    PFILE_OBJECTCONSTFileObject;

    PKTRANSACTIONCONSTTransaction;

}FLT_RELATED_OBJECTS,*PFLT_RELATED_OBJECTS;

 

(2)_In_FLT_INSTANCE_SETUP_FLAGS Flags标记是什么操作导致激发了InstanceSetup这个回调。

FLTFL_INSTANCE_SETUP_AUTOMATIC_ATTACHMENT标记是在minifilter注册时,一个自动的绑定通知,过滤管理器为刚加载的minifilter枚举所有的卷,如果使用者已经明确指定了一个实例绑定到某个卷,则不会设置这个标记。

FLTFL_INSTANCE_SETUP_MANUAL_ATTACHMENT标记是用户态调用FilterAttach或者FilterAttachAtAltitude,或者内核态调用FltAttachVolume时发起的手工请求。

FLTFL_INSTANCE_SETUP_NEWLY_MOUNTED_VOLUME标记是新挂载一个卷时发起的请求。

 

(3)_In_DEVICE_TYPEVolumeDeviceType参数传递卷设备类型,它是一个ULONG类型,具体定义如下图

总共有84种之多,针对文件系统的话一般的值是FILE_DEVICE_DISK_FILE_SYSTEM

(4)_In_FLT_FILESYSTEM_TYPE VolumeFilesystemType 参数传递卷文件系统类型,比如我们熟悉的NTFS,FAT32等等。是一个enum枚举类型,具体定义如下图

 

2.    绑定指定卷

绑定指定的卷,首先得确定哪一个卷才是需要绑定的。

利用InstanceSetup回调函数得到的参数卷设备类型VolumeDeviceType和卷文件系统类型VolumeFileSystemType可以筛选出基本的卷类型,做一个初步筛选。

接下来可以调用FltGetVolumeProperties函数来获取卷属性,基本用法在WDK的示例驱动中均有涉及,如下:

status=FltGetVolumeProperties(FltObjects->Volume,

                                        volProp,

                                        sizeof(volPropBuffer),

                                        &retLen);

返回是否获取成功的状态值,volProp即是获取到的卷属性,卷属性定义如下

typedefstruct_FLT_VOLUME_PROPERTIES{

    DEVICE_TYPEDeviceType;

    ULONGDeviceCharacteristics;

    ULONGDeviceObjectFlags;

    ULONGAlignmentRequirement;

    USHORTSectorSize;

    USHORTReserved0;

    UNICODE_STRINGFileSystemDriverName;

    UNICODE_STRINGFileSystemDeviceName;

    UNICODE_STRINGRealDeviceName;

}FLT_VOLUME_PROPERTIES,*PFLT_VOLUME_PROPERTIES;

可以利用卷属性中的这些信息锁定它是否是我们想要绑定的这个卷。

 

确定绑定卷之后,做完异常处理等,就可以返回STATUS_SUCCESS了,当然,如果不是我们想要绑定的卷,则返回STATUS_FLT_DO_NOT_ATTACH

 

简单的举例,比如在我的虚拟机win7上,D盘对应的卷名称是HarddiskVolume3,现在要绑定到D盘,则首先判断卷设备类型VolumeDeviceType是8(即FILE_DEVICE_DISK_FILE_SYSTEM),卷文件系统类型VolumeFileSystemType是2(即NTFS),然后调用FltGetVolumeProperties得到卷属性,取出RealDeviceName判断是否是\Device\HarddiskVolume3,最后返回STATUS_SUCCESS。就完成了这个驱动对D盘的绑定。当然这个过程中还有一些异常处理等操作。最后在WDK的示例驱动基础上修改。

 

 

 

0 0
原创粉丝点击