Windows 7快速筛选文件

Windows 7快速筛选文件,第1张

Windows7的“库”不仅可以将某一类文件夹集中在一起,其实,文件库一个更强大的应用是将这些文件夹中的包含某一个关键字的文件都找出来,并“集中”管理。

1.找出包含某一关键字的全部文件

打开任意一个文件夹,从导航栏里找到“库”,单击其下的子文件库,在搜索栏里输入关键字(例如“摩擦力”)并按回车,很快,与这一关键词相关的文件将会全部找出来。

由于Win 7的搜索功能默认会将文件库当中的.文件纳入到索引中,因此文件库当中的搜索既会按文件名进行,又会按文件内容进行。搜索完毕后单击“保存搜索”,名为“摩擦力”的搜索结果将保存下来。今后,只要双击保存过的搜索结果,即可将该搜索结果当中的文件全部找出来,而不需要再次搜索,可谓一劳永逸。

2.增加筛选条件,显示特定文件

根据上面的介绍,只要包含搜索关键字的文档都会被罗列出来,那么我们如何查看某一类特定的文件呢?其实只要在前面的搜索基础上世改闹加入搜罩这一筛选条件即可。

双击前面保存过的搜索结果,在排序按钮一栏中找到“类型”,勾选其下的“Microsoft Office Word 97 – 2003文件”,这样就只有Word文档才会显示出来。这里的类型选项,Win 7会自动识别搜索结果当中所包含的所有文件的类型,因此,只需要通过选择就可以轻松实现查看该搜索结果当中某一特定类型的文件。

此外,我们还可以根据其他条件来进行筛选。比如对于照片文件,可添加光圈、快门等筛选条件;对邮件,可按发件人、收件人进行筛选。如果筛选按钮中没有出现你所需的条件,还可以右击排序按钮再选择“其它”来添加。

Win 7的文件库可以帮助我们更好地管理电脑中的文件,通过文件库搜索,可以将分散的文档集中在一起,对于文件的管理也更加一目了然,而通过不同条件的筛选,则可以进一步实现无用信息的快速过滤。可以说Win 7的文件库为我们提供了一种新的文件管理方歼禅式,如果你是一个不太有条理的人,那么文件库就是你一定要好好地用上一用的了!

1、获得文件全路径以及判断时机

除在所有 IRP_MJ_XXX 之前自己从头创建 IRP 发送到下层设备查询全路径外,不要尝试在 IRP_MJ_CREATE 以外的地方获得全路径,因为只有在 IRP_MJ_CREATE

中才会使用 ObCreateObject() 来建立一个有效的 FILE_OBJECT。而在 IRP_READ IRP_WRITE 中它们是直接 *** 作 FCB (File Control Block)的。

2、从头建立 IRP 发送关注点

无论你建立什么样的 IRP,是 IRP_MJ_CREATE 也好还是 IRP_MJ_DIRECTORY_CONTROL也罢,最要提醒的就是一些标志。不同的标志会代来不同的结果,有些结果是直接返回失败。这里指的标志不光是 IRP->Flags,还要考虑 IO_STACK_LOCATION->Flags还有其它等等。尤其是你要达到一些特殊目的,这时候更需要注意,如 IRP_MN_QUERY_DIRECTORY,不同的标志结果有很大的不同。

3、从头建立 IRP 获取全路径注意点

自己从头建立一个 IRP_MJ_QUERY_INFORMATION 的 IRP 获取全路径时需要注意,不仅在 IRP_MJ_CREATE 要做区别处理,在 IRP_MJ_CLOSE 也要做同样的处理,否则如果目标是 NTFS 文件系统的话可能产生 deadlock。如果是 NTFS 那么在 IRP_MJ_CLEANUP 的时候也需要对 FO_STREAM_FILE 类型的文件做同样处理。

4、获得本地/远程访问用户名(域名/SID)

方法只有在 IRP_MJ_CREATE 中才可用,那是因为 IO_SECURITY_CONTEXT 只有在 IO_STACK_LOCATION->Parameters.Create.SecurityContext 才会有效。这样你才有可能从 IO_SECURITY_CONTEXT->SecurityContext->AccessState->SubjectSecurityContext.XXXToken 中获得访问 TOKEN,从而进一步得到用户名或 SID。记得 IFS 中有一个库,它的 LIB 导出一个函数可以让你在获得以上信息后得到用户名与域名。但如果你想兼容 NT4 的话,只能自己分析来得出本地和远程的 SID。

5、文件与目录的判断

正确的方法在楚狂人的文档里已经说过了,再补充一句。如果你的文件过滤驱动要兼容所有文件系统,那么不要神耐桐十分相信从 FileObject->FsContext 里取得的数据。正确的方法还是在你传递下去 IRP_MJ_CREATE 后从最下层文件系统延设备栈返回到你这里后再获得。

6、加/解密中判断点

