diff options
Diffstat (limited to 'pdf')
-rw-r--r-- | pdf/pdf_cmap_load.c | 1 | ||||
-rw-r--r-- | pdf/pdf_function.c | 9 | ||||
-rw-r--r-- | pdf/pdf_interpret.c | 2 | ||||
-rw-r--r-- | pdf/pdf_repair.c | 10 | ||||
-rw-r--r-- | pdf/pdf_shade.c | 44 | ||||
-rw-r--r-- | pdf/pdf_stream.c | 15 | ||||
-rw-r--r-- | pdf/pdf_xref.c | 31 |
7 files changed, 75 insertions, 37 deletions
diff --git a/pdf/pdf_cmap_load.c b/pdf/pdf_cmap_load.c index fcf30ad0..3257516c 100644 --- a/pdf/pdf_cmap_load.c +++ b/pdf/pdf_cmap_load.c @@ -38,7 +38,6 @@ pdf_load_embedded_cmap(pdf_document *xref, fz_obj *stmobj) fz_try(ctx) { - file = pdf_open_stream(xref, fz_to_num(stmobj), fz_to_gen(stmobj)); phase = 1; cmap = pdf_load_cmap(ctx, file); diff --git a/pdf/pdf_function.c b/pdf/pdf_function.c index ff602021..23acc4db 100644 --- a/pdf/pdf_function.c +++ b/pdf/pdf_function.c @@ -836,8 +836,10 @@ load_postscript_func(pdf_function *func, pdf_document *xref, fz_obj *dict, int n int tok; int len; fz_context *ctx = xref->ctx; + int locked = 0; fz_var(stream); + fz_var(locked); fz_try(ctx) { @@ -856,15 +858,16 @@ load_postscript_func(pdf_function *func, pdf_document *xref, fz_obj *dict, int n codeptr = 0; parse_code(func, stream, &codeptr); } - fz_catch(ctx) + fz_always(ctx) { fz_close(stream); + } + fz_catch(ctx) + { fz_throw(ctx, "cannot parse calculator function (%d %d R)", num, gen); } func->size += func->u.p.cap * sizeof(psobj); - - fz_close(stream); } static void diff --git a/pdf/pdf_interpret.c b/pdf/pdf_interpret.c index b5938829..ea7f7692 100644 --- a/pdf/pdf_interpret.c +++ b/pdf/pdf_interpret.c @@ -942,6 +942,7 @@ copy_state(fz_context *ctx, pdf_gstate *gs, pdf_gstate *old) pdf_keep_xobject(ctx, gs->softmask); } + static pdf_csi * pdf_new_csi(pdf_document *xref, fz_device *dev, fz_matrix ctm, char *event, fz_cookie *cookie, pdf_gstate *gstate) { @@ -2517,6 +2518,7 @@ pdf_run_keyword(pdf_csi *csi, fz_obj *rdb, fz_stream *file, char *buf) fz_warn(ctx, "unknown keyword: '%s'", buf); break; } + fz_assert_lock_not_held(ctx, FZ_LOCK_FILE); } static void diff --git a/pdf/pdf_repair.c b/pdf/pdf_repair.c index 15886a8f..0dc0e132 100644 --- a/pdf/pdf_repair.c +++ b/pdf/pdf_repair.c @@ -67,7 +67,7 @@ pdf_repair_obj(fz_stream *file, char *buf, int cap, int *stmofsp, int *stmlenp, } obj = fz_dict_gets(dict, "Length"); - if (fz_is_int(obj)) + if (!fz_is_indirect(obj) && fz_is_int(obj)) stm_len = fz_to_int(obj); fz_drop_obj(dict); @@ -184,12 +184,14 @@ pdf_repair_obj_stm(pdf_document *xref, int num, int gen) fz_throw(ctx, "corrupt object stream (%d %d R)", num, gen); } } - fz_catch(ctx) + fz_always(ctx) { fz_close(stm); + } + fz_catch(ctx) + { fz_throw(ctx, "cannot load object stream object (%d %d R)", num, gen); } - fz_close(stm); } void @@ -386,7 +388,9 @@ pdf_repair_xref(pdf_document *xref, char *buf, int bufsize) /* corrected stream length */ if (list[i].stm_len >= 0) { + fz_unlock(ctx, FZ_LOCK_FILE); dict = pdf_load_object(xref, list[i].num, list[i].gen); + fz_lock(ctx, FZ_LOCK_FILE); /* RJW: "cannot load stream object (%d %d R)", list[i].num, list[i].gen */ length = fz_new_int(ctx, list[i].stm_len); diff --git a/pdf/pdf_shade.c b/pdf/pdf_shade.c index 15f5de6b..fb5dd72c 100644 --- a/pdf/pdf_shade.c +++ b/pdf/pdf_shade.c @@ -604,7 +604,7 @@ pdf_load_mesh_params(pdf_document *xref, fz_obj *dict, struct mesh_params *p) static void pdf_load_type4_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, - int funcs, pdf_function **func, fz_stream *stream) + int funcs, pdf_function **func) { fz_context *ctx = xref->ctx; struct mesh_params p; @@ -612,6 +612,7 @@ pdf_load_type4_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, int ncomp; int flag; int i; + fz_stream *stream; pdf_load_mesh_params(xref, dict, &p); @@ -623,6 +624,8 @@ pdf_load_type4_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, else ncomp = shade->colorspace->n; + stream = pdf_open_stream(xref, fz_to_num(dict), fz_to_gen(dict)); + while (!fz_is_eof_bits(stream)) { flag = fz_read_bits(stream, p.bpflag); @@ -665,11 +668,12 @@ pdf_load_type4_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, break; } } + fz_close(stream); } static void pdf_load_type5_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, - int funcs, pdf_function **func, fz_stream *stream) + int funcs, pdf_function **func) { fz_context *ctx = xref->ctx; struct mesh_params p; @@ -677,6 +681,7 @@ pdf_load_type5_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, int first; int ncomp; int i, k; + fz_stream *stream; pdf_load_mesh_params(xref, dict, &p); @@ -692,6 +697,8 @@ pdf_load_type5_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, buf = fz_malloc_array(ctx, p.vprow, sizeof(struct vertex)); first = 1; + stream = pdf_open_stream(xref, fz_to_num(dict), fz_to_gen(dict)); + while (!fz_is_eof_bits(stream)) { for (i = 0; i < p.vprow; i++) @@ -713,13 +720,14 @@ pdf_load_type5_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, fz_free(ctx, ref); fz_free(ctx, buf); + fz_close(stream); } /* Type 6 & 7 -- Patch mesh shadings */ static void pdf_load_type6_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, - int funcs, pdf_function **func, fz_stream *stream) + int funcs, pdf_function **func) { fz_context *ctx = xref->ctx; struct mesh_params p; @@ -728,6 +736,7 @@ pdf_load_type6_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, fz_point prevp[12]; int ncomp; int i, k; + fz_stream *stream; pdf_load_mesh_params(xref, dict, &p); @@ -741,6 +750,8 @@ pdf_load_type6_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, hasprevpatch = 0; + stream = pdf_open_stream(xref, fz_to_num(dict), fz_to_gen(dict)); + while (!fz_is_eof_bits(stream)) { float c[4][FZ_MAX_COLORS]; @@ -834,11 +845,12 @@ pdf_load_type6_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, hasprevpatch = 1; } } + fz_close(stream); } static void pdf_load_type7_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, - int funcs, pdf_function **func, fz_stream *stream) + int funcs, pdf_function **func) { fz_context *ctx = xref->ctx; struct mesh_params p; @@ -847,6 +859,7 @@ pdf_load_type7_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, fz_point prevp[16]; int ncomp; int i, k; + fz_stream *stream; pdf_load_mesh_params(xref, dict, &p); @@ -860,6 +873,8 @@ pdf_load_type7_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, hasprevpatch = 0; + stream = pdf_open_stream(xref, fz_to_num(dict), fz_to_gen(dict)); + while (!fz_is_eof_bits(stream)) { float c[4][FZ_MAX_COLORS]; @@ -953,6 +968,7 @@ pdf_load_type7_shade(fz_shade *shade, pdf_document *xref, fz_obj *dict, hasprevpatch = 1; } } + fz_close(stream); } /* Load all of the shading dictionary parameters, then switch on the shading type. */ @@ -962,7 +978,6 @@ pdf_load_shading_dict(pdf_document *xref, fz_obj *dict, fz_matrix transform) { fz_shade *shade = NULL; pdf_function *func[FZ_MAX_COLORS] = { NULL }; - fz_stream *stream = NULL; fz_obj *obj; int funcs = 0; int type = 0; @@ -972,7 +987,6 @@ pdf_load_shading_dict(pdf_document *xref, fz_obj *dict, fz_matrix transform) fz_var(shade); fz_var(func); fz_var(funcs); - fz_var(stream); fz_var(type); fz_try(ctx) @@ -1041,35 +1055,25 @@ pdf_load_shading_dict(pdf_document *xref, fz_obj *dict, fz_matrix transform) } } - if (type >= 4 && type <= 7) - { - stream = pdf_open_stream(xref, fz_to_num(dict), fz_to_gen(dict)); - /* RJW: "cannot open shading stream (%d %d R)", fz_to_num(dict), fz_to_gen(dict) */ - } - switch (type) { case 1: pdf_load_function_based_shading(shade, xref, dict, func[0]); break; case 2: pdf_load_axial_shading(shade, xref, dict, funcs, func); break; case 3: pdf_load_radial_shading(shade, xref, dict, funcs, func); break; - case 4: pdf_load_type4_shade(shade, xref, dict, funcs, func, stream); break; - case 5: pdf_load_type5_shade(shade, xref, dict, funcs, func, stream); break; - case 6: pdf_load_type6_shade(shade, xref, dict, funcs, func, stream); break; - case 7: pdf_load_type7_shade(shade, xref, dict, funcs, func, stream); break; + case 4: pdf_load_type4_shade(shade, xref, dict, funcs, func); break; + case 5: pdf_load_type5_shade(shade, xref, dict, funcs, func); break; + case 6: pdf_load_type6_shade(shade, xref, dict, funcs, func); break; + case 7: pdf_load_type7_shade(shade, xref, dict, funcs, func); break; default: fz_throw(ctx, "unknown shading type: %d", type); } - if (stream) - fz_close(stream); for (i = 0; i < funcs; i++) if (func[i]) pdf_drop_function(ctx, func[i]); } fz_catch(ctx) { - if (stream) - fz_close(stream); for (i = 0; i < funcs; i++) if (func[i]) pdf_drop_function(ctx, func[i]); diff --git a/pdf/pdf_stream.c b/pdf/pdf_stream.c index 3db8eb1c..a01bab55 100644 --- a/pdf/pdf_stream.c +++ b/pdf/pdf_stream.c @@ -225,6 +225,7 @@ pdf_open_filter(fz_stream *chain, pdf_document *xref, fz_obj *stmobj, int num, i else if (fz_array_len(filters) > 0) chain = build_filter_chain(chain, xref, filters, params, num, gen); + fz_lock_stream(chain); return chain; } @@ -276,6 +277,7 @@ pdf_open_raw_stream(pdf_document *xref, int num, int gen) fz_throw(xref->ctx, "object is not a stream"); stm = pdf_open_raw_filter(xref->file, xref, x->obj, num, gen); + fz_lock_stream(stm); fz_seek(xref->file, x->stm_ofs, 0); return stm; } @@ -316,6 +318,7 @@ pdf_open_stream_with_offset(pdf_document *xref, int num, int gen, fz_obj *dict, fz_throw(xref->ctx, "object is not a stream"); stm = pdf_open_filter(xref->file, xref, dict, num, gen); + fz_lock_stream(stm); fz_seek(xref->file, stm_ofs, 0); return stm; } @@ -378,9 +381,6 @@ pdf_load_stream(pdf_document *xref, int num, int gen) fz_var(buf); - stm = pdf_open_stream(xref, num, gen); - /* RJW: "cannot open stream (%d %d R)", num, gen */ - dict = pdf_load_object(xref, num, gen); /* RJW: "cannot load stream dictionary (%d %d R)", num, gen */ @@ -393,16 +393,21 @@ pdf_load_stream(pdf_document *xref, int num, int gen) fz_drop_obj(dict); + stm = pdf_open_stream(xref, num, gen); + /* RJW: "cannot open stream (%d %d R)", num, gen */ + fz_try(ctx) { buf = fz_read_all(stm, len); } - fz_catch(ctx) + fz_always(ctx) { fz_close(stm); + } + fz_catch(ctx) + { fz_throw(ctx, "cannot read raw stream (%d %d R)", num, gen); } - fz_close(stm); return buf; } diff --git a/pdf/pdf_xref.c b/pdf/pdf_xref.c index 210c2f44..41a7ba3a 100644 --- a/pdf/pdf_xref.c +++ b/pdf/pdf_xref.c @@ -293,6 +293,8 @@ pdf_read_new_xref_section(pdf_document *xref, fz_stream *stm, int i0, int i1, in } } +/* Entered with file locked. Drops the lock in the middle, but then picks + * it up again before exiting. */ static fz_obj * pdf_read_new_xref(pdf_document *xref, char *buf, int cap) { @@ -319,6 +321,7 @@ pdf_read_new_xref(pdf_document *xref, char *buf, int cap) fz_try(ctx) { + fz_unlock(ctx, FZ_LOCK_FILE); obj = fz_dict_gets(trailer, "Size"); if (!obj) fz_throw(ctx, "xref stream missing Size entry (%d %d R)", num, gen); @@ -368,10 +371,12 @@ pdf_read_new_xref(pdf_document *xref, char *buf, int cap) fz_drop_obj(index); fz_rethrow(ctx); } + fz_lock(ctx, FZ_LOCK_FILE); return trailer; } +/* File is locked on entry, and exit (but may be dropped in the middle) */ static fz_obj * pdf_read_xref(pdf_document *xref, int ofs, char *buf, int cap) { @@ -649,10 +654,12 @@ pdf_open_document_with_stream(fz_stream *file) fz_obj *obj; fz_obj *nobj = NULL; int i, repaired = 0; + int locked; fz_context *ctx = file->ctx; fz_var(dict); fz_var(nobj); + fz_var(locked); /* install pdf specific callback */ fz_resolve_indirect = pdf_resolve_indirect; @@ -663,6 +670,9 @@ pdf_open_document_with_stream(fz_stream *file) xref->file = fz_keep_stream(file); xref->ctx = ctx; + fz_lock(ctx, FZ_LOCK_FILE); + locked = 1; + fz_try(ctx) { pdf_load_xref(xref, xref->scratch, sizeof xref->scratch); @@ -691,6 +701,9 @@ pdf_open_document_with_stream(fz_stream *file) if (repaired) pdf_repair_xref(xref, xref->scratch, sizeof xref->scratch); + fz_unlock(ctx, FZ_LOCK_FILE); + locked = 0; + encrypt = fz_dict_gets(xref->trailer, "Encrypt"); id = fz_dict_gets(xref->trailer, "ID"); if (fz_is_dict(encrypt)) @@ -749,6 +762,11 @@ pdf_open_document_with_stream(fz_stream *file) } } } + fz_always(ctx) + { + if (locked) + fz_unlock(ctx, FZ_LOCK_FILE); + } fz_catch(ctx) { fz_drop_obj(dict); @@ -910,18 +928,17 @@ pdf_load_obj_stm(pdf_document *xref, int num, int gen, char *buf, int cap) } } } - fz_catch(ctx) + fz_always(ctx) { fz_close(stm); fz_free(xref->ctx, ofsbuf); fz_free(xref->ctx, numbuf); fz_drop_obj(objstm); + } + fz_catch(ctx) + { fz_throw(ctx, "cannot open object stream (%d %d R)", num, gen); } - fz_close(stm); - fz_free(xref->ctx, ofsbuf); - fz_free(xref->ctx, numbuf); - fz_drop_obj(objstm); } /* @@ -950,6 +967,7 @@ pdf_cache_object(pdf_document *xref, int num, int gen) } else if (x->type == 'n') { + fz_lock(ctx, FZ_LOCK_FILE); fz_seek(xref->file, x->ofs, 0); fz_try(ctx) @@ -959,6 +977,7 @@ pdf_cache_object(pdf_document *xref, int num, int gen) } fz_catch(ctx) { + fz_unlock(ctx, FZ_LOCK_FILE); fz_throw(ctx, "cannot parse object (%d %d R)", num, gen); } @@ -966,11 +985,13 @@ pdf_cache_object(pdf_document *xref, int num, int gen) { fz_drop_obj(x->obj); x->obj = NULL; + fz_unlock(ctx, FZ_LOCK_FILE); fz_throw(ctx, "found object (%d %d R) instead of (%d %d R)", rnum, rgen, num, gen); } if (xref->crypt) pdf_crypt_obj(ctx, xref->crypt, x->obj, num, gen); + fz_unlock(ctx, FZ_LOCK_FILE); } else if (x->type == 'o') { |