@@ -134,7 +134,7 @@ handle_range_request(TSMBuffer req_buf, TSMLoc req_loc, HostConfiguration *hc)
134134
135135//  Forward declarations for ZSTD compression functions
136136#if  HAVE_ZSTD_H
137- static  void  zstd_compress_init (Data *data);
137+ static  void  zstd_compress_init (Data *data,  unsigned   long   long  content_size = ZSTD_CONTENTSIZE_UNKNOWN );
138138static  void  zstd_compress_finish (Data *data);
139139static  void  zstd_compress_one (Data *data, const  char  *upstream_buffer, int64_t  upstream_length);
140140#endif 
@@ -361,7 +361,6 @@ etag_header(TSMBuffer bufp, TSMLoc hdr_loc)
361361  return  ret;
362362}
363363
364- //  FIXME: some things are potentially compressible. those responses
365364static  void 
366365compress_transform_init (TSCont contp, Data *data)
367366{
@@ -389,7 +388,19 @@ compress_transform_init(TSCont contp, Data *data)
389388
390389#if  HAVE_ZSTD_H
391390  if  (data->compression_type  & COMPRESSION_TYPE_ZSTD) {
392-     zstd_compress_init (data);
391+     //  Try to get content length from response headers
392+     unsigned  long  long  content_size = ZSTD_CONTENTSIZE_UNKNOWN;
393+     TSMLoc content_length_loc       = TSMimeHdrFieldFind (bufp, hdr_loc, TS_MIME_FIELD_CONTENT_LENGTH, TS_MIME_LEN_CONTENT_LENGTH);
394+     if  (content_length_loc != TS_NULL_MLOC) {
395+       unsigned  int  hdr_value = TSMimeHdrFieldValueUintGet (bufp, hdr_loc, content_length_loc, -1 );
396+       if  (hdr_value > 0 ) {
397+         content_size = static_cast <unsigned  long  long >(hdr_value);
398+         debug (" Found content-length header: %llu" 
399+       }
400+       TSHandleMLocRelease (bufp, hdr_loc, content_length_loc);
401+     }
402+ 
403+     zstd_compress_init (data, content_size);
393404    if  (!data->zstrm_zstd .cctx ) {
394405      TSError (" Failed to create Zstandard compression context" 
395406      return ;
@@ -504,7 +515,7 @@ brotli_transform_one(Data *data, const char *upstream_buffer, int64_t upstream_l
504515
505516#if  HAVE_ZSTD_H
506517static  void 
507- zstd_compress_init (Data *data)
518+ zstd_compress_init (Data *data,  unsigned   long   long  content_size )
508519{
509520  if  (!data->zstrm_zstd .cctx ) {
510521    error (" Failed to initialize Zstd compression context" 
@@ -532,7 +543,25 @@ zstd_compress_init(Data *data)
532543    return ;
533544  }
534545
535-   debug (" zstd compression context initialized with level %d" hc ->zstd_compression_level ());
546+   //  Enable content size flag - this will include the content size in the frame header
547+   result = ZSTD_CCtx_setParameter (data->zstrm_zstd .cctx , ZSTD_c_contentSizeFlag, 1 );
548+   if  (ZSTD_isError (result)) {
549+     error (" Failed to enable Zstd content size flag: %s" ZSTD_getErrorName (result));
550+     return ;
551+   }
552+ 
553+   //  Set the pledged source size if known
554+   if  (content_size != ZSTD_CONTENTSIZE_UNKNOWN) {
555+     result = ZSTD_CCtx_setPledgedSrcSize (data->zstrm_zstd .cctx , content_size);
556+     if  (ZSTD_isError (result)) {
557+       error (" Failed to set Zstd pledged source size: %s" ZSTD_getErrorName (result));
558+       return ;
559+     }
560+     debug (" zstd compression context initialized with level %d and content size %llu" hc ->zstd_compression_level (),
561+           content_size);
562+   } else  {
563+     debug (" zstd compression context initialized with level %d (unknown content size)" hc ->zstd_compression_level ());
564+   }
536565}
537566
538567static  void 
0 commit comments