diff options
author | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2004-01-22 11:35:58 +0000 |
---|---|---|
committer | hubicka <hubicka@138bc75d-0d04-0410-961f-82ee72b054a4> | 2004-01-22 11:35:58 +0000 |
commit | e5b19a8c19bd2ca1c92c36d51470441ef321034d (patch) | |
tree | 43cf04739c20a68832ea083d53c405fbe3c9949f /gcc/alias.c | |
parent | 2f733a64eb6e0b0db554f9b50aa02f6409cf162a (diff) | |
download | gcc-e5b19a8c19bd2ca1c92c36d51470441ef321034d.tar.gz |
* alias.c (reg_base_value): Turn into varray.
(reg_base_value_size): Kill.
(old_reg_base_value): New deletable varray.
(alias_invariant_size): New variable.
(REG_BASE_VALUE): Update to use varray.
(find_base_value): Likewise.
(record_set): Likewise.
(record_base_value): Likewise.
(memrefs_conflict_p): Likewise.
(record_set): Likewise
(record_base_value): Likewise.
(memrefs_conflict_p): Use alias_invariant_size.
(init_alias_analysis): Use varray; set alias_invariant_size;
rescale other arrays to be sized by maxreg.
(end_alias_analysis): Save reg_base_value; clear alias_invariant_size.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@76349 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/alias.c')
-rw-r--r-- | gcc/alias.c | 100 |
1 files changed, 61 insertions, 39 deletions
diff --git a/gcc/alias.c b/gcc/alias.c index 2fd8bc3398a..5fd88120ae4 100644 --- a/gcc/alias.c +++ b/gcc/alias.c @@ -157,17 +157,21 @@ static void memory_modified_1 (rtx, rtx, void *); current function performs nonlocal memory memory references for the purposes of marking the function as a constant function. */ -static GTY((length ("reg_base_value_size"))) rtx *reg_base_value; +static GTY(()) varray_type reg_base_value; static rtx *new_reg_base_value; -static unsigned int reg_base_value_size; /* size of reg_base_value array */ + +/* We preserve the copy of old array around to avoid amount of garbage + produced. About 8% of garbage produced were attributed to this + array. */ +static GTY((deletable (""))) varray_type old_reg_base_value; /* Static hunks of RTL used by the aliasing code; these are initialized once per function to avoid unnecessary RTL allocations. */ static GTY (()) rtx static_reg_base_value[FIRST_PSEUDO_REGISTER]; #define REG_BASE_VALUE(X) \ - (REGNO (X) < reg_base_value_size \ - ? reg_base_value[REGNO (X)] : 0) + (reg_base_value && REGNO (X) < VARRAY_SIZE (reg_base_value) \ + ? VARRAY_RTX (reg_base_value, REGNO (X)) : 0) /* Vector of known invariant relationships between registers. Set in loop unrolling. Indexed by register number, if nonzero the value @@ -178,6 +182,7 @@ static GTY (()) rtx static_reg_base_value[FIRST_PSEUDO_REGISTER]; Because this array contains only pseudo registers it has no effect after reload. */ static rtx *alias_invariant; +unsigned int alias_invariant_size; /* Vector indexed by N giving the initial (unchanging) value known for pseudo-register N. This array is initialized in @@ -778,7 +783,7 @@ find_base_value (rtx src) The test above is not sufficient because the scheduler may move a copy out of an arg reg past the NOTE_INSN_FUNCTION_BEGIN. */ if ((regno >= FIRST_PSEUDO_REGISTER || fixed_regs[regno]) - && regno < reg_base_value_size) + && regno < VARRAY_SIZE (reg_base_value)) { /* If we're inside init_alias_analysis, use new_reg_base_value to reduce the number of relaxation iterations. */ @@ -786,8 +791,8 @@ find_base_value (rtx src) && REG_N_SETS (regno) == 1) return new_reg_base_value[regno]; - if (reg_base_value[regno]) - return reg_base_value[regno]; + if (VARRAY_RTX (reg_base_value, regno)) + return VARRAY_RTX (reg_base_value, regno); } return 0; @@ -931,7 +936,7 @@ record_set (rtx dest, rtx set, void *data ATTRIBUTE_UNUSED) regno = REGNO (dest); - if (regno >= reg_base_value_size) + if (regno >= VARRAY_SIZE (reg_base_value)) abort (); /* If this spans multiple hard registers, then we must indicate that every @@ -1030,21 +1035,20 @@ record_set (rtx dest, rtx set, void *data ATTRIBUTE_UNUSED) void record_base_value (unsigned int regno, rtx val, int invariant) { - if (regno >= reg_base_value_size) - return; - - if (invariant && alias_invariant) + if (invariant && alias_invariant && regno < alias_invariant_size) alias_invariant[regno] = val; + if (regno >= VARRAY_SIZE (reg_base_value)) + VARRAY_GROW (reg_base_value, max_reg_num ()); + if (GET_CODE (val) == REG) { - if (REGNO (val) < reg_base_value_size) - reg_base_value[regno] = reg_base_value[REGNO (val)]; - + VARRAY_RTX (reg_base_value, regno) + = REG_BASE_VALUE (val); return; } - - reg_base_value[regno] = find_base_value (val); + VARRAY_RTX (reg_base_value, regno) + = find_base_value (val); } /* Clear alias info for a register. This is used if an RTL transformation @@ -1682,8 +1686,8 @@ memrefs_conflict_p (int xsize, rtx x, int ysize, rtx y, HOST_WIDE_INT c) unsigned int r_x = REGNO (x), r_y = REGNO (y); rtx i_x, i_y; /* invariant relationships of X and Y */ - i_x = r_x >= reg_base_value_size ? 0 : alias_invariant[r_x]; - i_y = r_y >= reg_base_value_size ? 0 : alias_invariant[r_y]; + i_x = r_x >= alias_invariant_size ? 0 : alias_invariant[r_x]; + i_y = r_y >= alias_invariant_size ? 0 : alias_invariant[r_y]; if (i_x == 0 && i_y == 0) break; @@ -2710,7 +2714,7 @@ memory_modified_in_insn_p (rtx mem, rtx insn) void init_alias_analysis (void) { - int maxreg = max_reg_num (); + unsigned int maxreg = max_reg_num (); int changed, pass; int i; unsigned int ui; @@ -2730,17 +2734,31 @@ init_alias_analysis (void) /* Overallocate reg_base_value to allow some growth during loop optimization. Loop unrolling can create a large number of registers. */ - reg_base_value_size = maxreg * 2; - reg_base_value = ggc_alloc_cleared (reg_base_value_size * sizeof (rtx)); + if (old_reg_base_value) + { + reg_base_value = old_reg_base_value; + /* If varray gets large zeroing cost may get important. */ + if (VARRAY_SIZE (reg_base_value) > 256 + && VARRAY_SIZE (reg_base_value) > 4 * maxreg) + VARRAY_GROW (reg_base_value, maxreg); + VARRAY_CLEAR (reg_base_value); + if (VARRAY_SIZE (reg_base_value) < maxreg) + VARRAY_GROW (reg_base_value, maxreg); + } + else + { + VARRAY_RTX_INIT (reg_base_value, maxreg, "reg_base_value"); + } - new_reg_base_value = xmalloc (reg_base_value_size * sizeof (rtx)); - reg_seen = xmalloc (reg_base_value_size); + new_reg_base_value = xmalloc (maxreg * sizeof (rtx)); + reg_seen = xmalloc (maxreg); if (! reload_completed && flag_old_unroll_loops) { /* ??? Why are we realloc'ing if we're just going to zero it? */ alias_invariant = xrealloc (alias_invariant, - reg_base_value_size * sizeof (rtx)); - memset (alias_invariant, 0, reg_base_value_size * sizeof (rtx)); + maxreg * sizeof (rtx)); + memset (alias_invariant, 0, maxreg * sizeof (rtx)); + alias_invariant_size = maxreg; } /* The basic idea is that each pass through this loop will use the @@ -2777,10 +2795,10 @@ init_alias_analysis (void) copying_arguments = true; /* Wipe the potential alias information clean for this pass. */ - memset (new_reg_base_value, 0, reg_base_value_size * sizeof (rtx)); + memset (new_reg_base_value, 0, maxreg * sizeof (rtx)); /* Wipe the reg_seen array clean. */ - memset (reg_seen, 0, reg_base_value_size); + memset (reg_seen, 0, maxreg); /* Mark all hard registers which may contain an address. The stack, frame and argument pointers may contain an address. @@ -2868,13 +2886,16 @@ init_alias_analysis (void) } /* Now propagate values from new_reg_base_value to reg_base_value. */ - for (ui = 0; ui < reg_base_value_size; ui++) + if (maxreg != (unsigned int) max_reg_num()) + abort (); + for (ui = 0; ui < maxreg; ui++) { if (new_reg_base_value[ui] - && new_reg_base_value[ui] != reg_base_value[ui] - && ! rtx_equal_p (new_reg_base_value[ui], reg_base_value[ui])) + && new_reg_base_value[ui] != VARRAY_RTX (reg_base_value, ui) + && ! rtx_equal_p (new_reg_base_value[ui], + VARRAY_RTX (reg_base_value, ui))) { - reg_base_value[ui] = new_reg_base_value[ui]; + VARRAY_RTX (reg_base_value, ui) = new_reg_base_value[ui]; changed = 1; } } @@ -2882,7 +2903,7 @@ init_alias_analysis (void) while (changed && ++pass < MAX_ALIAS_LOOP_PASSES); /* Fill in the remaining entries. */ - for (i = FIRST_PSEUDO_REGISTER; i < maxreg; i++) + for (i = FIRST_PSEUDO_REGISTER; i < (int)maxreg; i++) if (reg_known_value[i] == 0) reg_known_value[i] = regno_reg_rtx[i]; @@ -2901,16 +2922,17 @@ init_alias_analysis (void) { changed = 0; pass++; - for (ui = 0; ui < reg_base_value_size; ui++) + for (ui = 0; ui < maxreg; ui++) { - rtx base = reg_base_value[ui]; + rtx base = VARRAY_RTX (reg_base_value, ui); if (base && GET_CODE (base) == REG) { unsigned int base_regno = REGNO (base); if (base_regno == ui) /* register set from itself */ - reg_base_value[ui] = 0; + VARRAY_RTX (reg_base_value, ui) = 0; else - reg_base_value[ui] = reg_base_value[base_regno]; + VARRAY_RTX (reg_base_value, ui) + = VARRAY_RTX (reg_base_value, base_regno); changed = 1; } } @@ -2928,17 +2950,17 @@ init_alias_analysis (void) void end_alias_analysis (void) { + old_reg_base_value = reg_base_value; free (reg_known_value + FIRST_PSEUDO_REGISTER); reg_known_value = 0; reg_known_value_size = 0; free (reg_known_equiv_p + FIRST_PSEUDO_REGISTER); reg_known_equiv_p = 0; - reg_base_value = 0; - reg_base_value_size = 0; if (alias_invariant) { free (alias_invariant); alias_invariant = 0; + alias_invariant_size = 0; } } |