ggc-common.c (ggc_alloc_cleared_stat, [...]): Rename from ...; make statistics transparent.
* ggc-common.c (ggc_alloc_cleared_stat, ggc_realloc_stat): Rename from ...; make statistics transparent. (ggc_alloc_cleared, ggc_realloc_stat): ... these. (loc_descriptor): New structure. (hash_descriptor, eq_descriptor, loc_descriptor, cmp_statistics, add_statistics): New static function. (ggc_record_overhead, dump_statistics): New global function. * ggc-none.c (ggc_alloc_types_stat, ggc_alloc_stat, ggc_alloc_zone_stat, ggc_alloc_cleared_stat, ggc_realloc_stat, ggc_alloc_typed_stat): Rename from ...; accept locations (ggc_alloc_types, ggc_alloc, ggc_alloc_zone, ggc_alloc_cleared, ggc_realloc, ggc_alloc_typed): ... this one. from ...; accept locations * ggc-page.c (ggc_alloc_typed_stat, ggc_alloc_zone_stat, ggc_alloc_stat): Rename from ... ; pass locations * ggc-page.c (ggc_alloc_typed, ggc_alloc_zone, ggc_alloc): ... this one. (ggc_alloc_stat): Record overehead. * ggc.h (ggc_alloc_types, ggc_alloc, ggc_alloc_zone, ggc_alloc_cleared, ggc_realloc, ggc_alloc_typed): Turn to macros (ggc_alloc_types_stat, ggc_alloc_stat, ggc_alloc_zone_stat, ggc_alloc_cleared_stat, ggc_realloc_stat, ggc_alloc_typed_stat): Declare. (dump_ggc_loc_satistics, ggc_record_overehead): Declare. * langhooks.h (lhd_make_node): Declare. (LANG_HOOKS_MAKE_TYPE): Default to new function, * langhooks.c (lhd_make_node): New. * rtl.c (rtx_alloc_stat, swallow_copy_rtx_stat): Rename from ... ; pass locations. (rtx_alloc, swallow_copy_rtx): ... this one. * rtl.h (rtx_alloc, swallow_copy_rtx): Turn to macros. * rtl.c (rtx_alloc_stat, swallow_copy_rtx_stat): Declare. * toplpev.c (finalize): Dump stats. * tree.c (make_node_stat, copy_node_stat, make_tree_vec_stat, build_tree_list_stat, tree_cons_stat, build?_stat, build_decl_stat): Rename from ... ; pass locators. (make_node, copy_node, make_tree_vec, build_tree_list, tree_cons, build?, build_decl): Declare. * tree.h (make_node_stat, copy_node_stat, make_tree_vec_stat, build_tree_list_stat, tree_cons_stat, build?_stat, build_decl_stat): Declare. (make_node, copy_node, make_tree_vec, build_tree_list, tree_cons, build?, build_decl): New macros. * Makefile.in (RTL_H, TREE_H): Add statistics.h dependency. * statistics.h: New file. From-SVN: r78826
This commit is contained in:
parent
6ba7b54780
commit
b9dcdee46e
@ -1,3 +1,51 @@
|
||||
2004-03-03 Jan Hubicka <jh@suse.cz>
|
||||
|
||||
* ggc-common.c (ggc_alloc_cleared_stat, ggc_realloc_stat):
|
||||
Rename from ...; make statistics transparent.
|
||||
(ggc_alloc_cleared, ggc_realloc_stat): ... these.
|
||||
(loc_descriptor): New structure.
|
||||
(hash_descriptor, eq_descriptor, loc_descriptor, cmp_statistics,
|
||||
add_statistics):
|
||||
New static function.
|
||||
(ggc_record_overhead, dump_statistics): New global function.
|
||||
* ggc-none.c (ggc_alloc_types_stat, ggc_alloc_stat, ggc_alloc_zone_stat,
|
||||
ggc_alloc_cleared_stat, ggc_realloc_stat, ggc_alloc_typed_stat): Rename
|
||||
from ...; accept locations
|
||||
(ggc_alloc_types, ggc_alloc, ggc_alloc_zone, ggc_alloc_cleared,
|
||||
ggc_realloc, ggc_alloc_typed): ... this one.
|
||||
from ...; accept locations
|
||||
* ggc-page.c (ggc_alloc_typed_stat, ggc_alloc_zone_stat,
|
||||
ggc_alloc_stat): Rename from ... ; pass locations
|
||||
* ggc-page.c (ggc_alloc_typed, ggc_alloc_zone, ggc_alloc):
|
||||
... this one.
|
||||
(ggc_alloc_stat): Record overehead.
|
||||
* ggc.h (ggc_alloc_types, ggc_alloc, ggc_alloc_zone, ggc_alloc_cleared,
|
||||
ggc_realloc, ggc_alloc_typed): Turn to macros
|
||||
(ggc_alloc_types_stat, ggc_alloc_stat, ggc_alloc_zone_stat,
|
||||
ggc_alloc_cleared_stat, ggc_realloc_stat, ggc_alloc_typed_stat): Declare.
|
||||
(dump_ggc_loc_satistics, ggc_record_overehead): Declare.
|
||||
* langhooks.h (lhd_make_node): Declare.
|
||||
(LANG_HOOKS_MAKE_TYPE): Default to new function,
|
||||
* langhooks.c (lhd_make_node): New.
|
||||
* rtl.c (rtx_alloc_stat, swallow_copy_rtx_stat): Rename from ... ; pass
|
||||
locations.
|
||||
(rtx_alloc, swallow_copy_rtx): ... this one.
|
||||
* rtl.h (rtx_alloc, swallow_copy_rtx): Turn to macros.
|
||||
* rtl.c (rtx_alloc_stat, swallow_copy_rtx_stat): Declare.
|
||||
* toplpev.c (finalize): Dump stats.
|
||||
* tree.c (make_node_stat, copy_node_stat, make_tree_vec_stat,
|
||||
build_tree_list_stat, tree_cons_stat, build?_stat, build_decl_stat):
|
||||
Rename from ... ; pass locators.
|
||||
(make_node, copy_node, make_tree_vec, build_tree_list, tree_cons,
|
||||
build?, build_decl): Declare.
|
||||
* tree.h (make_node_stat, copy_node_stat, make_tree_vec_stat,
|
||||
build_tree_list_stat, tree_cons_stat, build?_stat, build_decl_stat):
|
||||
Declare.
|
||||
(make_node, copy_node, make_tree_vec, build_tree_list, tree_cons,
|
||||
build?, build_decl): New macros.
|
||||
* Makefile.in (RTL_H, TREE_H): Add statistics.h dependency.
|
||||
* statistics.h: New file.
|
||||
|
||||
2004-03-03 Maciej W. Rozycki <macro@ds2.pg.gda.pl>
|
||||
Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
|
@ -663,10 +663,10 @@ LANGHOOKS_DEF_H = langhooks-def.h $(HOOKS_H)
|
||||
TARGET_DEF_H = target-def.h $(HOOKS_H)
|
||||
MACHMODE_H = machmode.h mode-classes.def insn-modes.h
|
||||
RTL_BASE_H = rtl.h rtl.def $(MACHMODE_H)
|
||||
RTL_H = $(RTL_BASE_H) genrtl.h input.h
|
||||
RTL_H = $(RTL_BASE_H) genrtl.h input.h statistics.h
|
||||
PARAMS_H = params.h params.def
|
||||
TREE_H = tree.h tree.def $(MACHMODE_H) tree-check.h version.h builtins.def \
|
||||
input.h
|
||||
input.h statistics.h
|
||||
BASIC_BLOCK_H = basic-block.h bitmap.h sbitmap.h varray.h $(PARTITION_H) \
|
||||
hard-reg-set.h cfghooks.h
|
||||
COVERAGE_H = coverage.h gcov-io.h gcov-iov.h
|
||||
|
147
gcc/ggc-common.c
147
gcc/ggc-common.c
@ -129,22 +129,22 @@ ggc_mark_roots (void)
|
||||
|
||||
/* Allocate a block of memory, then clear it. */
|
||||
void *
|
||||
ggc_alloc_cleared (size_t size)
|
||||
ggc_alloc_cleared_stat (size_t size MEM_STAT_DECL)
|
||||
{
|
||||
void *buf = ggc_alloc (size);
|
||||
void *buf = ggc_alloc_stat (size PASS_MEM_STAT);
|
||||
memset (buf, 0, size);
|
||||
return buf;
|
||||
}
|
||||
|
||||
/* Resize a block of memory, possibly re-allocating it. */
|
||||
void *
|
||||
ggc_realloc (void *x, size_t size)
|
||||
ggc_realloc_stat (void *x, size_t size MEM_STAT_DECL)
|
||||
{
|
||||
void *r;
|
||||
size_t old_size;
|
||||
|
||||
if (x == NULL)
|
||||
return ggc_alloc (size);
|
||||
return ggc_alloc_stat (size PASS_MEM_STAT);
|
||||
|
||||
old_size = ggc_get_size (x);
|
||||
|
||||
@ -166,7 +166,7 @@ ggc_realloc (void *x, size_t size)
|
||||
return x;
|
||||
}
|
||||
|
||||
r = ggc_alloc (size);
|
||||
r = ggc_alloc_stat (size PASS_MEM_STAT);
|
||||
|
||||
/* Since ggc_get_size returns the size of the pool, not the size of the
|
||||
individually allocated object, we'd access parts of the old object
|
||||
@ -761,3 +761,140 @@ init_ggc_heuristics (void)
|
||||
set_param_value ("ggc-min-heapsize", ggc_min_heapsize_heuristic());
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef GATHER_STATISTICS
|
||||
|
||||
/* Datastructure used to store per-call-site statistics. */
|
||||
struct loc_descriptor
|
||||
{
|
||||
const char *file;
|
||||
int line;
|
||||
const char *function;
|
||||
int times;
|
||||
size_t allocated;
|
||||
size_t overhead;
|
||||
};
|
||||
|
||||
/* Hashtable used for statistics. */
|
||||
static htab_t loc_hash;
|
||||
|
||||
/* Hash table helpers functions. */
|
||||
static hashval_t
|
||||
hash_descriptor (const void *p)
|
||||
{
|
||||
const struct loc_descriptor *d = p;
|
||||
|
||||
return htab_hash_pointer (d->function) | d->line;
|
||||
}
|
||||
|
||||
static int
|
||||
eq_descriptor (const void *p1, const void *p2)
|
||||
{
|
||||
const struct loc_descriptor *d = p1;
|
||||
const struct loc_descriptor *d2 = p2;
|
||||
|
||||
return (d->file == d2->file && d->line == d2->line
|
||||
&& d->function == d2->function);
|
||||
}
|
||||
|
||||
/* Return descriptor for given call site, create new one if needed. */
|
||||
static struct loc_descriptor *
|
||||
loc_descriptor (const char *name, int line, const char *function)
|
||||
{
|
||||
struct loc_descriptor loc;
|
||||
struct loc_descriptor **slot;
|
||||
|
||||
loc.file = name;
|
||||
loc.line = line;
|
||||
loc.function = function;
|
||||
if (!loc_hash)
|
||||
loc_hash = htab_create (10, hash_descriptor, eq_descriptor, NULL);
|
||||
|
||||
slot = (struct loc_descriptor **) htab_find_slot (loc_hash, &loc, 1);
|
||||
if (*slot)
|
||||
return *slot;
|
||||
*slot = xcalloc (sizeof (**slot), 1);
|
||||
(*slot)->file = name;
|
||||
(*slot)->line = line;
|
||||
(*slot)->function = function;
|
||||
return *slot;
|
||||
}
|
||||
|
||||
/* Record ALLOCATED and OVERHEAD bytes to descritor NAME:LINE (FUNCTION). */
|
||||
void ggc_record_overhead (size_t allocated, size_t overhead,
|
||||
const char *name, int line, const char *function)
|
||||
{
|
||||
struct loc_descriptor *loc = loc_descriptor (name, line, function);
|
||||
|
||||
loc->times++;
|
||||
loc->allocated+=allocated;
|
||||
loc->overhead+=overhead;
|
||||
}
|
||||
|
||||
/* Helper for qsort; sort descriptors by amount of memory consumed. */
|
||||
static int
|
||||
cmp_statistic (const void *loc1, const void *loc2)
|
||||
{
|
||||
struct loc_descriptor *l1 = *(struct loc_descriptor **) loc1;
|
||||
struct loc_descriptor *l2 = *(struct loc_descriptor **) loc2;
|
||||
return (l1->allocated + l1->overhead) - (l2->allocated + l2->overhead);
|
||||
}
|
||||
|
||||
/* Collect array of the descriptors from hashtable. */
|
||||
struct loc_descriptor **loc_array;
|
||||
static int
|
||||
add_statistics (void **slot, void *b)
|
||||
{
|
||||
int *n = (int *)b;
|
||||
loc_array[*n] = (struct loc_descriptor *) *slot;
|
||||
(*n)++;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Dump per-site memory statistics. */
|
||||
#endif
|
||||
void dump_ggc_loc_statistics (void)
|
||||
{
|
||||
#ifdef GATHER_STATISTICS
|
||||
int nentries = 0;
|
||||
char s[4096];
|
||||
size_t count, size, overhead;
|
||||
int i;
|
||||
|
||||
loc_array = xcalloc (sizeof (*loc_array), loc_hash->n_elements);
|
||||
fprintf (stderr, "-------------------------------------------------------\n");
|
||||
fprintf (stderr, "\n%-60s %10s %10s %10s\n",
|
||||
"source location", "Times", "Allocated", "Overhead");
|
||||
fprintf (stderr, "-------------------------------------------------------\n");
|
||||
count = 0;
|
||||
size = 0;
|
||||
overhead = 0;
|
||||
htab_traverse (loc_hash, add_statistics, &nentries);
|
||||
qsort (loc_array, nentries, sizeof (*loc_array), cmp_statistic);
|
||||
for (i = 0; i < nentries; i++)
|
||||
{
|
||||
struct loc_descriptor *d = loc_array[i];
|
||||
size += d->allocated;
|
||||
count += d->times;
|
||||
overhead += d->overhead;
|
||||
}
|
||||
for (i = 0; i < nentries; i++)
|
||||
{
|
||||
struct loc_descriptor *d = loc_array[i];
|
||||
if (d->allocated)
|
||||
{
|
||||
const char *s1 = d->file;
|
||||
const char *s2;
|
||||
while ((s2 = strstr (s1, "gcc/")))
|
||||
s1 = s2 + 4;
|
||||
sprintf (s, "%s:%i (%s)", s1, d->line, d->function);
|
||||
fprintf (stderr, "%-60s %10i %10li %10li:%.3f%%\n", s,
|
||||
d->times, (long)d->allocated, (long)d->overhead,
|
||||
(d->allocated + d->overhead) *100.0 / (size + overhead));
|
||||
}
|
||||
}
|
||||
fprintf (stderr, "%-60s %10ld %10ld %10ld\n",
|
||||
"Total", (long)count, (long)size, (long)overhead);
|
||||
fprintf (stderr, "-------------------------------------------------------\n");
|
||||
#endif
|
||||
}
|
||||
|
@ -32,31 +32,33 @@ struct alloc_zone *rtl_zone = NULL;
|
||||
struct alloc_zone *garbage_zone = NULL;
|
||||
|
||||
void *
|
||||
ggc_alloc_typed (enum gt_types_enum gte ATTRIBUTE_UNUSED, size_t size)
|
||||
ggc_alloc_typed_stat (enum gt_types_enum gte ATTRIBUTE_UNUSED, size_t size
|
||||
MEM_STAT_DECL)
|
||||
{
|
||||
return xmalloc (size);
|
||||
}
|
||||
|
||||
void *
|
||||
ggc_alloc (size_t size)
|
||||
ggc_alloc_stat (size_t size MEM_STAT_DECL)
|
||||
{
|
||||
return xmalloc (size);
|
||||
}
|
||||
|
||||
void *
|
||||
ggc_alloc_zone (size_t size, struct alloc_zone *zone ATTRIBUTE_UNUSED)
|
||||
ggc_alloc_zone_stat (size_t size, struct alloc_zone *zone ATTRIBUTE_UNUSED
|
||||
MEM_STAT_DECL)
|
||||
{
|
||||
return xmalloc (size);
|
||||
}
|
||||
|
||||
void *
|
||||
ggc_alloc_cleared (size_t size)
|
||||
ggc_alloc_cleared_stat (size_t size MEM_STAT_DECL)
|
||||
{
|
||||
return xcalloc (size, 1);
|
||||
}
|
||||
|
||||
void *
|
||||
ggc_realloc (void *x, size_t size)
|
||||
ggc_realloc_stat (void *x, size_t size MEM_STAT_DECL)
|
||||
{
|
||||
return xrealloc (x, size);
|
||||
}
|
||||
|
@ -1044,23 +1044,25 @@ static unsigned char size_lookup[257] =
|
||||
/* Typed allocation function. Does nothing special in this collector. */
|
||||
|
||||
void *
|
||||
ggc_alloc_typed (enum gt_types_enum type ATTRIBUTE_UNUSED, size_t size)
|
||||
ggc_alloc_typed_stat (enum gt_types_enum type ATTRIBUTE_UNUSED, size_t size
|
||||
MEM_STAT_DECL)
|
||||
{
|
||||
return ggc_alloc (size);
|
||||
return ggc_alloc_stat (size PASS_MEM_STAT);
|
||||
}
|
||||
|
||||
/* Zone allocation function. Does nothing special in this collector. */
|
||||
|
||||
void *
|
||||
ggc_alloc_zone (size_t size, struct alloc_zone *zone ATTRIBUTE_UNUSED)
|
||||
ggc_alloc_zone_stat (size_t size, struct alloc_zone *zone ATTRIBUTE_UNUSED
|
||||
MEM_STAT_DECL)
|
||||
{
|
||||
return ggc_alloc (size);
|
||||
return ggc_alloc_stat (size PASS_MEM_STAT);
|
||||
}
|
||||
|
||||
/* Allocate a chunk of memory of SIZE bytes. Its contents are undefined. */
|
||||
|
||||
void *
|
||||
ggc_alloc (size_t size)
|
||||
ggc_alloc_stat (size_t size MEM_STAT_DECL)
|
||||
{
|
||||
size_t order, word, bit, object_offset, object_size;
|
||||
struct page_entry *entry;
|
||||
@ -1171,6 +1173,9 @@ ggc_alloc (size_t size)
|
||||
G.page_tails[order]->next = entry;
|
||||
G.page_tails[order] = entry;
|
||||
}
|
||||
#ifdef GATHER_STATISTICS
|
||||
ggc_record_overhead (OBJECT_SIZE (order), OBJECT_SIZE (order) - size PASS_MEM_STAT);
|
||||
#endif
|
||||
|
||||
/* Calculate the object's address. */
|
||||
result = entry->page + object_offset;
|
||||
|
23
gcc/ggc.h
23
gcc/ggc.h
@ -21,6 +21,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
|
||||
#ifndef GCC_GGC_H
|
||||
#define GCC_GGC_H
|
||||
#include "statistics.h"
|
||||
|
||||
/* Symbols are marked with `ggc' for `gcc gc' so as not to interfere with
|
||||
an external gc library that might be linked in. */
|
||||
@ -210,21 +211,31 @@ extern struct alloc_zone *rtl_zone;
|
||||
extern struct alloc_zone *tree_zone;
|
||||
|
||||
/* The internal primitive. */
|
||||
extern void *ggc_alloc (size_t);
|
||||
extern void *ggc_alloc_stat (size_t MEM_STAT_DECL);
|
||||
#define ggc_alloc(s) ggc_alloc_stat (s MEM_STAT_INFO)
|
||||
/* Allocate an object into the specified allocation zone. */
|
||||
extern void *ggc_alloc_zone (size_t, struct alloc_zone *);
|
||||
extern void *ggc_alloc_zone_stat (size_t, struct alloc_zone * MEM_STAT_DECL);
|
||||
#define ggc_alloc_zone(s,z) ggc_alloc_zone_stat (s,z MEM_STAT_INFO)
|
||||
/* Allocate an object of the specified type and size. */
|
||||
extern void *ggc_alloc_typed (enum gt_types_enum, size_t);
|
||||
extern void *ggc_alloc_typed_stat (enum gt_types_enum, size_t MEM_STAT_DECL);
|
||||
#define ggc_alloc_typed(s,z) ggc_alloc_typed_stat (s,z MEM_STAT_INFO)
|
||||
/* Like ggc_alloc, but allocates cleared memory. */
|
||||
extern void *ggc_alloc_cleared (size_t);
|
||||
extern void *ggc_alloc_cleared_stat (size_t MEM_STAT_DECL);
|
||||
#define ggc_alloc_cleared(s) ggc_alloc_cleared_stat (s MEM_STAT_INFO)
|
||||
/* Like ggc_alloc_zone, but allocates cleared memory. */
|
||||
extern void *ggc_alloc_cleared_zone (size_t, struct alloc_zone *);
|
||||
extern void *ggc_alloc_cleared_zone (size_t, struct alloc_zone * MEM_STAT_DECL);
|
||||
#define ggc_alloc_cleared_zone(s,z) ggc_alloc_cleared_stat (s,z MEM_STAT_INFO)
|
||||
/* Resize a block. */
|
||||
extern void *ggc_realloc (void *, size_t);
|
||||
extern void *ggc_realloc_stat (void *, size_t MEM_STAT_DECL);
|
||||
#define ggc_realloc(s,z) ggc_realloc_stat (s,z MEM_STAT_INFO)
|
||||
/* Like ggc_alloc_cleared, but performs a multiplication. */
|
||||
extern void *ggc_calloc (size_t, size_t);
|
||||
/* Free a block. To be used when known for certain it's not reachable. */
|
||||
extern void ggc_free (void *);
|
||||
|
||||
extern void ggc_record_overhead (size_t, size_t MEM_STAT_DECL);
|
||||
|
||||
extern void dump_ggc_loc_statistics (void);
|
||||
|
||||
#define ggc_alloc_rtx(CODE) \
|
||||
((rtx) ggc_alloc_typed (gt_ggc_e_7rtx_def, RTX_SIZE (CODE)))
|
||||
|
@ -206,6 +206,7 @@ extern tree lhd_callgraph_analyze_expr (tree *, int *, tree);
|
||||
/* Tree dump hooks. */
|
||||
extern bool lhd_tree_dump_dump_tree (void *, tree);
|
||||
extern int lhd_tree_dump_type_quals (tree);
|
||||
extern tree lhd_make_node (enum tree_code);
|
||||
|
||||
#define LANG_HOOKS_TREE_DUMP_DUMP_TREE_FN lhd_tree_dump_dump_tree
|
||||
#define LANG_HOOKS_TREE_DUMP_TYPE_QUALS_FN lhd_tree_dump_type_quals
|
||||
@ -217,7 +218,7 @@ extern int lhd_tree_dump_type_quals (tree);
|
||||
|
||||
/* Types hooks. There are no reasonable defaults for most of them,
|
||||
so we create a compile-time error instead. */
|
||||
#define LANG_HOOKS_MAKE_TYPE make_node
|
||||
#define LANG_HOOKS_MAKE_TYPE lhd_make_node
|
||||
#define LANG_HOOKS_INCOMPLETE_TYPE_ERROR lhd_incomplete_type_error
|
||||
#define LANG_HOOKS_TYPE_PROMOTES_TO lhd_type_promotes_to
|
||||
#define LANG_HOOKS_REGISTER_BUILTIN_TYPE lhd_register_builtin_type
|
||||
|
@ -562,4 +562,10 @@ lhd_callgraph_analyze_expr (tree *tp ATTRIBUTE_UNUSED,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
tree
|
||||
lhd_make_node (enum tree_code code)
|
||||
{
|
||||
return make_node (code);
|
||||
}
|
||||
|
||||
#include "gt-langhooks.h"
|
||||
|
@ -173,11 +173,11 @@ rtvec_alloc (int n)
|
||||
all the rest is initialized to zero. */
|
||||
|
||||
rtx
|
||||
rtx_alloc (RTX_CODE code)
|
||||
rtx_alloc_stat (RTX_CODE code MEM_STAT_DECL)
|
||||
{
|
||||
rtx rt;
|
||||
|
||||
rt = ggc_alloc_rtx (code);
|
||||
rt = ggc_alloc_typed_stat (gt_ggc_e_7rtx_def, RTX_SIZE (code) PASS_MEM_STAT);
|
||||
|
||||
/* We want to clear everything up to the FLD array. Normally, this
|
||||
is one int, but we don't want to assume that and it isn't very
|
||||
@ -309,11 +309,12 @@ copy_rtx (rtx orig)
|
||||
/* Create a new copy of an rtx. Only copy just one level. */
|
||||
|
||||
rtx
|
||||
shallow_copy_rtx (rtx orig)
|
||||
shallow_copy_rtx_stat (rtx orig MEM_STAT_DECL)
|
||||
{
|
||||
rtx copy;
|
||||
|
||||
copy = ggc_alloc_rtx (GET_CODE (orig));
|
||||
copy = ggc_alloc_typed_stat (gt_ggc_e_7rtx_def, RTX_SIZE (GET_CODE (orig))
|
||||
PASS_MEM_STAT);
|
||||
memcpy (copy, orig, RTX_SIZE (GET_CODE (orig)));
|
||||
return copy;
|
||||
}
|
||||
|
@ -21,6 +21,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
|
||||
#ifndef GCC_RTL_H
|
||||
#define GCC_RTL_H
|
||||
#include "statistics.h"
|
||||
|
||||
struct function;
|
||||
|
||||
@ -1556,9 +1557,12 @@ extern rtx emit_copy_of_insn_after (rtx, rtx);
|
||||
extern void set_reg_attrs_from_mem (rtx, rtx);
|
||||
extern void set_mem_attrs_from_reg (rtx, rtx);
|
||||
extern void set_reg_attrs_for_parm (rtx, rtx);
|
||||
extern void set_reg_pointer_align (rtx, unsigned int);
|
||||
|
||||
/* In rtl.c */
|
||||
extern rtx rtx_alloc (RTX_CODE);
|
||||
extern rtx rtx_alloc_stat (RTX_CODE MEM_STAT_DECL);
|
||||
#define rtx_alloc(c) rtx_alloc_stat (c MEM_STAT_INFO)
|
||||
|
||||
extern rtvec rtvec_alloc (int);
|
||||
extern rtx copy_rtx (rtx);
|
||||
extern void dump_rtx_statistics (void);
|
||||
@ -1568,7 +1572,8 @@ extern rtx copy_rtx_if_shared (rtx);
|
||||
|
||||
/* In rtl.c */
|
||||
extern rtx copy_most_rtx (rtx, rtx);
|
||||
extern rtx shallow_copy_rtx (rtx);
|
||||
extern rtx shallow_copy_rtx_stat (rtx MEM_STAT_DECL);
|
||||
#define shallow_copy_rtx(a) shallow_copy_rtx_stat (a MEM_STAT_INFO)
|
||||
extern int rtx_equal_p (rtx, rtx);
|
||||
|
||||
/* In emit-rtl.c */
|
||||
|
34
gcc/statistics.h
Normal file
34
gcc/statistics.h
Normal file
@ -0,0 +1,34 @@
|
||||
/* Memory statistics helpers.
|
||||
Copyright (C) 2004
|
||||
Free Software Foundation, Inc.
|
||||
Contributed by Cygnus Solutions.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
GCC is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2, or (at your option)
|
||||
any later version.
|
||||
|
||||
GCC is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
||||
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
|
||||
License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GCC; see the file COPYING. If not, write to the Free
|
||||
the Free Software Foundation, 59 Temple Place - Suite 330, Boston,
|
||||
MA 02111-1307, USA. */
|
||||
|
||||
#ifndef GCC_STATISTICS
|
||||
#define GCC_STATISTICS
|
||||
#ifdef GATHER_STATISTICS
|
||||
#define MEM_STAT_DECL , const char *_loc_name ATTRIBUTE_UNUSED, int _loc_line ATTRIBUTE_UNUSED, const char *_loc_function ATTRIBUTE_UNUSED
|
||||
#define PASS_MEM_STAT , _loc_name, _loc_line, _loc_function
|
||||
#define MEM_STAT_INFO , __FILE__, __LINE__, __FUNCTION__
|
||||
#else
|
||||
#define MEM_STAT_DECL
|
||||
#define PASS_MEM_STAT
|
||||
#define MEM_STAT_INFO
|
||||
#endif
|
||||
#endif
|
@ -2527,6 +2527,7 @@ finalize (void)
|
||||
dump_rtx_statistics ();
|
||||
dump_varray_statistics ();
|
||||
dump_alloc_pool_statistics ();
|
||||
dump_ggc_loc_statistics ();
|
||||
}
|
||||
|
||||
/* Free up memory for the benefit of leak detectors. */
|
||||
|
49
gcc/tree.c
49
gcc/tree.c
@ -200,7 +200,7 @@ tree_size (tree node)
|
||||
Achoo! I got a code in the node. */
|
||||
|
||||
tree
|
||||
make_node (enum tree_code code)
|
||||
make_node_stat (enum tree_code code MEM_STAT_DECL)
|
||||
{
|
||||
tree t;
|
||||
int type = TREE_CODE_CLASS (code);
|
||||
@ -269,7 +269,7 @@ make_node (enum tree_code code)
|
||||
tree_node_sizes[(int) kind] += length;
|
||||
#endif
|
||||
|
||||
t = ggc_alloc_tree (length);
|
||||
t = ggc_alloc_zone_stat (length, tree_zone PASS_MEM_STAT);
|
||||
|
||||
memset (t, 0, length);
|
||||
|
||||
@ -340,14 +340,14 @@ make_node (enum tree_code code)
|
||||
TREE_CHAIN is zero and it has a fresh uid. */
|
||||
|
||||
tree
|
||||
copy_node (tree node)
|
||||
copy_node_stat (tree node MEM_STAT_DECL)
|
||||
{
|
||||
tree t;
|
||||
enum tree_code code = TREE_CODE (node);
|
||||
size_t length;
|
||||
|
||||
length = tree_size (node);
|
||||
t = ggc_alloc_tree (length);
|
||||
t = ggc_alloc_zone_stat (length, tree_zone PASS_MEM_STAT);
|
||||
memcpy (t, node, length);
|
||||
|
||||
TREE_CHAIN (t) = 0;
|
||||
@ -554,7 +554,7 @@ build_complex (tree type, tree real, tree imag)
|
||||
/* Build a newly constructed TREE_VEC node of length LEN. */
|
||||
|
||||
tree
|
||||
make_tree_vec (int len)
|
||||
make_tree_vec_stat (int len MEM_STAT_DECL)
|
||||
{
|
||||
tree t;
|
||||
int length = (len - 1) * sizeof (tree) + sizeof (struct tree_vec);
|
||||
@ -564,9 +564,10 @@ make_tree_vec (int len)
|
||||
tree_node_sizes[(int) vec_kind] += length;
|
||||
#endif
|
||||
|
||||
t = ggc_alloc_tree (length);
|
||||
t = ggc_alloc_zone_stat (length, tree_zone PASS_MEM_STAT);
|
||||
|
||||
memset (t, 0, length);
|
||||
|
||||
TREE_SET_CODE (t, TREE_VEC);
|
||||
TREE_VEC_LENGTH (t) = len;
|
||||
|
||||
@ -1024,9 +1025,9 @@ nreverse (tree t)
|
||||
purpose and value fields are PARM and VALUE. */
|
||||
|
||||
tree
|
||||
build_tree_list (tree parm, tree value)
|
||||
build_tree_list_stat (tree parm, tree value MEM_STAT_DECL)
|
||||
{
|
||||
tree t = make_node (TREE_LIST);
|
||||
tree t = make_node_stat (TREE_LIST PASS_MEM_STAT);
|
||||
TREE_PURPOSE (t) = parm;
|
||||
TREE_VALUE (t) = value;
|
||||
return t;
|
||||
@ -1037,11 +1038,12 @@ build_tree_list (tree parm, tree value)
|
||||
and whose TREE_CHAIN is CHAIN. */
|
||||
|
||||
tree
|
||||
tree_cons (tree purpose, tree value, tree chain)
|
||||
tree_cons_stat (tree purpose, tree value, tree chain MEM_STAT_DECL)
|
||||
{
|
||||
tree node;
|
||||
|
||||
node = ggc_alloc_tree (sizeof (struct tree_list));
|
||||
node = ggc_alloc_zone_stat (sizeof (struct tree_list),
|
||||
tree_zone PASS_MEM_STAT);
|
||||
|
||||
memset (node, 0, sizeof (struct tree_common));
|
||||
|
||||
@ -2296,7 +2298,7 @@ stabilize_reference_1 (tree e)
|
||||
magic within the build macro. */
|
||||
|
||||
tree
|
||||
build0 (enum tree_code code, tree tt)
|
||||
build0_stat (enum tree_code code, tree tt MEM_STAT_DECL)
|
||||
{
|
||||
tree t;
|
||||
|
||||
@ -2305,14 +2307,14 @@ build0 (enum tree_code code, tree tt)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
t = make_node_stat (code PASS_MEM_STAT);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
tree
|
||||
build1 (enum tree_code code, tree type, tree node)
|
||||
build1_stat (enum tree_code code, tree type, tree node MEM_STAT_DECL)
|
||||
{
|
||||
int length = sizeof (struct tree_exp);
|
||||
#ifdef GATHER_STATISTICS
|
||||
@ -2343,7 +2345,7 @@ build1 (enum tree_code code, tree type, tree node)
|
||||
abort ();
|
||||
#endif /* ENABLE_CHECKING */
|
||||
|
||||
t = ggc_alloc_tree (length);
|
||||
t = ggc_alloc_zone_stat (length, tree_zone PASS_MEM_STAT);
|
||||
|
||||
memset (t, 0, sizeof (struct tree_common));
|
||||
|
||||
@ -2429,7 +2431,7 @@ build1 (enum tree_code code, tree type, tree node)
|
||||
} while (0)
|
||||
|
||||
tree
|
||||
build2 (enum tree_code code, tree tt, tree arg0, tree arg1)
|
||||
build2_stat (enum tree_code code, tree tt, tree arg0, tree arg1 MEM_STAT_DECL)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
@ -2440,7 +2442,7 @@ build2 (enum tree_code code, tree tt, tree arg0, tree arg1)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
t = make_node_stat (code PASS_MEM_STAT);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
/* Below, we automatically set TREE_SIDE_EFFECTS and TREE_READONLY for the
|
||||
@ -2487,7 +2489,8 @@ build2 (enum tree_code code, tree tt, tree arg0, tree arg1)
|
||||
}
|
||||
|
||||
tree
|
||||
build3 (enum tree_code code, tree tt, tree arg0, tree arg1, tree arg2)
|
||||
build3_stat (enum tree_code code, tree tt, tree arg0, tree arg1,
|
||||
tree arg2 MEM_STAT_DECL)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
@ -2508,7 +2511,7 @@ build3 (enum tree_code code, tree tt, tree arg0, tree arg1, tree arg2)
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
t = make_node_stat (code PASS_MEM_STAT);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
fro = first_rtl_op (code);
|
||||
@ -2525,8 +2528,8 @@ build3 (enum tree_code code, tree tt, tree arg0, tree arg1, tree arg2)
|
||||
}
|
||||
|
||||
tree
|
||||
build4 (enum tree_code code, tree tt, tree arg0, tree arg1,
|
||||
tree arg2, tree arg3)
|
||||
build4_stat (enum tree_code code, tree tt, tree arg0, tree arg1,
|
||||
tree arg2, tree arg3 MEM_STAT_DECL)
|
||||
{
|
||||
bool constant, read_only, side_effects;
|
||||
tree t;
|
||||
@ -2537,7 +2540,7 @@ build4 (enum tree_code code, tree tt, tree arg0, tree arg1,
|
||||
abort ();
|
||||
#endif
|
||||
|
||||
t = make_node (code);
|
||||
t = make_node_stat (code PASS_MEM_STAT);
|
||||
TREE_TYPE (t) = tt;
|
||||
|
||||
fro = first_rtl_op (code);
|
||||
@ -2631,11 +2634,11 @@ build_nt (enum tree_code code, ...)
|
||||
Other slots are initialized to 0 or null pointers. */
|
||||
|
||||
tree
|
||||
build_decl (enum tree_code code, tree name, tree type)
|
||||
build_decl_stat (enum tree_code code, tree name, tree type MEM_STAT_DECL)
|
||||
{
|
||||
tree t;
|
||||
|
||||
t = make_node (code);
|
||||
t = make_node_stat (code PASS_MEM_STAT);
|
||||
|
||||
/* if (type == error_mark_node)
|
||||
type = integer_type_node; */
|
||||
|
35
gcc/tree.h
35
gcc/tree.h
@ -25,6 +25,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#include "machmode.h"
|
||||
#include "version.h"
|
||||
#include "input.h"
|
||||
#include "statistics.h"
|
||||
|
||||
/* Codes of tree nodes */
|
||||
|
||||
@ -2066,11 +2067,13 @@ extern size_t tree_size (tree);
|
||||
The TREE_CODE is the only argument. Contents are initialized
|
||||
to zero except for a few of the common fields. */
|
||||
|
||||
extern tree make_node (enum tree_code);
|
||||
extern tree make_node_stat (enum tree_code MEM_STAT_DECL);
|
||||
#define make_node(t) make_node_stat (t MEM_STAT_INFO)
|
||||
|
||||
/* Make a copy of a node, with all the same contents. */
|
||||
|
||||
extern tree copy_node (tree);
|
||||
extern tree copy_node_stat (tree MEM_STAT_DECL);
|
||||
#define copy_node(t) copy_node_stat (t MEM_STAT_INFO)
|
||||
|
||||
/* Make a copy of a chain of TREE_LIST nodes. */
|
||||
|
||||
@ -2078,7 +2081,8 @@ extern tree copy_list (tree);
|
||||
|
||||
/* Make a TREE_VEC. */
|
||||
|
||||
extern tree make_tree_vec (int);
|
||||
extern tree make_tree_vec_stat (int MEM_STAT_DECL);
|
||||
#define make_tree_vec(t) make_tree_vec_stat (t MEM_STAT_INFO)
|
||||
|
||||
/* Return the (unique) IDENTIFIER_NODE node for a given name.
|
||||
The name is supplied as a char *. */
|
||||
@ -2124,11 +2128,17 @@ extern tree build_nt (enum tree_code, ...);
|
||||
#define _buildC2(x,a1,a2,a3,a4,a5,a6,a7,a8,a9,c,...) c
|
||||
#endif
|
||||
|
||||
extern tree build0 (enum tree_code, tree);
|
||||
extern tree build1 (enum tree_code, tree, tree);
|
||||
extern tree build2 (enum tree_code, tree, tree, tree);
|
||||
extern tree build3 (enum tree_code, tree, tree, tree, tree);
|
||||
extern tree build4 (enum tree_code, tree, tree, tree, tree, tree);
|
||||
extern tree build0_stat (enum tree_code, tree MEM_STAT_DECL);
|
||||
#define build0(c,t) build0_stat (c,t MEM_STAT_INFO)
|
||||
extern tree build1_stat (enum tree_code, tree, tree MEM_STAT_DECL);
|
||||
#define build1(c,t1,t2) build1_stat (c,t1,t2 MEM_STAT_INFO)
|
||||
extern tree build2_stat (enum tree_code, tree, tree, tree MEM_STAT_DECL);
|
||||
#define build2(c,t1,t2,t3) build2_stat (c,t1,t2,t3 MEM_STAT_INFO)
|
||||
extern tree build3_stat (enum tree_code, tree, tree, tree, tree MEM_STAT_DECL);
|
||||
#define build3(c,t1,t2,t3,t4) build3_stat (c,t1,t2,t3,t4 MEM_STAT_INFO)
|
||||
extern tree build4_stat (enum tree_code, tree, tree, tree, tree,
|
||||
tree MEM_STAT_DECL);
|
||||
#define build4(c,t1,t2,t3,t4,t5) build4_stat (c,t1,t2,t3,t4,t5 MEM_STAT_INFO)
|
||||
|
||||
extern tree build_int_2_wide (unsigned HOST_WIDE_INT, HOST_WIDE_INT);
|
||||
extern tree build_vector (tree, tree);
|
||||
@ -2136,8 +2146,10 @@ extern tree build_constructor (tree, tree);
|
||||
extern tree build_real_from_int_cst (tree, tree);
|
||||
extern tree build_complex (tree, tree, tree);
|
||||
extern tree build_string (int, const char *);
|
||||
extern tree build_tree_list (tree, tree);
|
||||
extern tree build_decl (enum tree_code, tree, tree);
|
||||
extern tree build_tree_list_stat (tree, tree MEM_STAT_DECL);
|
||||
#define build_tree_list(t,q) build_tree_list_stat(t,q MEM_STAT_INFO)
|
||||
extern tree build_decl_stat (enum tree_code, tree, tree MEM_STAT_DECL);
|
||||
#define build_decl(c,t,q) build_decl_stat (c,t,q MEM_STAT_INFO)
|
||||
extern tree build_block (tree, tree, tree, tree, tree);
|
||||
extern tree build_expr_wfl (tree, const char *, int, int);
|
||||
|
||||
@ -2495,7 +2507,8 @@ extern tree chainon (tree, tree);
|
||||
|
||||
/* Make a new TREE_LIST node from specified PURPOSE, VALUE and CHAIN. */
|
||||
|
||||
extern tree tree_cons (tree, tree, tree);
|
||||
extern tree tree_cons_stat (tree, tree, tree MEM_STAT_DECL);
|
||||
#define tree_cons(t,q,w) tree_cons_stat (t,q,w MEM_STAT_INFO)
|
||||
|
||||
/* Return the last tree node in a chain. */
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user