只判断 IRP_PAGING_IO,IRP_SYNCHRONOUS_PAGING_IO,IRP_NOCACHE 是没错的。如果有问题,相信是自己的问题。关于有人提到在 FILE_OBJECT->Flags中的 FO_NO_INTERMEDIATE_BUFFERING 是否需要判断,对此问题的回答是只要你判断了 IRP_NOCACHE 就不用再判断 FILE_OBJECT 中的,因为它最终会设置 IRP->Flags 为 IRP_NOCACHE。关于你看到的诸如 IRP_DEFER_IO_COMPLETION 等 IRP 不要去管它,因为它只是一个过程。最游坦终读写还是如上所介绍。至于以上这些 IRP 哪个是由 CC MGR 发送的,哪些是由 I/O MGR 发送和在什么时候发送的,这个已经有很多讨论了,相信可以找到。

7、举例说明关于 IRP 传递与完成注意事项

只看 Walter Oney 的那本 《Programming the Microsoft Windows driver model》里介绍的流程,自己没有实际的体会还是不够的,那里只介绍了基础概念,让自己有了知识。知道如何用,在什么情况下用,用哪种方法,能够用的稳定这叫有了技术。我们从另一个角度出发,把问题分为两段来看,这样利于总结。一个 IRP 在过滤驱动中,把它分为需要亩纯安装 CompleteRoutine 的与无需安装 CompleteRoutine 的。那么在不需要安装 CompleteRoutine 的有以下几类情况。

(1) 拿到这个 IRP 后什么都不做,直接调用 IoCompleteRequest() 来返回。

(2) 拿到这个 IRP 后什么都不做,直接传递到底层设备,使用IoSkipCurrentIrpStackLocation() 后调用 IoCallDriver() 传递。

(3) 使用 IoBuildSynchronousFsdRequest() 或 IoBuildDeviceIoControlRequest()来建立 IRP 的。

以上几种根据需要直接使用即可,除了一些参数与标志需要注意外,没有什么系统机制相关的东西需要注意了。那么再来看需要安装 CompleteRoutine 的情况。我们把这种情况再细分为两种,一是在 CompleteRoutine 中返回标志为STATUS_MORE_PROCESSING_REQUIRED 的情况。二是返回处这个外的标志,需要使用函数IoMarkIrpPending() 的情况。在 CompleteRoutine 中绝大多数就这么两种情况,你需要使用其中的一种情况。那么为什么需要安装 CompleteRoutine 呢?那是因为我们对其 IRP 从上层驱动,经过我们驱动,在经过底层设备栈返回到我们这一层驱动时需要得到其中内容作为参考依据的,还有对其中内容需要进行修改的。再有一种情况是没有经过上层驱动,而 IRP 的产生是在我们驱动直接下发到底层驱动,而经过设备栈后返回到我们这一层,且我们不在希望它继续向上返回的,因为这个 IRP 本身就不是从上层来的。综上所述,先来看下 IoMarkIrpPending() 的情况。

(1) 在 CompleteRoutine 中判断 Irp->PendingReturned 并使用 IoMarkIrpPending()然后返回。这种方法在没有使用 KeSetEvent() 的情况下,且不是自建 IRP 发送到底层驱动返回时使用。也就是说有可能我所做的工作都是在 CompleteRoutine 中进行的。比如加/解密时,我在这里对下层驱动返回数据的判断并修改。修改后因为没有使用 STATUS_MORE_PROCESSING_REQUIRED 标志,它会延设备堆一直向上返回并到用户得到数据为止。这里一定要注意,在这种情况下 CompleteRoutine返回后,不要在碰这个 IRP。也就是说如果这个时候你使用了 IoCompleteRequest()的话会出现一个 MULTIPLE_IRP_COMPLIETE_REQUEST 的 BSOD 错误。

(2) 在 CompleteRoutine 中直接返回 STATUS_MORE_PROCESSING_REQUIRED 标志。这种情况在使用了 KeSetEvent() 的函数下出现。这里又有两个小小的分之。

1) 出现于上层发送到我这里,当我这里使用 IoCallDriver() 后,底层返回数据经过我这一层时,我想让它暂时停止继续向上传递,让这个 IRP 稍微歇息一会,等我对这个 IRP 返回的数据 *** 作完成后(一般是没有在 CompleteRoutine中对返回数据进行 *** 作情况下,也就是说等到完成例程返回后再进行 *** 作),由我来调用 IoCompleteRequest() 让它延着设备栈继续返回。这里要注意,我们是想让它返回的,所以调用了 IoCompleteRequest()。这个可不同于下面所讲的自己从头分配 IRP 时在 CompleteRoutine 中已经调用 IoFreeIrp() 释放了当前IRP 的情况。比如我在做一个改变文件大小,向文件头写入加密标志的驱动时,在上层发来了 IRP_MJ_QUERY_INFORMATION 查询文件,我想在这个时候获得文件信息进行判断,然后根据我的判断结果再移动文件指针。注意:上面是两步,第一步是先获得文件大小,那么在这个时候我就需要用到上述办法,先让这个 IRP传递下去,得到我想要的东西后在进行对比。等待适当时机完成这个 IRP,让数据继续传递,直到用户收到为止。第二步我会结合下面小节来讲。

