@@ -220,56 +220,91 @@ static void *compress_with_checksum(const void *original_data, size_t original_l
220220 return compressed_buffer ;
221221}
222222
223+ /*
224+ * This test validates that the flb_decompress API can seamlessly handle
225+ * three or more independent Zstd frames concatenated into a single buffer.
226+ */
223227void test_zstd_streaming_decompress_multi_chunk (void )
224228{
225- struct flb_decompression_context * ctx ;
226- char * output_buf ;
229+ int ret = 0 ;
230+ const char * original1 = "This is the first payload." ;
231+ const char * original2 = "This is the second, slightly longer payload." ;
232+ const char * original3 = "And this is the final, third payload." ;
233+ size_t original1_len = strlen (original1 );
234+ size_t original2_len = strlen (original2 );
235+ size_t original3_len = strlen (original3 );
236+ size_t max_original_len ;
237+
238+ void * compressed1 = NULL , * compressed2 = NULL , * compressed3 = NULL ;
239+ size_t compressed1_len = 0 , compressed2_len = 0 , compressed3_len = 0 ;
240+
241+ char * concatenated_buffer = NULL ;
242+ size_t concatenated_len = 0 ;
243+
244+ char * output_buffer = NULL ;
227245 size_t output_len ;
228- size_t total_written = 0 ;
229- int ret ;
230- size_t chunk1_size = 0 ;
231- size_t chunk2_size = 0 ;
232- size_t chunk3_size = 0 ;
233- char * original_text = "zstd streaming is a feature that must be tested with multiple, uneven chunks!" ;
234- size_t original_len ;
235- void * compressed_buf = NULL ;
236- size_t compressed_len = 0 ;
237246
238- original_len = strlen (original_text );
239- compressed_buf = compress_with_checksum (original_text , original_len , & compressed_len );
240- TEST_CHECK (compressed_buf != NULL );
247+ struct flb_decompression_context * ctx ;
241248
242- ctx = flb_decompression_context_create (FLB_COMPRESSION_ALGORITHM_ZSTD , compressed_len );
249+ flb_zstd_compress ((void * )original1 , original1_len , & compressed1 , & compressed1_len );
250+ TEST_CHECK (compressed1 != NULL );
251+
252+ flb_zstd_compress ((void * )original2 , original2_len , & compressed2 , & compressed2_len );
253+ TEST_CHECK (compressed2 != NULL );
254+
255+ flb_zstd_compress ((void * )original3 , original3_len , & compressed3 , & compressed3_len );
256+ TEST_CHECK (compressed3 != NULL );
257+
258+ concatenated_len = compressed1_len + compressed2_len + compressed3_len ;
259+ concatenated_buffer = flb_malloc (concatenated_len );
260+ TEST_CHECK (concatenated_buffer != NULL );
261+
262+ memcpy (concatenated_buffer , compressed1 , compressed1_len );
263+ memcpy (concatenated_buffer + compressed1_len , compressed2 , compressed2_len );
264+ memcpy (concatenated_buffer + compressed1_len + compressed2_len , compressed3 , compressed3_len );
265+
266+ flb_free (compressed1 );
267+ flb_free (compressed2 );
268+ flb_free (compressed3 );
269+
270+ /* Create context and append the entire concatenated buffer */
271+ ctx = flb_decompression_context_create (FLB_COMPRESSION_ALGORITHM_ZSTD , 0 );
243272 TEST_CHECK (ctx != NULL );
244- output_buf = flb_malloc (original_len + 1 );
245273
246- chunk1_size = compressed_len / 3 ;
247- chunk2_size = compressed_len / 2 ;
248- chunk3_size = compressed_len - chunk1_size - chunk2_size ;
274+ append_to_context (ctx , concatenated_buffer , concatenated_len );
249275
250- append_to_context (ctx , compressed_buf , chunk1_size );
251- output_len = original_len ;
252- ret = flb_decompress (ctx , output_buf , & output_len );
276+ /* Allocate an output buffer large enough for the biggest payload */
277+ max_original_len = original1_len ;
278+ if (original2_len > max_original_len ) max_original_len = original2_len ;
279+ if (original3_len > max_original_len ) max_original_len = original3_len ;
280+ output_buffer = flb_malloc (max_original_len );
281+ TEST_CHECK (output_buffer != NULL );
282+
283+ output_len = original1_len ;
284+ ret = flb_decompress (ctx , output_buffer , & output_len );
253285 TEST_CHECK (ret == FLB_DECOMPRESSOR_SUCCESS );
254- total_written += output_len ;
286+ TEST_CHECK (output_len == original1_len );
287+ TEST_CHECK (memcmp (original1 , output_buffer , original1_len ) == 0 );
255288
256- append_to_context (ctx , (char * )compressed_buf + chunk1_size , chunk2_size );
257- output_len = original_len - total_written ;
258- ret = flb_decompress (ctx , output_buf + total_written , & output_len );
289+ output_len = original2_len ;
290+ ret = flb_decompress (ctx , output_buffer , & output_len );
259291 TEST_CHECK (ret == FLB_DECOMPRESSOR_SUCCESS );
260- total_written += output_len ;
292+ TEST_CHECK (output_len == original2_len );
293+ TEST_CHECK (memcmp (original2 , output_buffer , original2_len ) == 0 );
261294
262- append_to_context (ctx , (char * )compressed_buf + chunk1_size + chunk2_size , chunk3_size );
263- output_len = original_len - total_written ;
264- ret = flb_decompress (ctx , output_buf + total_written , & output_len );
295+ output_len = original3_len ;
296+ ret = flb_decompress (ctx , output_buffer , & output_len );
265297 TEST_CHECK (ret == FLB_DECOMPRESSOR_SUCCESS );
266- total_written += output_len ;
298+ TEST_CHECK (output_len == original3_len );
299+ TEST_CHECK (memcmp (original3 , output_buffer , original3_len ) == 0 );
267300
268- TEST_CHECK (total_written == original_len );
269- TEST_CHECK (memcmp (original_text , output_buf , original_len ) == 0 );
301+ output_len = 1 ; /* Ask for one byte */
302+ ret = flb_decompress (ctx , output_buffer , & output_len );
303+ TEST_CHECK (ret == FLB_DECOMPRESSOR_SUCCESS );
304+ TEST_CHECK (output_len == 0 ); /* Should produce 0 bytes */
270305
271- flb_free (compressed_buf );
272- flb_free (output_buf );
306+ flb_free (concatenated_buffer );
307+ flb_free (output_buffer );
273308 flb_decompression_context_destroy (ctx );
274309}
275310
0 commit comments