VeraCrypt
aboutsummaryrefslogtreecommitdiff
path: root/src/Common/libzip/zip_algorithm_deflate.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/Common/libzip/zip_algorithm_deflate.c')
-rw-r--r--src/Common/libzip/zip_algorithm_deflate.c106
1 files changed, 66 insertions, 40 deletions
diff --git a/src/Common/libzip/zip_algorithm_deflate.c b/src/Common/libzip/zip_algorithm_deflate.c
index d28a1ac5..3c85e204 100644
--- a/src/Common/libzip/zip_algorithm_deflate.c
+++ b/src/Common/libzip/zip_algorithm_deflate.c
@@ -1,9 +1,9 @@
/*
zip_algorithm_deflate.c -- deflate (de)compression routines
- Copyright (C) 2017-2019 Dieter Baron and Thomas Klausner
+ Copyright (C) 2017-2021 Dieter Baron and Thomas Klausner
This file is part of libzip, a library to manipulate ZIP archives.
- The authors can be contacted at <libzip@nih.at>
+ The authors can be contacted at <info@libzip.org>
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
@@ -40,27 +40,44 @@
struct ctx {
zip_error_t *error;
bool compress;
- int compression_flags;
+ int level;
+ int mem_level;
bool end_of_input;
z_stream zstr;
};
+static zip_uint64_t
+maximum_compressed_size(zip_uint64_t uncompressed_size) {
+ /* max deflate size increase: size + ceil(size/16k)*5+6 */
+
+ zip_uint64_t compressed_size = uncompressed_size + (uncompressed_size + 16383) / 16384 * 5 + 6;
+
+ if (compressed_size < uncompressed_size) {
+ return ZIP_UINT64_MAX;
+ }
+ return compressed_size;
+}
+
+
static void *
-allocate(bool compress, int compression_flags, zip_error_t *error) {
+allocate(bool compress, zip_uint32_t compression_flags, zip_error_t *error) {
struct ctx *ctx;
if ((ctx = (struct ctx *)malloc(sizeof(*ctx))) == NULL) {
- zip_error_set(error, ZIP_ET_SYS, errno);
- return NULL;
+ zip_error_set(error, ZIP_ET_SYS, errno);
+ return NULL;
}
ctx->error = error;
ctx->compress = compress;
- ctx->compression_flags = compression_flags;
- if (ctx->compression_flags < 1 || ctx->compression_flags > 9) {
- ctx->compression_flags = Z_BEST_COMPRESSION;
+ if (compression_flags >= 1 && compression_flags <= 9) {
+ ctx->level = (int)compression_flags;
+ }
+ else {
+ ctx->level = Z_BEST_COMPRESSION;
}
+ ctx->mem_level = compression_flags == TORRENTZIP_COMPRESSION_FLAGS ? TORRENTZIP_MEM_LEVEL : MAX_MEM_LEVEL;
ctx->end_of_input = false;
ctx->zstr.zalloc = Z_NULL;
@@ -72,13 +89,15 @@ allocate(bool compress, int compression_flags, zip_error_t *error) {
static void *
-compress_allocate(zip_uint16_t method, int compression_flags, zip_error_t *error) {
+compress_allocate(zip_uint16_t method, zip_uint32_t compression_flags, zip_error_t *error) {
+ (void)method;
return allocate(true, compression_flags, error);
}
static void *
-decompress_allocate(zip_uint16_t method, int compression_flags, zip_error_t *error) {
+decompress_allocate(zip_uint16_t method, zip_uint32_t compression_flags, zip_error_t *error) {
+ (void)method;
return allocate(false, compression_flags, error);
}
@@ -96,40 +115,43 @@ general_purpose_bit_flags(void *ud) {
struct ctx *ctx = (struct ctx *)ud;
if (!ctx->compress) {
- return 0;
+ return 0;
}
- if (ctx->compression_flags < 3) {
- return 2 << 1;
+ if (ctx->level < 3) {
+ return 2 << 1;
}
- else if (ctx->compression_flags > 7) {
- return 1 << 1;
+ else if (ctx->level > 7) {
+ return 1 << 1;
}
return 0;
}
static bool
-start(void *ud) {
+start(void *ud, zip_stat_t *st, zip_file_attributes_t *attributes) {
struct ctx *ctx = (struct ctx *)ud;
int ret;
+ (void)st;
+ (void)attributes;
+
ctx->zstr.avail_in = 0;
ctx->zstr.next_in = NULL;
ctx->zstr.avail_out = 0;
ctx->zstr.next_out = NULL;
if (ctx->compress) {
- /* negative value to tell zlib not to write a header */
- ret = deflateInit2(&ctx->zstr, ctx->compression_flags, Z_DEFLATED, -MAX_WBITS, MAX_MEM_LEVEL, Z_DEFAULT_STRATEGY);
+ /* negative value to tell zlib not to write a header */
+ ret = deflateInit2(&ctx->zstr, ctx->level, Z_DEFLATED, -MAX_WBITS, ctx->mem_level, Z_DEFAULT_STRATEGY);
}
else {
- ret = inflateInit2(&ctx->zstr, -MAX_WBITS);
+ ret = inflateInit2(&ctx->zstr, -MAX_WBITS);
}
if (ret != Z_OK) {
- zip_error_set(ctx->error, ZIP_ER_ZLIB, ret);
- return false;
+ zip_error_set(ctx->error, ZIP_ER_ZLIB, ret);
+ return false;
}
@@ -143,15 +165,15 @@ end(void *ud) {
int err;
if (ctx->compress) {
- err = deflateEnd(&ctx->zstr);
+ err = deflateEnd(&ctx->zstr);
}
else {
- err = inflateEnd(&ctx->zstr);
+ err = inflateEnd(&ctx->zstr);
}
if (err != Z_OK) {
- zip_error_set(ctx->error, ZIP_ER_ZLIB, err);
- return false;
+ zip_error_set(ctx->error, ZIP_ER_ZLIB, err);
+ return false;
}
return true;
@@ -163,8 +185,8 @@ input(void *ud, zip_uint8_t *data, zip_uint64_t length) {
struct ctx *ctx = (struct ctx *)ud;
if (length > UINT_MAX || ctx->zstr.avail_in > 0) {
- zip_error_set(ctx->error, ZIP_ER_INVAL, 0);
- return false;
+ zip_error_set(ctx->error, ZIP_ER_INVAL, 0);
+ return false;
}
ctx->zstr.avail_in = (uInt)length;
@@ -185,44 +207,47 @@ end_of_input(void *ud) {
static zip_compression_status_t
process(void *ud, zip_uint8_t *data, zip_uint64_t *length) {
struct ctx *ctx = (struct ctx *)ud;
+ uInt avail_out;
int ret;
- ctx->zstr.avail_out = (uInt)ZIP_MIN(UINT_MAX, *length);
+ avail_out = (uInt)ZIP_MIN(UINT_MAX, *length);
+ ctx->zstr.avail_out = avail_out;
ctx->zstr.next_out = (Bytef *)data;
if (ctx->compress) {
- ret = deflate(&ctx->zstr, ctx->end_of_input ? Z_FINISH : 0);
+ ret = deflate(&ctx->zstr, ctx->end_of_input ? Z_FINISH : 0);
}
else {
- ret = inflate(&ctx->zstr, Z_SYNC_FLUSH);
+ ret = inflate(&ctx->zstr, Z_SYNC_FLUSH);
}
- *length = *length - ctx->zstr.avail_out;
+ *length = avail_out - ctx->zstr.avail_out;
switch (ret) {
case Z_OK:
- return ZIP_COMPRESSION_OK;
+ return ZIP_COMPRESSION_OK;
case Z_STREAM_END:
- return ZIP_COMPRESSION_END;
+ return ZIP_COMPRESSION_END;
case Z_BUF_ERROR:
- if (ctx->zstr.avail_in == 0) {
- return ZIP_COMPRESSION_NEED_DATA;
- }
+ if (ctx->zstr.avail_in == 0) {
+ return ZIP_COMPRESSION_NEED_DATA;
+ }
- /* fallthrough */
+ /* fallthrough */
default:
- zip_error_set(ctx->error, ZIP_ER_ZLIB, ret);
- return ZIP_COMPRESSION_ERROR;
+ zip_error_set(ctx->error, ZIP_ER_ZLIB, ret);
+ return ZIP_COMPRESSION_ERROR;
}
}
/* clang-format off */
zip_compression_algorithm_t zip_algorithm_deflate_compress = {
+ maximum_compressed_size,
compress_allocate,
deallocate,
general_purpose_bit_flags,
@@ -236,6 +261,7 @@ zip_compression_algorithm_t zip_algorithm_deflate_compress = {
zip_compression_algorithm_t zip_algorithm_deflate_decompress = {
+ maximum_compressed_size,
decompress_allocate,
deallocate,
general_purpose_bit_flags,