2) 出现于自己从头建立 IRP,当使用 IoAllocate() 或 IoBuildAsynchronousFsdRequest()创建 IRP 调用 IoCallDriver() 后,底层返回数据到我这一层时,我不想让这个 IRP 继续向上延设备栈传递。因为这个 IRP 就是在我这层次建立的,上层本就不知道有这么一个 IRP。那么到这里我就要在 CompleteRoutine 中使用 IoFreeIrp()来释放掉这个 IRP,并不让它继续传递。这里一定要注意,在 CompleteRoutine函数返回后,这个 IRP 已经释放了,如果这个时候在有任何关于这个 IRP 的 *** 作那么后果是灾难性的,必定导致 BSOD 错误。前面 1) 小节给出的例子只完成了第一步这里继续讲第二步,第一步我重用这个 IRP 得到了文件大小,那么这个时候虽然知道大小,但我还是无法知道这个文件是否被我加过密。这时,我就需要在这里自己从头建立一个 IRP_MJ_READ 的 IRP 来读取文件来判断是否我加密过了的文件,如果是,则要减少相应的大小,然后继续返回。注意:这里的返回是指让第一步的IRP 返回。而不是我们自己创建的。我们创建的都已经在CompleteRoutine 中销毁了。

8、关于完成 IRP 的动作简介

当一个底层驱动调用了 IoCompleteRequest() 函数时,基本上所有设备栈相关 IRP 处理工作都是在它那里完成的。包括 IRP->Flags 的一些标志的判断,对 APC 的处理,抛出MULTIPLE_IRP_COMPLETE_REQUESTS 错误等。当它延设备栈一直调用驱动所安装的 CompleteRoutine时,如果发现 STATUS_MORE_PROCESSING_REQUIRED 这个标志,则会停止向上继续回滚。这也是为什么在 CompleteRoutine 中使用这个标志即可暂停 IRP 的原因。

9、关于 ObQueryNameString 的使用

这个函数的使用,在有些环境下会有问题。它的上层函数是 ZwQueryObject()。在某些情况下会导致系统挂起,或者直接 BSOD。它是从 对象管理器中的 ObpRootDirectoryObject开始遍历,通过 OBJECT_HEADER_TO_NAME_INFO 获得对象名称。今天问了下 PolyMeta好象是在处理 PIPE 时会挂启,这个问题出现在 2000 系统。在 XP 上好象补丁了。

10、关于重入问题

其实这个问题在很久前的 IFS FAQ 里已经介绍的很清楚,包括处理方法以及每种方法可能带来的问题。IFS FAQ 里的 Q34 一共介绍了四种方法,包括自己从头建立 IRP发送,使用 ShadowDevice,使用特征字符串,根据线程 ID,在 XP 下使用IoCreateFileSpecifyDeviceObjectHint() 函数。并且把以上几种在不同环境下使用要处理的问题也做了简单的介绍。且在 Q33 里介绍了在 CIFS 碰到的 FILE_COMPLETE_IF_OPLOCKED 问题的解决方法。

1、打开文件资源管理器,切换到详细信息视图。

在 详细信息 视图下,文件资源管理器才会显示 名称、修改日期 等文件列表的标题,这也是实现文察辩核件筛选的前提。

2、以文件名为依据筛选。

我们点击 名称 列右侧的下拉箭头,会出现排序依据——按照先数字、后字母、再拼音首字母的依据排序。

我们选择 拼音 A - F 作为本次筛选的依据;我们发现地址栏中的文件位置(图中蓝色下划线的位置),也同时体现出了本次筛选的依据。

取消文件名筛选。

筛选过后,我们发现 名称 一列的右侧,原来的下拉箭头已经变成了对勾符号。我们只需再次点击它,在下拉列表中取消灶清对最近一次筛选依据的选择,文件夹就会返回到无筛选的原来状态。

对其他列进败掘行筛选。

当然,文件列表中的修改日期、类型、大小等列,也都是可以筛选的。

如图,我把上述三种筛选条件的下拉列表截图放到了一起。

多列复合筛选。

在对一列进行筛选之后,还可以以此为基础继续进行筛选。

如图,即是“拼音 T - Z 范围内的 Word 文档”这种复合筛选。

增加可用的筛选列。

如果当前的列无法满足筛选要求,可以点击文件资源管理器 查看 选项卡-->当前视图 组-->添加列 按钮,调出列标题选择的下拉列表,点选需要进行筛选的列,即可实现对该列或多列的筛选。


欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/tougao/12301775.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-24
下一篇 2023-05-24

发表评论

登录后才能评论

评论列表(0条)

保存