diff options
author | Richard Sandiford <richard.sandiford@linaro.org> | 2017-11-19 14:46:21 +0000 |
---|---|---|
committer | Richard Sandiford <richard.sandiford@linaro.org> | 2017-11-20 15:09:41 +0000 |
commit | 44e10175b6664f9174334186aa25c0c22f125990 (patch) | |
tree | 8e2c2286a3330edb4e204d8f522eec30eebe02cb | |
parent | 84886b4ebd1e9640f10fe23f1e5862cf9440678a (diff) | |
download | gcc-44e10175b6664f9174334186aa25c0c22f125990.tar.gz |
:: Fix gcc.c-torture/execute/960419-2.c
-rw-r--r-- | gcc/cselib.c | 39 |
1 files changed, 11 insertions, 28 deletions
diff --git a/gcc/cselib.c b/gcc/cselib.c index 9c8f206c909..c491bded100 100644 --- a/gcc/cselib.c +++ b/gcc/cselib.c @@ -1440,15 +1440,8 @@ expand_loc (struct elt_loc_list *p, struct expand_value_data *evd, for (; p; p = p->next) { - /* Return these right away to avoid returning stack pointer based - expressions for frame pointer and vice versa, which is something - that would confuse DSE. See the comment in cselib_expand_value_rtx_1 - for more details. */ if (REG_P (p->loc) - && (REGNO (p->loc) == STACK_POINTER_REGNUM - || REGNO (p->loc) == FRAME_POINTER_REGNUM - || REGNO (p->loc) == HARD_FRAME_POINTER_REGNUM - || REGNO (p->loc) == cfa_base_preserved_regno)) + && REGNO (p->loc) == cfa_base_preserved_regno) return p->loc; /* Avoid infinite recursion trying to expand a reg into a the same reg. */ @@ -1614,26 +1607,7 @@ cselib_expand_value_rtx_1 (rtx orig, struct expand_value_data *evd, rtx result; unsigned regno = REGNO (orig); - /* The only thing that we are not willing to do (this - is requirement of dse and if others potential uses - need this function we should add a parm to control - it) is that we will not substitute the - STACK_POINTER_REGNUM, FRAME_POINTER or the - HARD_FRAME_POINTER. - - These expansions confuses the code that notices that - stores into the frame go dead at the end of the - function and that the frame is not effected by calls - to subroutines. If you allow the - STACK_POINTER_REGNUM substitution, then dse will - think that parameter pushing also goes dead which is - wrong. If you allow the FRAME_POINTER or the - HARD_FRAME_POINTER then you lose the opportunity to - make the frame assumptions. */ - if (regno == STACK_POINTER_REGNUM - || regno == FRAME_POINTER_REGNUM - || regno == HARD_FRAME_POINTER_REGNUM - || regno == cfa_base_preserved_regno) + if (regno == cfa_base_preserved_regno) return orig; bitmap_set_bit (evd->regs_active, regno); @@ -2389,6 +2363,15 @@ cselib_record_set (rtx dest, cselib_val *src_elt, cselib_val *dest_addr_elt) if (REG_P (dest)) { + /* Do not record equivalences for the frame pointer, since that is + ultimately set from the stack pointer. We need to maintain + the invariant (relied on by alias.c) that references to a given + region of the stack consistently use the frame pointer or + consistently use the stack pointer; we cannot mix the two. */ + if (dest == hard_frame_pointer_rtx + || dest == frame_pointer_rtx) + return; + unsigned int dreg = REGNO (dest); if (dreg < FIRST_PSEUDO_REGISTER) { |