summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSebastian Rasmussen <sebras@gmail.com>2019-02-09 13:34:17 +0100
committerSebastian Rasmussen <sebras@gmail.com>2019-02-12 19:06:46 +0100
commit660eaabf87a143b5217dc875550968883d8e4fc0 (patch)
treeb18ef3b21216911b96b89f5c39b3796386583862
parent0d942b34ae4a5385f5cd3cfa9b2c708f56c65860 (diff)
downloadghostpdl-660eaabf87a143b5217dc875550968883d8e4fc0.tar.gz
Bug 700554: jbig2: Use custom allocator for jbig2dec/luratech decoders.
-rw-r--r--base/sjbig2.c88
-rw-r--r--base/sjbig2.h2
-rw-r--r--base/sjbig2_luratech.c32
-rw-r--r--base/sjbig2_luratech.h2
-rw-r--r--psi/zfjbig2.c2
5 files changed, 98 insertions, 28 deletions
diff --git a/base/sjbig2.c b/base/sjbig2.c
index f8817e16a..73a9b1bef 100644
--- a/base/sjbig2.c
+++ b/base/sjbig2.c
@@ -172,13 +172,37 @@ s_jbig2decode_invert_buffer(unsigned char *buf, int length)
*buf++ ^= 0xFF;
}
+typedef struct {
+ Jbig2Allocator allocator;
+ gs_memory_t *mem;
+} s_jbig2decode_allocator_t;
+
+static void *s_jbig2decode_alloc(Jbig2Allocator *_allocator, size_t size)
+{
+ s_jbig2decode_allocator_t *allocator = (s_jbig2decode_allocator_t *) _allocator;
+ return gs_alloc_bytes(allocator->mem, size, "s_jbig2decode_alloc");
+}
+
+static void s_jbig2decode_free(Jbig2Allocator *_allocator, void *p)
+{
+ s_jbig2decode_allocator_t *allocator = (s_jbig2decode_allocator_t *) _allocator;
+ gs_free_object(allocator->mem, p, "s_jbig2decode_free");
+}
+
+static void *s_jbig2decode_realloc(Jbig2Allocator *_allocator, void *p, size_t size)
+{
+ s_jbig2decode_allocator_t *allocator = (s_jbig2decode_allocator_t *) _allocator;
+ return gs_resize_object(allocator->mem, p, size, "s_jbig2decode_realloc");
+}
+
/* parse a globals stream packed into a gs_bytestring for us by the postscript
layer and stuff the resulting context into a pointer for use in later decoding */
int
-s_jbig2decode_make_global_data(byte *data, uint length, void **result)
+s_jbig2decode_make_global_data(gs_memory_t *mem, byte *data, uint length, void **result)
{
Jbig2Ctx *ctx = NULL;
int code;
+ s_jbig2decode_allocator_t *allocator;
/* the cvision encoder likes to include empty global streams */
if (length == 0) {
@@ -187,19 +211,34 @@ s_jbig2decode_make_global_data(byte *data, uint length, void **result)
return 0;
}
+ allocator = (s_jbig2decode_allocator_t *) gs_alloc_bytes(mem,
+ sizeof (s_jbig2decode_allocator_t), "s_jbig2_make_global_data");
+ if (allocator == NULL) {
+ *result = NULL;
+ return_error(gs_error_VMerror);
+ }
+
+ allocator->allocator.alloc = s_jbig2decode_alloc;
+ allocator->allocator.free = s_jbig2decode_free;
+ allocator->allocator.realloc = s_jbig2decode_realloc;
+ allocator->mem = mem;
+
/* allocate a context with which to parse our global segments */
- ctx = jbig2_ctx_new(NULL, JBIG2_OPTIONS_EMBEDDED, NULL,
- s_jbig2decode_error, NULL);
- if (ctx == NULL) return 0;
+ ctx = jbig2_ctx_new((Jbig2Allocator *) allocator, JBIG2_OPTIONS_EMBEDDED,
+ NULL, s_jbig2decode_error, NULL);
+ if (ctx == NULL) {
+ gs_free_object(mem, allocator, "s_jbig2_make_global_data");
+ return_error(gs_error_VMerror);
+ }
/* parse the global bitstream */
code = jbig2_data_in(ctx, data, length);
-
if (code) {
/* error parsing the global stream */
- jbig2_ctx_free(ctx);
+ allocator = (s_jbig2decode_allocator_t *) jbig2_ctx_free(ctx);
+ gs_free_object(allocator->mem, allocator, "s_jbig2_make_global_data");
*result = NULL;
- return code;
+ return_error(gs_error_ioerror);
}
/* canonize and store our global state */
@@ -213,8 +252,11 @@ void
s_jbig2decode_free_global_data(void *data)
{
Jbig2GlobalCtx *global_ctx = (Jbig2GlobalCtx*)data;
+ s_jbig2decode_allocator_t *allocator;
+
+ allocator = (s_jbig2decode_allocator_t *) jbig2_global_ctx_free(global_ctx);
- jbig2_global_ctx_free(global_ctx);
+ gs_free_object(allocator->mem, allocator, "s_jbig2decode_free_global_data");
}
/* store a global ctx pointer in our state structure */
@@ -237,6 +279,7 @@ s_jbig2decode_init(stream_state * ss)
stream_jbig2decode_state *const state = (stream_jbig2decode_state *) ss;
Jbig2GlobalCtx *global_ctx = state->global_ctx; /* may be NULL */
int code = 0;
+ s_jbig2decode_allocator_t *allocator = NULL;
state->callback_data = (s_jbig2_callback_data_t *)gs_alloc_bytes(
ss->memory->non_gc_memory,
@@ -247,9 +290,26 @@ s_jbig2decode_init(stream_state * ss)
state->callback_data->error = 0;
state->callback_data->last_message = NULL;
state->callback_data->repeats = 0;
- /* initialize the decoder with the parsed global context if any */
- state->decode_ctx = jbig2_ctx_new(NULL, JBIG2_OPTIONS_EMBEDDED,
- global_ctx, s_jbig2decode_error, state->callback_data);
+
+ allocator = (s_jbig2decode_allocator_t *) gs_alloc_bytes(ss->memory->non_gc_memory, sizeof (s_jbig2decode_allocator_t), "s_jbig2decode_init(allocator)");
+ if (allocator == NULL) {
+ s_jbig2decode_error(state->callback_data, "failed to allocate custom jbig2dec allocator", JBIG2_SEVERITY_FATAL, -1);
+ }
+ else {
+ allocator->allocator.alloc = s_jbig2decode_alloc;
+ allocator->allocator.free = s_jbig2decode_free;
+ allocator->allocator.realloc = s_jbig2decode_realloc;
+ allocator->mem = ss->memory->non_gc_memory;
+
+ /* initialize the decoder with the parsed global context if any */
+ state->decode_ctx = jbig2_ctx_new((Jbig2Allocator *) allocator, JBIG2_OPTIONS_EMBEDDED,
+ global_ctx, s_jbig2decode_error, state->callback_data);
+
+ if (state->decode_ctx == NULL) {
+ gs_free_object(allocator->mem, allocator, "s_jbig2decode_release");
+ }
+
+ }
code = state->callback_data->error;
}
@@ -323,11 +383,15 @@ s_jbig2decode_release(stream_state *ss)
stream_jbig2decode_state *const state = (stream_jbig2decode_state *) ss;
if (state->decode_ctx) {
+ s_jbig2decode_allocator_t *allocator = NULL;
+
if (state->image) jbig2_release_page(state->decode_ctx, state->image);
state->image = NULL;
s_jbig2decode_flush_errors(state->callback_data);
- jbig2_ctx_free(state->decode_ctx);
+ allocator = (s_jbig2decode_allocator_t *) jbig2_ctx_free(state->decode_ctx);
state->decode_ctx = NULL;
+
+ gs_free_object(allocator->mem, allocator, "s_jbig2decode_release");
}
if (state->callback_data) {
gs_memory_t *mem = state->callback_data->memory;
diff --git a/base/sjbig2.h b/base/sjbig2.h
index 6819a0221..4c046bdbd 100644
--- a/base/sjbig2.h
+++ b/base/sjbig2.h
@@ -62,7 +62,7 @@ extern const stream_template s_jbig2decode_template;
/* call ins to process the JBIG2Globals parameter */
int
-s_jbig2decode_make_global_data(byte *data, uint length, void **result);
+s_jbig2decode_make_global_data(gs_memory_t *mem, byte *data, uint length, void **result);
int
s_jbig2decode_set_global_data(stream_state *ss, s_jbig2_global_data_t *gd);
void
diff --git a/base/sjbig2_luratech.c b/base/sjbig2_luratech.c
index b6b25de3f..9efabe4c7 100644
--- a/base/sjbig2_luratech.c
+++ b/base/sjbig2_luratech.c
@@ -55,24 +55,28 @@ private_st_jbig2decode_state();
/* our implementation of the "parsed" /JBIG2Globals filter parameter */
typedef struct s_jbig2decode_global_data_s {
+ gs_memory_t *mem;
unsigned char *data;
unsigned long size;
} s_jbig2decode_global_data;
/* create a global data struct and copy data into it */
int
-s_jbig2decode_make_global_data(byte *data, uint size, void **result)
+s_jbig2decode_make_global_data(gs_memory_t *mem, byte *data, uint size, void **result)
{
s_jbig2decode_global_data *global = NULL;
- global = malloc(sizeof(*global));
+ global = gs_alloc_bytes(mem, sizeof (*global), "s_jbig2decode_make_global_data(global)");
if (global == NULL) return_error(gs_error_VMerror);
- global->data = malloc(size);
+ global->mem = mem;
+
+ global->data = gs_alloc_bytes(global->mem, size, "s_jbig2decode_make_global_data(global_data)");
if (global->data == NULL) {
- free(global);
+ gs_free_object(global->mem, global, "s_jbig2decode_make_global_data(global)");
return_error(gs_error_VMerror);
}
+
memcpy(global->data, data, size);
global->size = size;
@@ -87,10 +91,11 @@ s_jbig2decode_free_global_data(void *data)
s_jbig2decode_global_data *global = (s_jbig2decode_global_data*)data;
if (global->size && global->data) {
- free(global->data);
+ gs_free_object(global->mem, global->data, "s_jbig2decode_free_global_data(global_data)");
global->size = 0;
}
- free(global);
+
+ gs_free_object(global->mem, global, "s_jbig2decode_free_global_data(global)");
}
/* store a global ctx pointer in our state structure */
@@ -131,15 +136,16 @@ s_jbig2_invert_buffer(unsigned char *buf, int length)
static void * JB2_Callback
s_jbig2_alloc(unsigned long size, void *userdata)
{
- void *result = malloc(size);
- return result;
+ gs_memory_t *mem = (gs_memory_t *) userdata;
+ return gs_alloc_bytes(mem, size, "s_jbig2_alloc");
}
/* memory release */
static JB2_Error JB2_Callback
s_jbig2_free(void *ptr, void *userdata)
{
- free(ptr);
+ gs_memory_t *mem = (gs_memory_t *) userdata;
+ gs_free_object(mem, ptr, "s_jbig2_free");
return cJB2_Error_OK;
}
@@ -312,8 +318,8 @@ s_jbig2decode_process(stream_state * ss, stream_cursor_read * pr,
/* initialize the codec state and pass our callbacks */
error = JB2_Document_Start( &(state->doc),
- s_jbig2_alloc, ss, /* alloc and its data */
- s_jbig2_free, ss, /* free and its data */
+ s_jbig2_alloc, ss->memory->non_gc_memory, /* alloc and its data */
+ s_jbig2_free, ss->memory->non_gc_memory, /* free and its data */
s_jbig2_read, ss, /* read callback and data */
s_jbig2_message, ss); /* message callback and data */
if (error != cJB2_Error_OK) return ERRC;
@@ -404,8 +410,8 @@ s_jbig2encode_start(stream_jbig2encode_state *state)
/* initialize the compression handle */
err = JB2_Compress_Start(&(state->cmp),
- s_jbig2_alloc, state, /* alloc and its parameter data */
- s_jbig2_free, state, /* free callback */
+ s_jbig2_alloc, state->memory, /* alloc and its parameter data */
+ s_jbig2_free, state->memory, /* free callback */
s_jbig2_message, state);/* message callback */
if (err != cJB2_Error_OK) return err;
diff --git a/base/sjbig2_luratech.h b/base/sjbig2_luratech.h
index 367c45ad7..73725ac4a 100644
--- a/base/sjbig2_luratech.h
+++ b/base/sjbig2_luratech.h
@@ -54,7 +54,7 @@ extern const stream_template s_jbig2decode_template;
/* call in to process the JBIG2Globals parameter */
int
-s_jbig2decode_make_global_data(byte *data, uint size, void **result);
+s_jbig2decode_make_global_data(gs_memory_t *mem, byte *data, uint size, void **result);
int
s_jbig2decode_set_global_data(stream_state *ss, s_jbig2_global_data_t *gs);
void
diff --git a/psi/zfjbig2.c b/psi/zfjbig2.c
index 596a86f8b..2208a4183 100644
--- a/psi/zfjbig2.c
+++ b/psi/zfjbig2.c
@@ -104,7 +104,7 @@ z_jbig2makeglobalctx(i_ctx_t * i_ctx_p)
size = gs_object_size(imemory, op->value.pstruct);
data = r_ptr(op, byte);
- code = s_jbig2decode_make_global_data(data, size,
+ code = s_jbig2decode_make_global_data(imemory->non_gc_memory, data, size,
&global);
if (size > 0 && global == NULL) {
dmlprintf(imemory, "failed to create parsed JBIG2GLOBALS object.");