Use a local temporary buffer for decompression instead of a global.
[io-compress-brotli.git] / Brotli.xs
CommitLineData
f9995f31
MG
1#define PERL_NO_GET_CONTEXT
2#include "EXTERN.h"
3#include "perl.h"
4#include "XSUB.h"
5
6#include "ppport.h"
7
8#include <dec/decode.h>
fd0f6b13 9#include <common/dictionary.h>
f9995f31
MG
10
11#define BUFFER_SIZE 1048576
f9995f31
MG
12
13MODULE = IO::Compress::Brotli PACKAGE = IO::Uncompress::Brotli
14PROTOTYPES: ENABLE
15
16SV* unbro(buffer)
17 SV* buffer
18 PREINIT:
19 size_t decoded_size;
20 STRLEN encoded_size;
21 uint8_t *encoded_buffer, *decoded_buffer;
22 CODE:
23 encoded_buffer = (uint8_t*) SvPV(buffer, encoded_size);
24 if(!BrotliDecompressedSize(encoded_size, encoded_buffer, &decoded_size)){
25 croak("Error in BrotliDecompressedSize");
26 }
27 Newx(decoded_buffer, decoded_size+1, uint8_t);
28 decoded_buffer[decoded_size]=0;
ea94b872
QR
29 if(!BrotliDecoderDecompress(encoded_size, encoded_buffer, &decoded_size, decoded_buffer)){
30 croak("Error in BrotliDecoderDecompress");
f9995f31
MG
31 }
32 RETVAL = newSV(0);
33 sv_usepvn_flags(RETVAL, decoded_buffer, decoded_size, SV_HAS_TRAILING_NUL);
34 OUTPUT:
35 RETVAL
36
ea94b872 37SV* BrotliDecoderCreateInstance()
f9995f31 38 CODE:
ea94b872 39 RETVAL = newSViv((IV)BrotliDecoderCreateInstance(NULL, NULL, NULL));
f9995f31
MG
40 OUTPUT:
41 RETVAL
42
ea94b872 43void BrotliDecoderDestroyInstance(state)
f9995f31
MG
44 SV* state
45 CODE:
ea94b872 46 BrotliDecoderDestroyInstance((BrotliDecoderState*)SvIV(state));
f9995f31 47
ea94b872 48SV* BrotliDecoderDecompressStream(state, in)
f9995f31
MG
49 SV* state
50 SV* in
51 PREINIT:
261eae0a 52 uint8_t *next_in, *next_out, *buffer;
29037568 53 size_t available_in, available_out;
ea94b872 54 BrotliDecoderResult result;
f9995f31
MG
55 CODE:
56 next_in = (uint8_t*) SvPV(in, available_in);
261eae0a 57 Newx(buffer, BUFFER_SIZE, uint8_t);
f9995f31
MG
58 RETVAL = newSVpv("", 0);
59 result = BROTLI_RESULT_NEEDS_MORE_OUTPUT;
60 while(result == BROTLI_RESULT_NEEDS_MORE_OUTPUT) {
61 next_out = buffer;
62 available_out=BUFFER_SIZE;
782ccd86
QR
63 result = BrotliDecoderDecompressStream( (BrotliDecoderState*) SvIV(state),
64 &available_in,
65 (const uint8_t**) &next_in,
66 &available_out,
67 &next_out,
29037568 68 NULL );
f9995f31 69 if(!result){
261eae0a
QR
70 Safefree(buffer);
71 croak("Error in BrotliDecoderDecompressStream");
f9995f31
MG
72 }
73 sv_catpvn(RETVAL, (const char*)buffer, BUFFER_SIZE-available_out);
74 }
261eae0a 75 Safefree(buffer);
f9995f31
MG
76 OUTPUT:
77 RETVAL
78
5f975f9c 79void BrotliDecoderSetCustomDictionary(state, dict)
f9995f31
MG
80 SV* state
81 SV* dict
82 PREINIT:
83 size_t size;
84 uint8_t *data;
85 CODE:
86 data = SvPV(dict, size);
ea94b872 87 BrotliDecoderSetCustomDictionary((BrotliDecoderState*) SvIV(state), size, data);
This page took 0.016171 seconds and 4 git commands to generate.