diff options
author | Laurynas Biveinis <laurynas.biveinis@gmail.com> | 2006-08-13 15:05:15 +0000 |
---|---|---|
committer | Laurynas Biveinis <laurynas.biveinis@gmail.com> | 2006-08-13 15:05:15 +0000 |
commit | 34e84bae5f33a172e2627c11f3e3d050511e0e6f (patch) | |
tree | ec08d93ac592020373a1f7ccd3cb828ecbc24072 | |
parent | f68455dc292bbcdf411da364bbe1da7e60bca3bc (diff) |
Add type tag to type-allocated objects
git-svn-id: https://gcc.gnu.org/svn/gcc/branches/boehms-gc@116110 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r-- | gcc/alias.c | 2 | ||||
-rw-r--r-- | gcc/gengtype.c | 72 | ||||
-rwxr-xr-x | gcc/ggc-boehm.c | 48 | ||||
-rw-r--r-- | gcc/rtl.h | 3 | ||||
-rw-r--r-- | gcc/tree.h | 3 |
5 files changed, 122 insertions, 6 deletions
diff --git a/gcc/alias.c b/gcc/alias.c index 7c51ad79dd6..22ac07654ed 100644 --- a/gcc/alias.c +++ b/gcc/alias.c @@ -670,7 +670,7 @@ record_alias_subset (HOST_WIDE_INT superset, HOST_WIDE_INT subset) { /* Create an entry for the SUPERSET, so that we have a place to attach the SUBSET. */ - superset_entry = ggc_alloc (sizeof (struct alias_set_entry)); + superset_entry = ggc_alloc_alias_set_entry(); superset_entry->alias_set = superset; superset_entry->children = splay_tree_new_ggc (splay_tree_compare_ints); diff --git a/gcc/gengtype.c b/gcc/gengtype.c index 2ca4ac7af36..a0124c1dd79 100644 --- a/gcc/gengtype.c +++ b/gcc/gengtype.c @@ -1545,6 +1545,8 @@ walk_type (type_p t, struct walk_type_data *d) use_param_num = oo->name[9] == '\0' ? 0 : oo->name[9] - '0'; else if (strcmp (oo->name, "use_params") == 0) use_params_p = 1; + else if (strcmp (oo->name, "size_not_fixed") == 0) + ; else if (strcmp (oo->name, "desc") == 0) desc = oo->info; else if (strcmp (oo->name, "nested_ptr") == 0) @@ -2436,7 +2438,7 @@ write_enum_defn (type_p structures, type_p param_structs) { type_p s; - oprintf (header_file, "\n/* Enumeration of types known. */\n"); + oprintf (header_file, "\n/* Enumeration of known types. */\n"); oprintf (header_file, "enum gt_types_enum {\n"); for (s = structures; s; s = s->next) if (s->gc_used == GC_POINTED_TO @@ -2450,6 +2452,7 @@ write_enum_defn (type_p structures, type_p param_structs) output_mangled_typename (header_file, s); oprintf (header_file, ", \n"); } + for (s = param_structs; s; s = s->next) if (s->gc_used == GC_POINTED_TO) { @@ -2457,10 +2460,76 @@ write_enum_defn (type_p structures, type_p param_structs) output_mangled_typename (header_file, s); oprintf (header_file, ", \n"); } + oprintf (header_file, " gt_types_enum_last\n"); oprintf (header_file, "};\n"); } +/* Write out a macro for typed allocations for each known struct or union. */ + +static void +write_typed_alloc_defns (type_p structures) +{ + type_p s; + pair_p p; + + oprintf (header_file, + "\n/* Typed allocation for known structs and unions. */\n"); + for (s = structures; s; s = s->next) + if (s->gc_used == GC_POINTED_TO + || (s->gc_used == GC_MAYBE_POINTED_TO && s->u.s.line.file != NULL)) + { + options_p o; + int have_size = 0; + const char *type_kind; + + for (o = s->u.s.opt; o; o = o->next) + if (strcmp (o->name, "size_not_fixed") == 0) + have_size = 1; + + if (s->kind == TYPE_STRUCT) + type_kind = "struct "; + else if (s->kind == TYPE_UNION) + type_kind = "union "; + else + type_kind = ""; + + oprintf (header_file, "#define ggc_alloc_%s(%s) \\\n", + s->u.s.tag, (have_size ? "SIZE" : "")); + oprintf (header_file, " ggc_alloc_typed(gt_ggc_e_"); + output_mangled_typename (header_file, s); + if (have_size) + oprintf (header_file, ", SIZE)\n"); + else + oprintf (header_file, ", sizeof (%s%s))\n", + type_kind, s->u.s.tag); + } + + oprintf (header_file, + "\n/* Typed allocation for known typedefs. */\n"); + for (p = typedefs; p != NULL; p = p->next) + { + s = p->type; + if (strcmp (p->name, s->u.s.tag) == 0) + continue; + + if (s->gc_used == GC_POINTED_TO + || (s->gc_used == GC_MAYBE_POINTED_TO && s->u.s.line.file != NULL)) + { + if (s->kind != TYPE_STRUCT + && s->kind != TYPE_UNION) + continue; + + oprintf (header_file, "#define ggc_alloc_%s(%s) \\\n", + p->name, s->kind == TYPE_STRUCT ? "" : "__SIZE"); + oprintf (header_file, " ggc_alloc_typed(gt_ggc_e_"); + output_mangled_typename (header_file, s); + oprintf (header_file, ", sizeof (%s%s))\n", + s->kind == TYPE_STRUCT ? "struct " : "", s->u.s.tag); + } + } +} + /* Might T contain any non-pointer elements? */ static int @@ -3083,6 +3152,7 @@ main(int ARG_UNUSED (argc), char ** ARG_UNUSED (argv)) open_base_files (); write_enum_defn (structures, param_structs); + write_typed_alloc_defns (structures); write_types (structures, param_structs, &ggc_wtd); write_types (structures, param_structs, &pch_wtd); write_local (structures, param_structs); diff --git a/gcc/ggc-boehm.c b/gcc/ggc-boehm.c index 1de49592871..e9d7f4dead7 100755 --- a/gcc/ggc-boehm.c +++ b/gcc/ggc-boehm.c @@ -16,17 +16,25 @@ static int ggc_htab_register_weak_ptr(void **slot, void *info); static int ggc_htab_unregister_weak_ptr(void **slot, void *info); static void ggc_htab_delete_weak_ptr(void ** slot, void * object, void * info); + static size_t get_used_heap_size(void); static void register_gty_roots(void); static void gc_warning_filter(char * msg, GC_word arg); + +static enum gt_types_enum *get_type_offset(void * block); +static enum gt_types_enum get_block_type(void * block); + static void register_weak_pointers(void); static void unregister_weak_pointers(void); static size_t last_allocated = 0; +static size_t type_overhead = 0; static ggc_stringpool_roots stringpool_roots; static GC_warn_proc default_warn_proc; +#define OBJ_OVERHEAD sizeof(enum gt_types_enum) + void init_ggc (void) { @@ -52,6 +60,38 @@ ggc_alloc_stat (size_t size MEM_STAT_DECL) return result; } +enum gt_types_enum * +get_type_offset(void * block) +{ + return (enum gt_types_enum *)((char *)block + GC_size(block) - OBJ_OVERHEAD); +} + +void * +ggc_alloc_typed_stat (enum gt_types_enum type, size_t size MEM_STAT_DECL) +{ + void * result = NULL; + + size_t actual_obj_size; + const size_t obj_plus_info_size = size + OBJ_OVERHEAD; + type_overhead += obj_plus_info_size; + + result = GC_malloc (obj_plus_info_size); + actual_obj_size = GC_size(result); + + *(get_type_offset(result)) = type; + + /* Verification */ + gcc_assert (type == get_block_type (result)); + + return result; +} + +enum gt_types_enum +get_block_type(void * block) +{ + return *(get_type_offset(block)); +} + void * ggc_realloc_stat (void *x, size_t size MEM_STAT_DECL) { @@ -177,8 +217,9 @@ ggc_free (void * block) size_t ggc_get_size (const void * block) { - return GC_size((void *)block); /* Note that GC_size may return a bit larger - value than originally requested */ + return GC_size((void *)block) - OBJ_OVERHEAD; /* Note that GC_size may return + a bit larger value than + originally requested */ } int @@ -267,6 +308,9 @@ ggc_print_statistics (void) fprintf (stderr, "Used bytes in the heap: %lu\n", (unsigned long)get_used_heap_size()); + fprintf (stderr, + "Local ggc-boehm overhead: %lu\n", + (unsigned long)type_overhead); } int diff --git a/gcc/rtl.h b/gcc/rtl.h index 42c4db6524a..8f6bb99e59c 100644 --- a/gcc/rtl.h +++ b/gcc/rtl.h @@ -232,7 +232,8 @@ struct object_block GTY(()) /* RTL expression ("rtx"). */ struct rtx_def GTY((chain_next ("RTX_NEXT (&%h)"), - chain_prev ("RTX_PREV (&%h)"))) + chain_prev ("RTX_PREV (&%h)"), + size_not_fixed (""))) { /* The kind of expression this is. */ ENUM_BITFIELD(rtx_code) code: 16; diff --git a/gcc/tree.h b/gcc/tree.h index 9c1181873f8..ea77424ad52 100644 --- a/gcc/tree.h +++ b/gcc/tree.h @@ -3143,7 +3143,8 @@ struct tree_value_handle GTY(()) for various types of node. */ union tree_node GTY ((ptr_alias (union lang_tree_node), - desc ("tree_node_structure (&%h)"))) + desc ("tree_node_structure (&%h)"), + size_not_fixed (""))) { struct tree_common GTY ((tag ("TS_COMMON"))) common; struct tree_int_cst GTY ((tag ("TS_INT_CST"))) int_cst; |