- 浏览: 800634 次
- 性别:
- 来自: 广州
最新评论
-
mixture:
语句int num1, num2;的频度为1;语句i=0;的频 ...
算法时间复杂度的计算 [整理] -
zxjlwt:
学习了。http://surenpi.com
[问题解决]Error: ShouldNotReachHere() [整理] -
Animal:
谢谢 楼主 好东西
算法时间复杂度的计算 [整理] -
univasity:
gaidandan 写道缓存失败,,模拟器上可以缓存,同样代码 ...
[开发总结]WebView使用中遇到的一些问题&解决 -
blucelee2:
那么麻烦干吗,而且这种方法会导致,当拉太小的时候样式会丢掉,整 ...
[SWT]SashForm中固定单侧大小(&实现面板隐藏)
我在第一次使用 Everything 时,对其速度确实感到惊讶,后来了解到是通过操作 USN 实现的,并且有一定的局限性(只有 NTFS 下才能使用)。
近来清闲无事(失业了),搞些自己的小项目玩玩。其中也要处理到本地搜索这块,首先我想到的就是 Everything 。
我仔细地将官网和他论坛的帖子都看了遍,基本没找到什么讲到原理的。倒是官网上提供了一个 Everything 的 SDK 下载,是一个 IPC 的实现(我不是很懂,大概是程序关联之类的),需要 Everything 在后台跑才能调用操作。我也试了下效果,可以实现的,就是这样太麻烦了。
经过多日的搜搜,我发现了一个帖子,讨论的正是对 USN 的操作,同时我搜到了回帖者的 BLOG ,这一切让我有了开始的基础 …
言归正传:
初步认识 USN :
USN Journal 相当于 NTFS 的秘书,为他记录下改动的一切,并储存为 USN_RECORD 的格式。
更多的介绍请看以下链接:
Keeping an Eye on Your NTFS Drives: the Windows 2000 Change Journal Explained
下面来分享下近日研究的成果,一步步来探索 Everything 神奇的速度 USN的使用(Everything的快不单是用了USN,还需要建立索引,原来表达有误,改过来)
整个实现分为 6 步:
1. 判断驱动盘是否为 NTFS 格式
2. 获取驱动盘句柄
3. 初始化 USN 日志文件
4. 获取 USN 基本信息
5. 列出 USN 日志的所有数据
6. 删除 USN 日志文件
第一步:判断驱动盘是否 NTFS 格式
我们可以通过 GetVolumeInformation() 函数获取相关的信息进行判断。
可参考 MSDN : http://msdn.microsoft.com/en-us/library/aa364993%28VS.85%29.aspx
[[
这里我还找到了一个中文的说明:
GetVolumeInformation(
lpRootPathName: PChar; { 磁盘驱动器代码字符串}
lpVolumeNameBuffer: PChar; { 磁盘驱动器卷标名称}
nVolumeNameSize: DWORD; { 磁盘驱动器卷标名称长度}
lpVolumeSerialNumber: PDWORD; { 磁盘驱动器卷标序列号}
var lpMaximumComponentLength: DWORD; { 系统允许的最大文件名长度}
var lpFileSystemFlags: DWORD; { 文件系统标识}
lpFileSystemNameBuffer: PChar; { 文件操作系统名称}
nFileSystemNameSize: DWORD { 文件操作系统名称长度}
): BOOL;
上图可以看到,最后一个就是格式类型了,对应 lpFileSystemNameBuffer 。
]]
下面给出C++ 的实现作为参考:
/** * step 01. 判断驱动盘是否 NTFS 格式 */ char sysNameBuf[MAX_PATH] = {0}; int status = GetVolumeInformationA(volName, NULL, // 驱动盘名缓冲,这里我们不需要 0, NULL, NULL, NULL, sysNameBuf, // 驱动盘的系统名( FAT/NTFS) MAX_PATH); if (0!=status){ printf(" 文件系统名 : %s\n" , sysNameBuf); // 比较字符串 if (0==strcmp(sysNameBuf, "NTFS" )){ isNTFS = true ; }else { printf(" 该驱动盘非 NTFS 格式 \n" ); } }
USN Journal 并非一开始就存在的,需要手动打开。我们可以使用函数 DeviceIoControl() 并通过参数 FSCTL_CREATE_USN_JOURNAL 来操作。但仔细看 MSDN 会发现,需要先通过 CreateFile() 获取一个驱动盘的句柄。很多的后续操作都要用到这个句柄。
第二步:获取驱动盘句柄
可参考 MSDN : http://msdn.microsoft.com/en-us/library/aa363858%28VS.85%29.aspx
[[
对于我们目前的操作,注意看最后 Remarks ,
”Physical Disks and Volumes ” 中的一段:
The following requirements must be met for such a call to succeed:
- The caller must have administrative privileges. For more information, see Running with Special Privileges .
- The dwCreationDisposition parameter must have the OPEN_EXISTINGflag.
- When opening a volume or floppy disk, the dwShareMode parameter must have the FILE_SHARE_WRITEflag.
大概意思是,要成功执行需要满足一下条件:
1. 使用者需要获取管理员权限
2. dwCreationDisposition 参数 ( 倒数第三个 ) 必须带有 OPEN_EXISTIN 标识
3. 当打开一个驱动盘或软盘 , dwShareMode 参数 ( 第三个 ) 必须带有 FILE_SHARE_WRITE 标识
再有就是 ”Files ” 中的一段 :
Windows Server 2003 and Windows XP/2000:
If CREATE_ALWAYS and FILE_ATTRIBUTE_NORMAL are specified, CreateFile fails and sets the last error to ERROR_ACCESS_DENIED if the file exists and has the FILE_ATTRIBUTE_HIDDEN or FILE_ATTRIBUTE_SYSTEM attribute. To avoid the error, specify the same attributes as the existing file.
大概意思是:
在 windows2003,xp 和 2000 中如果设定了 CREATE_ALWAYS 和 FILE_ATTRIBUTE_NORMAL 两个属性,如果文件存在,并带有属性 FILE_ATTRIBUTE_HIDDEN 或 FILE_ATTRIBUTE_SYSTEM 的话, CreateFile 会失败,并且返回的错误信息为 ERROR_ACCESS_DENIED 。要避免这个错误,需要制定与文件本身相同的属性。
>> 所以我们这里尽量不使用 CREATE_ALWAYS 和 FILE_ATTRIBUTE_NORMAL 。我这里使用 FILE_ATTRIBUTE_HIDDEN 。
]]
照样贴上例子(我很少用 C++ ,写得不好,仅参考) :
/** * step 02. 获取驱动盘句柄 */ char fileName[MAX_PATH]; fileName[0] = '\0'; // 传入的文件名必须为\\.\C:的形式 strcpy(fileName, "\\\\.\\"); strcat(fileName, volName); // 为了方便操作,这里转为string进行去尾 string fileNameStr = (string)fileName; fileNameStr.erase(fileNameStr.find_last_of(":")+1); printf("驱动盘地址: %s\n", fileNameStr.data()); // 调用该函数需要管理员权限 hVol = CreateFileA(fileNameStr.data(), GENERIC_READ | GENERIC_WRITE, // 可以为0 FILE_SHARE_READ | FILE_SHARE_WRITE, // 必须包含有FILE_SHARE_WRITE NULL, // 这里不需要 OPEN_EXISTING, // 必须包含OPEN_EXISTING, CREATE_ALWAYS可能会导致错误 FILE_ATTRIBUTE_READONLY, // FILE_ATTRIBUTE_NORMAL可能会导致错误 NULL); // 这里不需要 if(INVALID_HANDLE_VALUE!=hVol){ getHandleSuccess = true; }else{ printf("获取驱动盘句柄失败 —— handle:%x error:%d\n", hVol, GetLastError()); }
第三步:打开 USN Journal 文件
MSDN : http://msdn.microsoft.com/en-us/library/aa364558%28v=VS.85%29.aspx
代码参考:
/** * step 03. 初始化USN日志文件 */ DWORD br; CREATE_USN_JOURNAL_DATA cujd; cujd.MaximumSize = 0; // 0表示使用默认值 cujd.AllocationDelta = 0; // 0表示使用默认值 status = DeviceIoControl(hVol, FSCTL_CREATE_USN_JOURNAL, &cujd, sizeof(cujd), NULL, 0, &br, NULL); if(0!=status){ initUsnJournalSuccess = true; }else{ printf("初始化USN日志文件失败 —— status:%x error:%d\n", status, GetLastError()); }
这时如果你能成功创建 USN 日志,那么对 USN 的探索即将开始 …
>> 目前你手上有的资源是 :
1. 某个 NTFS 驱动盘的 HANDLE;
2. 该驱动盘的 USN 日记已成功创建 .
--------------------------------------------- 未完待续 ------------------------------------------
发表评论
-
[问题解决]个推SDK使用侧记 -- 多个账号注册导致的问题
2013-12-28 14:40 2155这是我们项目最近用到的东西,用来实现消息推送。 (还不了 ... -
[问题解决] 个推(igetui)SDK使用侧记 -- 多个账号注册同一应用导致的问题
2013-12-28 14:33 0这是我们项目最近用到的东西,用来实现消息推送。 (还不了解 ... -
[SWT]打开Windows文件夹的方法 [整理]
2012-10-24 21:03 2451参考论坛帖子:http://www.iteye.com/top ... -
[SWT]SashForm中固定单侧大小(&实现面板隐藏)
2012-09-20 16:06 7008<!-- 额,发觉写篇博客都不知怎么选分类了。。。名称太 ... -
[Everything模仿] 相关项目资源整理
2012-04-29 20:04 3653一段时间来,发觉还是 ... -
[问题解决]Ubuntu10.04安装出现的显示器“无信号”问题
2011-12-11 20:42 4254<!-- 旧帖转移,2010-09-25 --> ... -
9个主流的开源许可协议[整理]
2011-12-05 23:15 29152关于开源许可 现今存在的开源协议很多,而经过 ... -
电子邮件收发原理和实现(POP3, SMTP) [整理]
2011-09-16 11:12 28193<!-- 最近工作上接触到了邮箱的开发,整理一下学到的东 ... -
讲解极小极大 (Minimax Explained) [译]
2011-09-11 21:00 6779原文链接:Minimax Explaine ... -
理解极小极大算法 (Understanding The Minimax Algorithm) [译]
2011-09-11 20:45 26961原文链接:Understanding Th ... -
Maven In Android
2011-08-31 17:32 3430Maven 一个项目管理工具,类似于Ant。相比Ant, ... -
[基础回顾]基于Eclipse的J2me和Android开发环境搭建
2011-03-23 00:10 1835<!-- 越是基础的东西就容易被忽略和轻视...我是接触 ... -
[SVN]423 Locked problem (Solved)
2011-03-03 17:15 8966今天使用SVN上传代码,突然冒出了一行红字... Se ... -
Everything研究之快速获取USN记录的文件路径
2011-01-06 17:04 8872<!-- 发觉越是没事干,记忆越差,乘还记得点什么,记录 ... -
Everything研究之读取NTFS下的USN日志文件(2)
2010-11-08 01:08 15615续>> /******************* ... -
[Swing]Netbean中使用外部资源
2010-10-22 15:43 1591要在NetBean中使用外部资源,首先需要在项目目录下创建一个 ... -
[Swing]实现一个文本自动完成工具
2010-10-17 00:00 3568//------------------------- ... -
[图形算法]J2me上的凹凸拼图实现思路
2010-04-05 21:31 6005出于个人兴趣,简单研究了一下凹凸拼图的实现。以下为本人的实现思 ... -
[特效研究]j2medev论坛里提到的一个显示特效实现
2010-03-14 16:05 2426原贴链接:http://www.j2medev.com/ ... -
[LUA]在eclipse中使用luajava
2009-10-17 23:23 4253<!--StartFragment--> st ...
相关推荐
原理是读取ntfs的USN文件日志,然后内建索引加速文件搜索过程。 1、列表文件支持批量处理(删除、复制、复制文件名路径、打开、重命名),或者引用系统菜单。 2、支持拼音首字母缩写搜索,指定文件夹内搜索,多...
原理是读取USN文件日志,然后内建索引加快文件搜索速度。 1、列表文件支持批量处理(删除、复制、复制文件名路径、打开、重命名),或者引用系统菜单。 2、支持拼音首字母缩写搜索,指定文件夹内搜索,多关键词搜索...
关于获取USN基本日志信息的C++ code block 上运行,因为是自己参照网上VC版本改编的可能会有些许疏漏。
Everything在首次使用时会建立一个索引数据库,通过读取NTFS USN日志来建立文件索引树,生成的索引文件非常小。在搜索栏中输入要搜索的文件名,瞬间就能够帮助你找到要找的文件。支持使用搜索语法及正则表达式语法...
原创资源物超所值.不使用任何jar包读取docx文件.Everything的java版本未完成但程序框架已经写出来了其中还包括java读取压缩文件解包压缩文件等各种文件操作类
这种快速,是因为Everything的索引无需逐一扫描硬盘文件,而是直接读取NTFS磁盘USN日志。这当然是既省力,又合理的做法。 第二个快速体现在搜索速度。在搜索框中键入字符后,搜索结果——或许称为过滤结果更准确...
原理是:Everything是靠读取NTFS文件系统中的USN日志来完成的,所以如果你的硬盘不是NTFS的,那就没有什么用了。 这是免安装版,解压使用时,默认是日文界面,要把那个.lng文件放到Everything的执行文件所在文件夹...
everything山寨版 源码 原理都是读取NTFS的USN信息
C#快速NTFS硬盘文件索引,基于 USN编程,范例很好,非本人原创。。。
这种快速,是因为Everything的索引无需逐一扫描硬盘文件,而是直接读取NTFS文件系统的USN日志。这当然是既省力,又合理的做法。 第二个快速体现在搜索速度。在搜索框中键入字符后,搜索结果——或许称为过滤结果更...
这种快速,是因为Everything的索引无需逐一扫描硬盘文件,而是直接读取NTFS文件系统的USN日志。这当然是既省力,又合理的做法。 第二个快速体现在搜索速度。在搜索框中键入字符后,搜索结果——或许称为过滤结果更...
用C++实现的基于NTFS下MFT和USN-Journal检索与类正则表达式-NFA-DFA字符串匹配的本地文件查找系统
此代码是基于VS2010,C#下的超级极速文件索引软件,可在10秒内整理出硬盘上的所有文件列表。对于研究USN编程具有很不错的指引。 只支持NTFS操作系统。 代码来源于网络,非本人原创。
由于WINDOWS自身搜软件快,软件源于读取NTFS文件系统中的USN日志来形成信息。
一款非常好用的日志分析工具(永久免费),这三个数据:“访问次数”、“总停留时间”和“总抓取量”,都是数字越高对网站越有利,所以需要想很多办法提高他们。大多数时候看他们绝对值没什么用处,而要看现在的和...
模拟everything的简单实现,大体思路: ntfs磁盘分区会有一个觉usn的日志系统,从这个日志系统中可以拿到类似全盘索引之类的数据,然后搜索时从这个数据格式出发,效率会比较高
华为MME USN9810硬件配置,最新架构的osta2.0介绍,基本的配置原则和步骤。
包含Everything工具和共享源码,以及NTFS磁盘搜索机制(USN MFT)的资料,希望能对有兴趣的同学提供帮助。
华为USN9810V900R011产品概述.pdf
usn日志获取完整demo