使用zlib解压缩zip文件。

13

我有一个archive.zip文件,其中包含两个加密的".txt"文件。我想解压缩该存档以获取这两个文件。

到目前为止,我已经做了以下工作:

FILE *FileIn = fopen("./archive.zip", "rb");
if (FileIn)
    printf("file opened\n");
else
    printf("unable to open file\n");

fseek(FileIn, 0, SEEK_END);
unsigned long FileInSize = ftell(FileIn);
printf("size of input compressed file : %u\n", FileInSize);

void *CompDataBuff = malloc(FileInSize);
void *UnCompDataBuff = NULL;

int fd = open ("archive.zip", O_RDONLY);
CompDataBuff = mmap(NULL, FileInSize, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0);
printf("buffer read : %s\n", (char *)CompDataBuff);

uLongf UnCompSize = (FileInSize * 11/10 + 12);
UnCompDataBuff = malloc(UnCompSize);

int ret_uncp ;

ret_uncp = uncompress((Bytef*)UnCompDataBuff, &UnCompSize, (const Bytef*)CompDataBuff,FileInSize);
printf("size of uncompressed data : %u\n", UnCompSize);

if (ret_uncp == Z_OK){
    printf("uncompression ok\n");
    printf("uncompressed data : %s\n",(char *)UnCompDataBuff);
    }
if (ret_uncp == Z_MEM_ERROR)
    printf("uncompression memory error\n");
if (ret_uncp == Z_BUF_ERROR)
    printf("uncompression buffer error\n");
if (ret_uncp == Z_DATA_ERROR)
    printf("uncompression data error\n");

我总是收到“数据解压错误”的提示,但不知道原因。现在我想知道如何检索我的数据并解压缩这两个文件。

4个回答

22

zip是一种文件格式,它在压缩数据流周围包装头部和尾部信息,以表示一组文件和目录。压缩的数据流几乎总是deflate数据流,实际上可以由zlib生成和解码。zlib还提供crc32函数,可用于在zip包装信息中生成和检查crc值。

zlib本身不会解码和分解zip结构。您可以编写自己的代码,使用规范(很容易做到)来执行此操作,或者您可以使用zlib distributioncontrib/minizip directory中的minizip例程,该例程提供打开、访问和关闭zip文件的功能。


1
谢谢。我添加了contrib/minizip头文件,并能够从zip文件中读取文件(在已经使用zlib的应用程序中)。我只需要编写一些简单的函数来包装对unzip.h接口的调用。 - Kenny Ostrom

10

Zlib并不是一个用于处理 .zip 文件的库。它支持解压缩 zlib 和 gzip 流,这两种流都是针对单个数据流而非类似于 .zip 的“归档”格式。

如果你需要打开和操作 .zip 归档,你需要使用另一个库(例如 libzip,还有许多其他库可供选择)。


哦,真的吗?我以为zlib可以处理.zip文件...不管怎样,谢谢你提供的信息! :) - user1336204
zlib实际上可以帮助处理zip文件,源代码分发版附带了处理zip文件的贡献代码。请参阅我的答案。 - Mark Adler

5
如前所述,zlib仅处理压缩,不进行归档。当您想要压缩或解压缩时,您正在从一个zip格式的存档中提取文件(还有其他格式,如rar、7zip等)。
如果您想创建zip文件或解压缩文件,则必须处理zip格式,而minizip是一个很好的库,强大且存在已经相当长的时间了。
有一个minizip的contrib https://github.com/nmoinvaz/minizip,其中包含如何使用它的示例。这并不难,您可以查看minizip.c和miniunz.c以获取有关如何使用它的代码。(Minizip使用zlib进行压缩) 此外,我最终构建了一个库,包装了minizip,并添加了一些不错的功能,使其更易于使用和面向对象化。让您可以做一些像压缩整个文件夹、流、向量等事情。以及完全在内存中执行所有操作。
带有示例的Repo在此处:https://github.com/sebastiandev/zipper Beta预发布:https://github.com/sebastiandev/zipper/releases/ 代码看起来像这样:
Zipper zipper("ziptest.zip");
zipper.add("somefile.txt");
zipper.add("myFolder");
zipper.close();


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接