From a8219903cfce3f735e842afbf4ff442ce5358218 Mon Sep 17 00:00:00 2001 From: Jan Kasiak Date: Sun, 1 Sep 2019 15:35:53 -0400 Subject: [PATCH] Fix streaming compression/decompression examples * Handle compression of empty file * Error in decompression in case of trailing data --- examples/streaming_compression.c | 8 ++++++-- examples/streaming_decompression.c | 18 ++++++++++++++++++ 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/examples/streaming_compression.c b/examples/streaming_compression.c index d1353a684..d0b04895f 100644 --- a/examples/streaming_compression.c +++ b/examples/streaming_compression.c @@ -44,8 +44,8 @@ static void compressFile_orDie(const char* fname, const char* outName, int cLeve * and writes all output produced to the output file. */ size_t const toRead = buffInSize; - size_t read; - while ((read = fread_orDie(buffIn, toRead, fin))) { + for (;;) { + size_t read = fread_orDie(buffIn, toRead, fin); /* Select the flush mode. * If the read may not be finished (read == toRead) we use * ZSTD_e_continue. If this is the last chunk, we use ZSTD_e_end. @@ -76,6 +76,10 @@ static void compressFile_orDie(const char* fname, const char* outName, int cLeve } while (!finished); CHECK(input.pos == input.size, "Impossible: zstd only returns 0 when the input is completely consumed!"); + + if (lastChunk) { + break; + } } ZSTD_freeCCtx(cctx); diff --git a/examples/streaming_decompression.c b/examples/streaming_decompression.c index bcd861b75..d26b45b34 100644 --- a/examples/streaming_decompression.c +++ b/examples/streaming_decompression.c @@ -34,7 +34,10 @@ static void decompressFile_orDie(const char* fname) */ size_t const toRead = buffInSize; size_t read; + size_t lastRet = 0; + int isEmpty = 1; while ( (read = fread_orDie(buffIn, toRead, fin)) ) { + isEmpty = 0; ZSTD_inBuffer input = { buffIn, read, 0 }; /* Given a valid frame, zstd won't consume the last byte of the frame * until it has flushed all of the decompressed data of the frame. @@ -53,9 +56,24 @@ static void decompressFile_orDie(const char* fname) size_t const ret = ZSTD_decompressStream(dctx, &output , &input); CHECK_ZSTD(ret); fwrite_orDie(buffOut, output.pos, fout); + lastRet = ret; } } + if (isEmpty) { + fprintf(stderr, "input is empty\n"); + exit(1); + } + + if (lastRet != 0) { + /* The last return value from ZSTD_decompressStream did not end on a + * frame, but we reached the end of the file! We assume this is an + * error, and the input was truncated. + */ + fprintf(stderr, "EOF before end of stream: %zu\n", lastRet); + exit(1); + } + ZSTD_freeDCtx(dctx); fclose_orDie(fin); fclose_orDie(fout);