阅读:10985回复:26
miniFilter下,文件透明加密文件大小返回的问题
我的透明加密加密标志放在文件头部,长度4K。现在经过测试,记事本和Office系列,AutoCAD都能正常加密解密。就是UltraEdit,写字板,打开文件后,文件内容是解密后的正确数据,但是,在正文后面,会有4K的空白区域,我觉得是这两个应用取到了实际的文件大小。
根据论坛上查找到的资料,我处理了IRP_MJ_QUERY_INFORMATION 的FileAllInformation(StandardInformation.EndOfFile 和AllocationSize ),FileAllocationInformation(AllocationSize ),FileValidDataLengthInformation (ValidDataLength ),FileStandardInformation (EndOfFile 和AllocationSize ),FileNetworkOpenInformation(AllocationSize ,EndOfFile ),IRP_MJ_DIRECTORY_CONTROL(FileBothDirectoryInformation )。跟踪观察,这些返回的数据都是我想要的结果。可为什么UltraEdit和写字板还是能够获取到实际文件的大小,搞不懂,难道他们是通过其他途径得到的文件大小? 下面是我的代码: SharePostQueryInfo: switch (FileInfoClass) { case FileAllInformation: { PFILE_ALL_INFORMATION psFileAllInfo = (PFILE_ALL_INFORMATION)FileInfoBuffer ; // 注意FileAllInformation,即使长度不够, // 依然可以返回前面的字节。 // 需要注意的是返回的字节里是否包含了StandardInformation // 这个可能影响文件的大小的信息。 if (Data->IoStatus.Information >= sizeof(FILE_BASIC_INFORMATION) + sizeof(FILE_STANDARD_INFORMATION)) { psFileAllInfo->StandardInformation.EndOfFile.QuadPart -= FILE_HEAD_LENGTH; psFileAllInfo->StandardInformation.AllocationSize.QuadPart -= FILE_HEAD_LENGTH; if(Data->IoStatus.Information >= sizeof(FILE_BASIC_INFORMATION) + sizeof(FILE_STANDARD_INFORMATION) + sizeof(FILE_INTERNAL_INFORMATION) + sizeof(FILE_EA_INFORMATION) + sizeof(FILE_ACCESS_INFORMATION) + sizeof(FILE_POSITION_INFORMATION)) { if(psFileAllInfo->PositionInformation.CurrentByteOffset.QuadPart >= FILE_HEAD_LENGTH) psFileAllInfo->PositionInformation.CurrentByteOffset.QuadPart -= FILE_HEAD_LENGTH; } } break ; } case FileAllocationInformation: { PFILE_ALLOCATION_INFORMATION psFileAllocInfo = (PFILE_ALLOCATION_INFORMATION)FileInfoBuffer; psFileAllocInfo->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; break ; } case FileValidDataLengthInformation: { PFILE_VALID_DATA_LENGTH_INFORMATION psFileValidLengthInfo = (PFILE_VALID_DATA_LENGTH_INFORMATION)FileInfoBuffer ; psFileValidLengthInfo->ValidDataLength.QuadPart -= FILE_HEAD_LENGTH; break ; } case FileStandardInformation: { PFILE_STANDARD_INFORMATION psFileStandardInfo = (PFILE_STANDARD_INFORMATION)FileInfoBuffer ; psFileStandardInfo->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; psFileStandardInfo->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; break ; } case FileEndOfFileInformation: { PFILE_END_OF_FILE_INFORMATION psFileEndInfo = (PFILE_END_OF_FILE_INFORMATION)FileInfoBuffer ; psFileEndInfo->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; break ; } case FilePositionInformation: { PFILE_POSITION_INFORMATION psFilePosInfo = (PFILE_POSITION_INFORMATION)FileInfoBuffer ; if(psFilePosInfo->CurrentByteOffset.QuadPart >= FILE_HEAD_LENGTH) psFilePosInfo->CurrentByteOffset.QuadPart -= FILE_HEAD_LENGTH; break ; } case FileNetworkOpenInformation: { PFILE_NETWORK_OPEN_INFORMATION psFileNetOpenInfo = (PFILE_NETWORK_OPEN_INFORMATION)FileInfoBuffer ; psFileNetOpenInfo->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; psFileNetOpenInfo->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; break ; } default: ASSERT(FALSE) ; }; SharePostDirCtrl是使用自带的SwapBuffer例子,只是在 RtlCopyMemory( origBuf, p2pCtx->SwappedBuffer, /*Data->IoStatus.Information*/ iopb->Parameters.DirectoryControl.QueryDirectory.Length );之前处理p2pCtx->SwappedBuffer,处理流程如下 switch (FileInfoClass) { case FileBothDirectoryInformation : { PFILE_BOTH_DIR_INFORMATION pbdi = (PFILE_BOTH_DIR_INFORMATION)pBuf; do { if (IsMyFile(pbdi)) { pbdi->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; pbdi->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; } if (!pbdi->NextEntryOffset) break; pbdi = (PFILE_BOTH_DIR_INFORMATION)((CHAR*)pbdi + pbdi->NextEntryOffset); } while (FALSE); break; } case FileDirectoryInformation : { PFILE_DIRECTORY_INFORMATION pfdi = (PFILE_DIRECTORY_INFORMATION)pBuf; do { if (IsMyFile(pfdi)) { pfdi->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; pfdi->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; } if (!pfdi->NextEntryOffset) break; pfdi = (PFILE_DIRECTORY_INFORMATION)((CHAR*)pfdi + pfdi->NextEntryOffset); } while (FALSE); break; } case FileFullDirectoryInformation : { PFILE_FULL_DIR_INFORMATION pffdi = (PFILE_FULL_DIR_INFORMATION)pBuf; do { if (IsMyFile(pffdi)) { pffdi->AllocationSize.QuadPart -= FILE_HEAD_LENGTH; pffdi->EndOfFile.QuadPart -= FILE_HEAD_LENGTH; } if (!pffdi->NextEntryOffset) break; pffdi = (PFILE_BOTH_DIR_INFORMATION)((CHAR*)pffdi + pffdi->NextEntryOffset); } while (FALSE); break; } default : break; } |
|
沙发#
发布于:2010-04-23 08:25
LZ可否将你的代码传我一份?谢谢!dongn0905@126.com
|
|
板凳#
发布于:2010-04-23 09:13
|
|
地板#
发布于:2010-04-23 22:15
memory manager gets file size from file context not from through IRPs.
|
|
地下室#
发布于:2010-04-24 10:55
那应该怎么做呢?修改FsContext?
|
|
5楼#
发布于:2010-05-06 19:10
决定一个文件的长度有很多方法的
你显然没有处理以下的方式: while(len = readfile) total += len |
|
6楼#
发布于:2010-05-11 11:23
回 5楼(bluacat) 的帖子
麻烦你能说的清楚一点吗,我不是太懂。 |
|
7楼#
发布于:2010-05-11 13:16
PreRead中应该也要处理一下:判断读取的offset是否已经超过了文件真正的内容长度,如果超过,直接返回成功,不需要再将irp下传了。
|
|
|
8楼#
发布于:2010-05-11 15:17
好像这样处理右键点属性,还是能看到4kb的文件头
|
|
9楼#
发布于:2010-05-12 17:31
楼主你改出来了吗,我的notepad也不行
|
|
10楼#
发布于:2010-05-12 17:51
回 8楼(crazy4stef) 的帖子
右键看到的文件大小是通过IRP_MJ_DIRECTORY_CONTROL的FileBothDirectoryInformation来处理的,但是这个时候文件对象无效,如果你要判断是否加密文件,就需要遍历读取所有结果集里面的文件判断是否加密文件,如果是酒需要减去加密标志头长度。shenhui说的我稍后试一下。我的WordPad和UltraEdit还是没解决。不知道是否有人能系统的说一下,加密标志在文件头的时候需要处理哪些文件长度信息才能完全隐藏文件头的大小。 |
|
11楼#
发布于:2010-05-12 18:32
4KB的空白区域应该是写的时候没写那么长,被对其到4kb去了,这里可能是cc把一个内存页面给purge到硬盘上
再调看看,楼主留个联系方式把,以后交流交流 |
|
12楼#
发布于:2010-05-12 23:25
I don't think there's good solution for this problem. I've repeated this many times already that only a real file system or a filter with its own FCB may solve this 文件透明加密 issue.
You may play with pre/post read/write. You may play with FCB. You may say it's working for most softwares including Word or VS. But for the past few years, I've seem so many failed filter drivers in production environment. The basic problem is that Windows FS, CMM and VMM are tightly coupled. Without ownership of file context, file-size-change is in conflict with Windows internal structure and synchronization mechanism especially. Hope someone can prove me wrong. So far, my thoughts got confirmed again and again...... |
|
13楼#
发布于:2010-05-13 08:38
啊。。。
那楼上有没有关于a filter with its own FCB的例子或资料? |
|
14楼#
发布于:2010-05-13 11:51
回 11楼(crazy4stef) 的帖子
QQ:94228827没太懂你说的情况,我的代码在上面有个链接里面,按你的说法其他程序或许也有这个问题,但是经过测试,Office2003系列和记事本,AutoCAD都没有问题 |
|
15楼#
发布于:2010-05-24 18:15
回 12楼(michaelgz) 的帖子
谢谢提醒,现在的问题是只能通过缓存管理器和虚拟内存管理器的修改来解决这个问题? |
|
16楼#
发布于:2010-05-27 13:37
http://www.osronline.com/showthread.cfm?link=178045
在OSRam找到了一个解决问题的帖子,但是不是太懂。希望有人给予指点。 |
|
17楼#
发布于:2010-05-27 22:42
That thread was talking about a file system. Unfortunately yours is not.
|
|
18楼#
发布于:2010-05-28 16:32
回 17楼(michaelgz) 的帖子
悲剧,这个问题搞的我快疯掉了。文件系统是使用CcSetFileSize来通知缓存管理器文件大小改变,我可不可以也使用这个来修改缓存管理器内保存的文件大小的值。如果可以,在什么时候修改可以达到这个目的? |
|
19楼#
发布于:2010-06-24 09:23
我测试了ReadFile,里面有个参数是返回读取了多少字节,这个值就是整个文件的大小(前提是传入的读取字节数大于整个文件的长度),但是读取的字节数不是从IOStatus的information来的吗,我的information值是期望的返回值啊,不知道这个值是从哪里来的。要不然这个information还有什么用呢。
微软的函数一塌糊涂。 |
|
上一页
下一页