diff options
author | Jeff Law <law@gcc.gnu.org> | 2013-01-18 00:54:47 -0700 |
---|---|---|
committer | Jeff Law <law@gcc.gnu.org> | 2013-01-18 00:54:47 -0700 |
commit | c664546f0e9d12d8f3249b67982e0b192e112bef (patch) | |
tree | eeafc6e254984b4679789b0594673c47e2dc2585 /gcc/regrename.c | |
parent | 1f8b0400aa92a00ab1fd022d9e3eb3e0c7526f38 (diff) |
re PR rtl-optimization/52573 (regrename creates overlapping register allocations for output operands)
PR rtl-optimization/52573
* regrename.c (build_def_use): Ignore REG_DEAD notes if there is
a REG_UNUSED for the same register.
* gcc.dg/pr52573.c: New test.
From-SVN: r195288
Diffstat (limited to 'gcc/regrename.c')
-rw-r--r-- | gcc/regrename.c | 11 |
1 files changed, 9 insertions, 2 deletions
diff --git a/gcc/regrename.c b/gcc/regrename.c index df3d341db51..20e2ae9f792 100644 --- a/gcc/regrename.c +++ b/gcc/regrename.c @@ -1710,9 +1710,16 @@ build_def_use (basic_block bb) scan_rtx (insn, &XEXP (note, 0), ALL_REGS, mark_read, OP_INOUT); - /* Step 4: Close chains for registers that die here. */ + /* Step 4: Close chains for registers that die here, unless + the register is mentioned in a REG_UNUSED note. In that + case we keep the chain open until step #7 below to ensure + it conflicts with other output operands of this insn. + See PR 52573. Arguably the insn should not have both + notes; it has proven difficult to fix that without + other undesirable side effects. */ for (note = REG_NOTES (insn); note; note = XEXP (note, 1)) - if (REG_NOTE_KIND (note) == REG_DEAD) + if (REG_NOTE_KIND (note) == REG_DEAD + && !find_regno_note (insn, REG_UNUSED, REGNO (XEXP (note, 0)))) { remove_from_hard_reg_set (&live_hard_regs, GET_MODE (XEXP (note, 0)), |