diff options
author | rth <rth@138bc75d-0d04-0410-961f-82ee72b054a4> | 2002-04-28 20:40:39 +0000 |
---|---|---|
committer | rth <rth@138bc75d-0d04-0410-961f-82ee72b054a4> | 2002-04-28 20:40:39 +0000 |
commit | ec1d95967451333d9e9633d851a76ac98e7b526a (patch) | |
tree | 2d1cd87e9ec72ca228d2bfd87f65be0151f4781f /gcc/ggc-common.c | |
parent | 73c5fe4f950e8d8b4085d363dc143422807d7e9a (diff) | |
download | gcc-ec1d95967451333d9e9633d851a76ac98e7b526a.tar.gz |
* ggc-common.c (ggc_mark_rtx_children_1): Rename from...
(ggc_mark_rtx_children): New.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@52864 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/ggc-common.c')
-rw-r--r-- | gcc/ggc-common.c | 38 |
1 files changed, 38 insertions, 0 deletions
diff --git a/gcc/ggc-common.c b/gcc/ggc-common.c index 6a6b69b3dd8..a90a01fb51a 100644 --- a/gcc/ggc-common.c +++ b/gcc/ggc-common.c @@ -38,6 +38,7 @@ static ggc_statistics *ggc_stats; /* Trees that have been marked, but whose children still need marking. */ varray_type ggc_pending_trees; +static void ggc_mark_rtx_children_1 PARAMS ((rtx)); static void ggc_mark_rtx_ptr PARAMS ((void *)); static void ggc_mark_tree_ptr PARAMS ((void *)); static void ggc_mark_rtx_varray_ptr PARAMS ((void *)); @@ -272,6 +273,43 @@ void ggc_mark_rtx_children (r) rtx r; { + rtx i, last; + + /* Special case the instruction chain. This is a data structure whose + chain length is potentially unbounded, and which contain references + within the chain (e.g. label_ref and insn_list). If do nothing here, + we risk blowing the stack recursing through a long chain of insns. + + Combat this by marking all of the instructions in the chain before + marking the contents of those instructions. */ + + switch (GET_CODE (r)) + { + case INSN: + case JUMP_INSN: + case CALL_INSN: + case NOTE: + case CODE_LABEL: + case BARRIER: + for (i = NEXT_INSN (r); ; i = NEXT_INSN (i)) + if (! ggc_test_and_set_mark (i)) + break; + last = i; + + for (i = NEXT_INSN (r); i != last; i = NEXT_INSN (i)) + ggc_mark_rtx_children_1 (i); + + default: + break; + } + + ggc_mark_rtx_children_1 (r); +} + +static void +ggc_mark_rtx_children_1 (r) + rtx r; +{ const char *fmt; int i; rtx next_rtx; |