unbro should not require maximum buffer size (RT #129480)
[io-compress-brotli.git] / Brotli.xs
index dff0a63f3b6017564e51b6582f683e28bcb19053..4e030a750b7cae5a5280c62bfe09b2029c765a2e 100644 (file)
--- a/Brotli.xs
+++ b/Brotli.xs
@@ -5,9 +5,8 @@
 
 #include "ppport.h"
 
-#include <dec/decode.h>
-#include <enc/encode.h>
-#include <common/dictionary.h>
+#include <brotli/decode.h>
+#include <brotli/encode.h>
 
 #define BUFFER_SIZE 1048576
 
@@ -24,24 +23,20 @@ MODULE = IO::Compress::Brotli               PACKAGE = IO::Uncompress::Brotli
 PROTOTYPES: ENABLE
 
 SV*
-unbro(buffer)
+unbro_given_size(buffer, decoded_size)
     SV* buffer
+    size_t decoded_size
   PREINIT:
-    size_t decoded_size;
     STRLEN encoded_size;
     uint8_t *encoded_buffer, *decoded_buffer;
   CODE:
     encoded_buffer = (uint8_t*) SvPV(buffer, encoded_size);
-    if(!BrotliDecompressedSize(encoded_size, encoded_buffer, &decoded_size)){
-        croak("Error in BrotliDecompressedSize");
-    }
-    Newx(decoded_buffer, decoded_size+1, uint8_t);
-    decoded_buffer[decoded_size]=0;
+    Newx(decoded_buffer, decoded_size, uint8_t);
     if(!BrotliDecoderDecompress(encoded_size, encoded_buffer, &decoded_size, decoded_buffer)){
         croak("Error in BrotliDecoderDecompress");
     }
     RETVAL = newSV(0);
-    sv_usepvn_flags(RETVAL, decoded_buffer, decoded_size, SV_HAS_TRAILING_NUL);
+    sv_usepvn(RETVAL, decoded_buffer, decoded_size);
   OUTPUT:
     RETVAL
 
@@ -73,8 +68,8 @@ decompress(self, in)
     next_in = (uint8_t*) SvPV(in, available_in);
     Newx(buffer, BUFFER_SIZE, uint8_t);
     RETVAL = newSVpv("", 0);
-    result = BROTLI_RESULT_NEEDS_MORE_OUTPUT;
-    while(result == BROTLI_RESULT_NEEDS_MORE_OUTPUT) {
+    result = BROTLI_DECODER_RESULT_NEEDS_MORE_OUTPUT;
+    while(result == BROTLI_DECODER_RESULT_NEEDS_MORE_OUTPUT) {
         next_out = buffer;
         available_out=BUFFER_SIZE;
         result = BrotliDecoderDecompressStream( self->decoder,
@@ -93,17 +88,6 @@ decompress(self, in)
   OUTPUT:
     RETVAL
 
-void
-set_dictionary(self, dict)
-    IO::Uncompress::Brotli self
-    SV* dict
-  PREINIT:
-    size_t size;
-    uint8_t *data;
-  CODE:
-    data = SvPV(dict, size);
-    BrotliDecoderSetCustomDictionary(self->decoder, size, data);
-
 
 MODULE = IO::Compress::Brotli          PACKAGE = IO::Compress::Brotli
 PROTOTYPES: ENABLE
@@ -122,7 +106,7 @@ bro(buffer, quality=BROTLI_DEFAULT_QUALITY, lgwin=BROTLI_DEFAULT_WINDOW)
     if( quality < BROTLI_MIN_QUALITY || quality > BROTLI_MAX_QUALITY ) {
         croak("Invalid quality value");
     }
-    if( lgwin < kBrotliMinWindowBits || lgwin > kBrotliMaxWindowBits ) {
+    if( lgwin < BROTLI_MIN_WINDOW_BITS || lgwin > BROTLI_MAX_WINDOW_BITS ) {
         croak("Invalid window value");
     }
     decoded_buffer = (uint8_t*) SvPV(buffer, decoded_size);
@@ -157,60 +141,80 @@ create(class)
   OUTPUT:
     RETVAL
 
-SV*
-window(self, window)
-    IO::Compress::Brotli self
-    U32 window
-  CODE:
-    if( window < kBrotliMinWindowBits || window > kBrotliMaxWindowBits ) {
-        croak("Invalid window value");
-    }
-    if( BrotliEncoderSetParameter(self->encoder, BROTLI_PARAM_LGWIN, window) )
-        RETVAL = newSVuv(1);
-    else
-        RETVAL = newSVuv(0);
-  OUTPUT:
-    RETVAL
-
-SV*
-quality(self, quality)
+bool BrotliEncoderSetParameter(self, value)
     IO::Compress::Brotli self
-    U32 quality
-  CODE:
-    if( quality < BROTLI_MIN_QUALITY || quality > BROTLI_MAX_QUALITY ) {
-        croak("Invalid quality value");
+    U32 value
+  ALIAS:
+    window  = 1
+    quality = 2
+    _mode   = 3
+  PREINIT:
+    BrotliEncoderParameter param;
+  INIT:
+    switch(ix){
+    case 0:
+        croak("BrotliEncoderSetParameter may not be called directly");
+        break;
+    case 1:
+        if( value < BROTLI_MIN_WINDOW_BITS || value > BROTLI_MAX_WINDOW_BITS ) {
+            croak("Invalid window value");
+        }
+        param = BROTLI_PARAM_LGWIN;
+        break;
+    case 2:
+        if( value < BROTLI_MIN_QUALITY || value > BROTLI_MAX_QUALITY ) {
+            croak("Invalid quality value");
+        }
+        param = BROTLI_PARAM_QUALITY;
+        break;
+    case 3:
+        /* Validation done on Perl side */
+        param = BROTLI_PARAM_MODE;
+        break;
+    default:
+        croak("Impossible ix in BrotliEncoderSetParameter");
+        break;
     }
-    if( BrotliEncoderSetParameter(self->encoder, BROTLI_PARAM_QUALITY, quality) )
-        RETVAL = newSVuv(1);
-    else
-        RETVAL = newSVuv(0);
-  OUTPUT:
-    RETVAL
-
-SV*
-_mode(self, mode)
-    IO::Compress::Brotli self
-    U32 mode
-  CODE:
-    if( BrotliEncoderSetParameter(self->encoder, BROTLI_PARAM_MODE, mode) )
-        RETVAL = newSVuv(1);
-    else
-        RETVAL = newSVuv(0);
-  OUTPUT:
-    RETVAL
+  C_ARGS:
+    self->encoder, param, value
 
 SV*
-_compress(self, in, op)
+_compress(self, in = &PL_sv_undef)
     IO::Compress::Brotli self
     SV* in
-    U8 op
+  ALIAS:
+    compress = 1
+    flush = 2
+    finish = 3
   PREINIT:
     uint8_t *next_in, *next_out, *buffer;
     size_t available_in, available_out;
     BROTLI_BOOL result;
+    BrotliEncoderOperation op;
   CODE:
-    next_in = (uint8_t*) SvPV(in, available_in);
+    switch(ix) {
+    case 0:
+        croak("_compress may not be called directly");
+        break;
+    case 1:
+        op = BROTLI_OPERATION_PROCESS;
+        break;
+    case 2:
+        op = BROTLI_OPERATION_FLUSH;
+        break;
+    case 3:
+        op = BROTLI_OPERATION_FINISH;
+        break;
+    default:
+        croak("Impossible ix in _compress");
+        break;
+    }
+
     Newx(buffer, BUFFER_SIZE, uint8_t);
+    if(in == &PL_sv_undef)
+        next_in = (uint8_t*) buffer, available_in = 0;
+    else
+        next_in = (uint8_t*) SvPV(in, available_in);
     RETVAL = newSVpv("", 0);
     while(1) {
         next_out = buffer;
@@ -245,15 +249,4 @@ DESTROY(self)
     IO::Compress::Brotli self
   CODE:
     BrotliEncoderDestroyInstance(self->encoder);
-
-void
-set_dictionary(self, dict)
-    IO::Compress::Brotli self
-    SV* dict
-  PREINIT:
-    size_t size;
-    uint8_t *data;
-  CODE:
-    data = SvPV(dict, size);
-    BrotliEncoderSetCustomDictionary(self->encoder, size, data);
-
+    Safefree(self);
This page took 0.013162 seconds and 4 git commands to generate.