diff --git a/Release/src/http/common/http_compression.cpp b/Release/src/http/common/http_compression.cpp index d8c5a7340c..b814093d1b 100644 --- a/Release/src/http/common/http_compression.cpp +++ b/Release/src/http/common/http_compression.cpp @@ -89,7 +89,14 @@ class zlib_compressor_base : public compress_provider throw std::runtime_error("Prior unrecoverable compression stream error " + std::to_string(m_state)); } +#if defined(__clang__) +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wtautological-constant-compare" +#endif // __clang__ if (input_size > std::numeric_limits::max() || output_size > std::numeric_limits::max()) +#if defined(__clang__) +#pragma clang diagnostic pop +#endif // __clang__ { throw std::runtime_error("Compression input or output size out of range"); } @@ -183,7 +190,14 @@ class zlib_decompressor_base : public decompress_provider throw std::runtime_error("Prior unrecoverable decompression stream error " + std::to_string(m_state)); } +#if defined(__clang__) +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wtautological-constant-compare" +#endif // __clang__ if (input_size > std::numeric_limits::max() || output_size > std::numeric_limits::max()) +#if defined(__clang__) +#pragma clang diagnostic pop +#endif // __clang__ { throw std::runtime_error("Compression input or output size out of range"); } @@ -297,13 +311,13 @@ class brotli_compressor : public compress_provider uint32_t block = 0, uint32_t nomodel = 0, uint32_t hint = 0) - : m_algorithm(BROTLI) - , m_window(window) + : m_window(window) , m_quality(quality) , m_mode(mode) , m_block(block) , m_nomodel(nomodel) , m_hint(hint) + , m_algorithm(BROTLI) { (void)reset(); } @@ -518,6 +532,7 @@ class brotli_decompressor : public decompress_provider // have to first allocate a guaranteed-large-enough buffer and then copy out of it, or we'd have to call // reset() if it failed due to insufficient output buffer space (and we'd need to use // BrotliDecoderGetErrorCode() to tell if that's why it failed) + (void)hint; m_state = BrotliDecoderDecompressStream(m_stream, &avail_in, &next_in, &avail_out, &next_out, &total_out); if (m_state == BROTLI_DECODER_RESULT_ERROR) { diff --git a/Release/tests/functional/http/client/compression_tests.cpp b/Release/tests/functional/http/client/compression_tests.cpp index 0e7f0b91ea..5a08103198 100644 --- a/Release/tests/functional/http/client/compression_tests.cpp +++ b/Release/tests/functional/http/client/compression_tests.cpp @@ -181,19 +181,12 @@ SUITE(compression_tests) bool compressible) { std::vector input_buffer; - std::vector cmp_buffer; - std::vector dcmp_buffer; - operation_result r; - std::vector chunk_sizes; - size_t csize; - size_t dsize; size_t i; - size_t nn; VERIFY_ARE_EQUAL(compressor->algorithm(), decompressor->algorithm()); input_buffer.reserve(buffer_size); - for (size_t i = 0; i < buffer_size; ++i) + for (i = 0; i < buffer_size; ++i) { uint8_t element; if (compressible) @@ -209,59 +202,52 @@ SUITE(compression_tests) } // compress in chunks - csize = 0; - cmp_buffer.resize(buffer_size); // pessimistic (or not, for non-compressible data) - for (i = 0; i < buffer_size; i += chunk_size) + std::vector chunk_sizes; + std::vector cmp_buffer(buffer_size); + size_t cmpsize = buffer_size; + size_t csize = 0; + operation_result r = {0}; + operation_hint hint = operation_hint::has_more; + for (i = 0; i < buffer_size || csize == cmpsize || !r.done; i += r.input_bytes_processed) { + if (i == buffer_size) + { + // the entire input buffer has been consumed by the compressor + hint = operation_hint::is_last; + } + if (csize == cmpsize) + { + // extend the output buffer if there may be more compressed bytes to retrieve + cmpsize += std::min(chunk_size, (size_t)200); + cmp_buffer.resize(cmpsize); + } r = compressor ->compress(input_buffer.data() + i, std::min(chunk_size, buffer_size - i), cmp_buffer.data() + csize, - std::min(chunk_size, buffer_size - csize), - operation_hint::has_more) + std::min(chunk_size, cmpsize - csize), + hint) .get(); - VERIFY_ARE_EQUAL(r.input_bytes_processed, std::min(chunk_size, buffer_size - i)); - VERIFY_ARE_EQUAL(r.done, false); + VERIFY_IS_TRUE(r.input_bytes_processed == std::min(chunk_size, buffer_size - i) || + r.output_bytes_produced == std::min(chunk_size, cmpsize - csize)); + VERIFY_IS_TRUE(hint == operation_hint::is_last || !r.done); chunk_sizes.push_back(r.output_bytes_produced); csize += r.output_bytes_produced; } - if (i >= buffer_size) - { - size_t cmpsize = buffer_size; - do - { - if (csize == cmpsize) - { - // extend the output buffer if there may be more compressed bytes to retrieve - cmpsize += std::min(chunk_size, (size_t)200); - cmp_buffer.resize(cmpsize); - } - r = compressor - ->compress(NULL, - 0, - cmp_buffer.data() + csize, - std::min(chunk_size, cmpsize - csize), - operation_hint::is_last) - .get(); - VERIFY_ARE_EQUAL(r.input_bytes_processed, 0); - chunk_sizes.push_back(r.output_bytes_produced); - csize += r.output_bytes_produced; - } while (csize == cmpsize); - VERIFY_ARE_EQUAL(r.done, true); - - // once more with no input, to assure no error and done - r = compressor->compress(NULL, 0, NULL, 0, operation_hint::is_last).get(); - VERIFY_ARE_EQUAL(r.input_bytes_processed, 0); - VERIFY_ARE_EQUAL(r.output_bytes_produced, 0); - VERIFY_ARE_EQUAL(r.done, true); - } + VERIFY_ARE_EQUAL(r.done, true); + + // once more with no input or output, to assure no error and done + r = compressor->compress(NULL, 0, NULL, 0, operation_hint::is_last).get(); + VERIFY_ARE_EQUAL(r.input_bytes_processed, 0); + VERIFY_ARE_EQUAL(r.output_bytes_produced, 0); + VERIFY_ARE_EQUAL(r.done, true); cmp_buffer.resize(csize); // actual // decompress in as-compressed chunks - nn = 0; - dsize = 0; - dcmp_buffer.resize(buffer_size); + std::vector dcmp_buffer(buffer_size); + size_t dsize = 0; + size_t nn = 0; for (std::vector::iterator it = chunk_sizes.begin(); it != chunk_sizes.end(); ++it) { if (*it) @@ -358,7 +344,8 @@ SUITE(compression_tests) void compress_test(std::shared_ptr cfactory, std::shared_ptr dfactory) { - size_t tuples[][2] = {{7999, 8192}, + size_t tuples[][2] = {{3, 1024}, + {7999, 8192}, {8192, 8192}, {16001, 8192}, {16384, 8192},