diff options
author | Chris Liddell <chris.liddell@artifex.com> | 2011-07-25 16:25:20 +0100 |
---|---|---|
committer | Chris Liddell <chris.liddell@artifex.com> | 2011-07-25 16:30:15 +0100 |
commit | f62ce181e3a68d7f652d9e903c70bd1a67423782 (patch) | |
tree | b6da908e03607ae3f5bc18216b9229f5a7e87081 | |
parent | 7dee8c1639a55e5b6ae4051afcfed9caa82e48b5 (diff) |
Bug 692367: NULL out pointers for three tables in the context
Add "finalize" methods for gs_name_table, io_device_table and
font_dir tables which ensure that the pointers in the lib
context are set to NULL when the memory is released.
No cluster differences.
-rw-r--r-- | gs/base/gsfont.c | 9 | ||||
-rw-r--r-- | gs/base/gsiodev.c | 24 | ||||
-rw-r--r-- | gs/base/gsstruct.h | 18 | ||||
-rw-r--r-- | gs/base/gxfcache.h | 4 | ||||
-rw-r--r-- | gs/psi/iname.c | 13 |
5 files changed, 61 insertions, 7 deletions
diff --git a/gs/base/gsfont.c b/gs/base/gsfont.c index ece4c9b2b..9535666bf 100644 --- a/gs/base/gsfont.c +++ b/gs/base/gsfont.c @@ -270,6 +270,15 @@ gs_font_dir_alloc2_limits(gs_memory_t * struct_mem, gs_memory_t * bits_mem, pdir->hash = 42; /* initialize the hash to a randomly picked number */ return pdir; } +static void +gs_font_dir_finalize(void *vptr) +{ + gs_font_dir *pdir = vptr; + if (pdir == pdir->memory->gs_lib_ctx->font_dir) { + pdir->memory->gs_lib_ctx->font_dir = NULL; + } +} + /* Allocate and minimally initialize a font. */ gs_font * diff --git a/gs/base/gsiodev.c b/gs/base/gsiodev.c index 65b279d05..9b6f0e408 100644 --- a/gs/base/gsiodev.c +++ b/gs/base/gsiodev.c @@ -31,9 +31,9 @@ extern_gx_io_device_table(); private_st_io_device(); gs_private_st_ptr(st_io_device_ptr, gx_io_device *, "gx_io_device *", iodev_ptr_enum_ptrs, iodev_ptr_reloc_ptrs); -gs_private_st_element(st_io_device_ptr_element, gx_io_device *, +gs_private_st_element_final(st_io_device_ptr_element, gx_io_device *, "gx_io_device *[]", iodev_ptr_elt_enum_ptrs, iodev_ptr_elt_reloc_ptrs, - st_io_device_ptr); + st_io_device_ptr,gs_iodev_finalize); /* Define the OS (%os%) device. */ iodev_proc_fopen(iodev_os_fopen); @@ -61,7 +61,7 @@ int gs_iodev_init(gs_memory_t * mem) { /* Make writable copies of all IODevices. */ gx_io_device **table = - gs_alloc_struct_array(mem, gx_io_device_table_count, + gs_alloc_struct_array(mem, gx_io_device_table_count + 1, gx_io_device *, &st_io_device_ptr_element, "gs_iodev_init(table)"); gs_lib_ctx_t *libctx = gs_lib_ctx_get_interp_instance(mem); @@ -80,6 +80,14 @@ gs_iodev_init(gs_memory_t * mem) table[i] = iodev; memcpy(table[i], gx_io_device_table[i], sizeof(gx_io_device)); } + /* FIXME: we allocate an extra pointer in the array and stuff + * the memory context in there, as we need access to it in the + * finalize method below. We get away it because everywhere that + * searches the table uses gx_io_device_table_count, rather than + * the actuall allocated length. + * A less naff solution would be preferable! + */ + table[gx_io_device_table_count] = (gx_io_device *) mem; libctx->io_device_table = table; code = gs_register_struct_root(mem, NULL, (void **)&libctx->io_device_table, @@ -102,6 +110,16 @@ gs_iodev_init(gs_memory_t * mem) return (code < 0 ? code : gs_note_error(gs_error_VMerror)); } +static void +gs_iodev_finalize(void *vptr) +{ + gx_io_device **table = vptr; + gs_memory_t * mem = ((gs_memory_t *)table[gx_io_device_table_count]); + + mem->gs_lib_ctx->io_device_table = NULL; +} + + /* ------ Default (unimplemented) IODevice procedures ------ */ int diff --git a/gs/base/gsstruct.h b/gs/base/gsstruct.h index cd33da11a..bdfc3ff64 100644 --- a/gs/base/gsstruct.h +++ b/gs/base/gsstruct.h @@ -620,6 +620,24 @@ extern void reloc_const_bytestring(gs_const_bytestring *pbs, gc_state_t *gcst); #define gs_private_st_element(stname, stype, sname, penum, preloc, basest)\ gs__st_element(private_st, stname, stype, sname, penum, preloc, basest) +#define gs__st_element_final(scope_st, stname, stype, sname, penum, preloc, basest, pfinal)\ + static ENUM_PTRS_BEGIN_PROC(penum) {\ + uint count = size / (uint)sizeof(stype);\ + if ( count == 0 ) return 0;\ + return ENUM_USING(basest, (EV_CONST char *)vptr + (index % count) * sizeof(stype),\ + sizeof(stype), index / count);\ + } ENUM_PTRS_END_PROC\ + static RELOC_PTRS_BEGIN(preloc) {\ + uint count = size / (uint)sizeof(stype);\ + for ( ; count; count--, vptr = (char *)vptr + sizeof(stype) )\ + RELOC_USING(basest, vptr, sizeof(stype));\ + } RELOC_PTRS_END\ + gs__st_composite_final(scope_st, stname, stype, sname, penum, preloc,pfinal) +#define gs_public_st_element_final(stname, stype, sname, penum, preloc, basest,pfinal)\ + gs__st_element_final(public_st, stname, stype, sname, penum, preloc, basest,pfinal) +#define gs_private_st_element_final(stname, stype, sname, penum, preloc, basest,pfinal)\ + gs__st_element_final(private_st, stname, stype, sname, penum, preloc, basest,pfinal) + /* A "structure" just consisting of a pointer. */ /* Note that in this case only, stype is a pointer type. */ /* Fortunately, C's bizarre 'const' syntax does what we want here. */ diff --git a/gs/base/gxfcache.h b/gs/base/gxfcache.h index 3f3b5a73c..f6b97360e 100644 --- a/gs/base/gxfcache.h +++ b/gs/base/gxfcache.h @@ -319,8 +319,8 @@ struct gs_font_dir_s { }; #define private_st_font_dir() /* in gsfont.c */\ - gs_private_st_composite(st_font_dir, gs_font_dir, "gs_font_dir",\ - font_dir_enum_ptrs, font_dir_reloc_ptrs) + gs_private_st_composite_final(st_font_dir, gs_font_dir, "gs_font_dir",\ + font_dir_enum_ptrs, font_dir_reloc_ptrs, gs_font_dir_finalize) /* Enumerate the pointers in a font directory, except for orig_fonts. */ #define font_dir_do_ptrs(m)\ diff --git a/gs/psi/iname.c b/gs/psi/iname.c index 96a6e8d8a..2d4764e18 100644 --- a/gs/psi/iname.c +++ b/gs/psi/iname.c @@ -37,13 +37,15 @@ static const byte nt_1char_names[NT_1CHAR_SIZE] = { NT_1CHAR_NAMES_DATA }; +static void gs_names_finalize(void *); + /* Structure descriptors */ gs_private_st_simple(st_name_sub_table, name_sub_table, "name_sub_table"); gs_private_st_composite(st_name_string_sub_table, name_string_sub_table_t, "name_string_sub_table_t", name_string_sub_enum_ptrs, name_string_sub_reloc_ptrs); -gs_private_st_composite(st_name_table, name_table, "name_table", - name_table_enum_ptrs, name_table_reloc_ptrs); +gs_private_st_composite_final(st_name_table, name_table, "name_table", + name_table_enum_ptrs, name_table_reloc_ptrs,gs_names_finalize); /* Forward references */ static int name_alloc_sub(name_table *); @@ -127,6 +129,13 @@ names_init(ulong count, gs_ref_memory_t *imem) return nt; } +static void +gs_names_finalize(void *vptr) +{ + name_table *nt = vptr; + nt->memory->gs_lib_ctx->gs_name_table = NULL; +} + /* Get the allocator for the name table. */ gs_memory_t * names_memory(const name_table * nt) |