From 91fb3992ace293b9c6dc4a766f2777453769ab20 Mon Sep 17 00:00:00 2001 From: Benjamin Sergeant Date: Fri, 30 Oct 2020 18:28:11 -0700 Subject: [PATCH] (ws gunzip + IXGZipCodec) Can decompress gziped data with libdeflate. ws gunzip computed output filename was incorrect (was the extension aka gz) instead of the file without the extension. Also check whether the output file is writeable. --- docs/CHANGELOG.md | 4 ++++ ixwebsocket/IXGzipCodec.cpp | 29 +++++++++++++++++++++++++++++ ixwebsocket/IXWebSocketVersion.h | 2 +- makefile | 3 +++ ws/ws.cpp | 7 ++++++- 5 files changed, 43 insertions(+), 2 deletions(-) diff --git a/docs/CHANGELOG.md b/docs/CHANGELOG.md index ade3246b..77d6fcbe 100644 --- a/docs/CHANGELOG.md +++ b/docs/CHANGELOG.md @@ -2,6 +2,10 @@ All changes to this project will be documented in this file. +## [10.5.4] - 2020-10-30 + +(ws gunzip + IXGZipCodec) Can decompress gziped data with libdeflate. ws gunzip computed output filename was incorrect (was the extension aka gz) instead of the file without the extension. Also check whether the output file is writeable. + ## [10.5.3] - 2020-10-19 (http code) With zlib disabled, some code should not be reached diff --git a/ixwebsocket/IXGzipCodec.cpp b/ixwebsocket/IXGzipCodec.cpp index cb7f9766..8e3a153c 100644 --- a/ixwebsocket/IXGzipCodec.cpp +++ b/ixwebsocket/IXGzipCodec.cpp @@ -102,8 +102,36 @@ namespace ix #endif } +#ifdef IXWEBSOCKET_USE_DEFLATE + static uint32_t loadDecompressedGzipSize(const uint8_t* p) + { + return ((uint32_t) p[0] << 0) | ((uint32_t) p[1] << 8) | ((uint32_t) p[2] << 16) | + ((uint32_t) p[3] << 24); + } +#endif + bool gzipDecompress(const std::string& in, std::string& out) { +#ifdef IXWEBSOCKET_USE_DEFLATE + struct libdeflate_decompressor* decompressor; + decompressor = libdeflate_alloc_decompressor(); + + const void* compressed_data = in.data(); + size_t compressed_size = in.size(); + + // Retrieve uncompressed size from the trailer of the gziped data + const uint8_t* ptr = reinterpret_cast(&in.front()); + auto uncompressed_size = loadDecompressedGzipSize(&ptr[compressed_size - 4]); + + // Use it to redimension our output buffer + out.resize(uncompressed_size); + + libdeflate_result result = libdeflate_gzip_decompress( + decompressor, compressed_data, compressed_size, &out.front(), uncompressed_size, NULL); + + libdeflate_free_decompressor(decompressor); + return result == LIBDEFLATE_SUCCESS; +#else z_stream inflateState; memset(&inflateState, 0, sizeof(inflateState)); @@ -143,6 +171,7 @@ namespace ix inflateEnd(&inflateState); return true; +#endif } #endif } // namespace ix diff --git a/ixwebsocket/IXWebSocketVersion.h b/ixwebsocket/IXWebSocketVersion.h index 24c445dc..106dbfb7 100644 --- a/ixwebsocket/IXWebSocketVersion.h +++ b/ixwebsocket/IXWebSocketVersion.h @@ -6,4 +6,4 @@ #pragma once -#define IX_WEBSOCKET_VERSION "10.5.3" +#define IX_WEBSOCKET_VERSION "10.5.4" diff --git a/makefile b/makefile index 53bf9a3a..b1a730a4 100644 --- a/makefile +++ b/makefile @@ -250,6 +250,9 @@ doc: change: format vim ixwebsocket/IXWebSocketVersion.h docs/CHANGELOG.md +change_no_format: + vim ixwebsocket/IXWebSocketVersion.h docs/CHANGELOG.md + commit: git commit -am "`sh tools/extract_latest_change.sh`" diff --git a/ws/ws.cpp b/ws/ws.cpp index cfc0b018..7f9a9f69 100644 --- a/ws/ws.cpp +++ b/ws/ws.cpp @@ -152,7 +152,7 @@ namespace idx = path.rfind('.'); if (idx != std::string::npos) { - std::string filename = path.substr(idx + 1); + std::string filename = path.substr(0, idx); return filename; } else @@ -1220,6 +1220,11 @@ namespace ix std::ofstream f; f.open(outputFilename); + if (!f.is_open()) + { + spdlog::error("Cannot open {} for writing", outputFilename); + return 1; + } f << decompressedBytes; f.close();