我正在使用ZipArchive在 iOS 应用程序中提取 zip 文件,但我想在打开文件之前知道它是否受密码保护,以便我可以将密码传递给 UnZipOpenFile 函数。
问问题
2364 次
4 回答
4
zip 文件的密码不记录在标题中,它记录在 zip 中的单个文件条目中
所以你需要检查 zip 中的所有文件
将此功能添加到 ZipArchive
-(BOOL) UnzipIsEncrypted {
int ret = unzGoToFirstFile( _unzFile );
if (ret == UNZ_OK) {
do {
ret = unzOpenCurrentFile( _unzFile );
if( ret!=UNZ_OK ) {
return NO;
}
unz_file_info fileInfo ={0};
ret = unzGetCurrentFileInfo(_unzFile, &fileInfo, NULL, 0, NULL, 0, NULL, 0);
if (ret!= UNZ_OK) {
return NO;
}
else if((fileInfo.flag & 1) == 1) {
return YES;
}
unzCloseCurrentFile( _unzFile );
ret = unzGoToNextFile( _unzFile );
} while( ret==UNZ_OK && UNZ_OK!=UNZ_END_OF_LIST_OF_FILE );
}
return NO;
}
于 2012-12-18T16:57:00.390 回答
3
实际上,我在 zipArchive 中找不到检测文件是否已加密的功能,因此我检查了文件头以检查它是否受密码保护,如以下链接所述:
http://secureartisan.wordpress.com/2008/11/04/analysis-of-encrypted-zip-files/
-(BOOL) IsEncrypted:(NSString*)path
{
NSData* fileData = [NSData dataWithContentsOfFile:path];
NSData* generalBitFlag = [fileData subdataWithRange:NSMakeRange(6, 2)];
NSString* genralBitFlgStr = [generalBitFlag description];
if ([genralBitFlgStr characterAtIndex:2]!='0')
{
return true;
}
else
{
return false;
}
}
谢谢大家
于 2012-06-11T10:04:46.880 回答
2
我自己没有使用过 ZipArchive,但是通过查看代码,可以首先使用UnzipOpenFile
没有密码参数的变体并尝试调用UnzipFileTo
. 如果失败,您重新打开,但输入密码并UnzipFileTo
再次调用。这样做的问题是您将无法区分无效的 zip 文件和使用无效的密码。
如果您真的需要知道文件是否已加密,您可以自己添加功能(未经测试的代码):
将此添加到unzip.c
minizip 中:
extern int ZEXPORT unzIsEncrypted (file)
unzFile file;
{
return ((unz_s*)file)->encrypted;
}
这要unzip.h
:
extern int ZEXPORT unzIsEncrypted OF((unzFile file));
这要ZipArchive.mm
:
- (BOOL)ZipIsEncrypted {
return unzIsEncrypted(_unzFile);
}
这要ZipArchive.h
:
- (BOOL)ZipIsEncrypted;
并在调用后使用UnzipFileTo
。
于 2012-06-07T16:13:42.397 回答
1
我正在解压缩超过 50mb 的加密文件,所以在 NSData 中加载完整文件对我来说是个问题。所以修改了答案,我用了这个:
-(BOOL) IsEncrypted:(NSString*)path
{
NSInteger chunkSize = 1024 //Read 1KB chunks.
NSFileHandle *handle = [NSFileHandle fileHandleForReadingAtPath:path];
NSData *fileData = [handle readDataOfLength:chunkSize];
NSData* generalBitFlag = [fileData subdataWithRange:NSMakeRange(6, 2)];
NSString* genralBitFlgStr = [generalBitFlag description];
if ([genralBitFlgStr characterAtIndex:2]!='0')
{
return true;
}
else
{
return false;
}
}
于 2014-03-25T11:29:46.560 回答