diff options
Diffstat (limited to 'gcc/alias.c')
-rw-r--r-- | gcc/alias.c | 18 |
1 files changed, 17 insertions, 1 deletions
diff --git a/gcc/alias.c b/gcc/alias.c index 4c7965d..5fa15cb 100644 --- a/gcc/alias.c +++ b/gcc/alias.c @@ -3191,12 +3191,21 @@ init_alias_target (void) && targetm.hard_regno_mode_ok (i, Pmode)) static_reg_base_value[i] = arg_base_value; + /* RTL code is required to be consistent about whether it uses the + stack pointer, the frame pointer or the argument pointer to + access a given area of the frame. We can therefore use the + base address to distinguish between the different areas. */ static_reg_base_value[STACK_POINTER_REGNUM] = unique_base_value (UNIQUE_BASE_VALUE_SP); static_reg_base_value[ARG_POINTER_REGNUM] = unique_base_value (UNIQUE_BASE_VALUE_ARGP); static_reg_base_value[FRAME_POINTER_REGNUM] = unique_base_value (UNIQUE_BASE_VALUE_FP); + + /* The above rules extend post-reload, with eliminations applying + consistently to each of the three pointers. Cope with cases in + which the frame pointer is eliminated to the hard frame pointer + rather than the stack pointer. */ if (!HARD_FRAME_POINTER_IS_FRAME_POINTER) static_reg_base_value[HARD_FRAME_POINTER_REGNUM] = unique_base_value (UNIQUE_BASE_VALUE_HFP); @@ -3329,7 +3338,14 @@ init_alias_analysis (void) /* Initialize the alias information for this pass. */ for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) - if (static_reg_base_value[i]) + if (static_reg_base_value[i] + /* Don't treat the hard frame pointer as special if we + eliminated the frame pointer to the stack pointer instead. */ + && !(i == HARD_FRAME_POINTER_REGNUM + && reload_completed + && !frame_pointer_needed + && targetm.can_eliminate (FRAME_POINTER_REGNUM, + STACK_POINTER_REGNUM))) { new_reg_base_value[i] = static_reg_base_value[i]; bitmap_set_bit (reg_seen, i); |