summaryrefslogtreecommitdiff
path: root/gcc/simplify-rtx.c
diff options
context:
space:
mode:
authorrth <rth@138bc75d-0d04-0410-961f-82ee72b054a4>2016-03-02 21:09:54 +0000
committerrth <rth@138bc75d-0d04-0410-961f-82ee72b054a4>2016-03-02 21:09:54 +0000
commit4fa2ff1ed3dc92d609a1b8d78f34a06b9eec250c (patch)
treebaae125ee96286848093048fcb31ae88608f9fe0 /gcc/simplify-rtx.c
parentdfb6d13960428024e961ec9c8dea91ec0e317fdd (diff)
downloadgcc-4fa2ff1ed3dc92d609a1b8d78f34a06b9eec250c.tar.gz
PR rtl-opt/67145
* simplify-rtx.c (simplify_plus_minus): Allow reassoc without simplification when all args are positive non-fixed registers. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@233916 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/simplify-rtx.c')
-rw-r--r--gcc/simplify-rtx.c22
1 files changed, 20 insertions, 2 deletions
diff --git a/gcc/simplify-rtx.c b/gcc/simplify-rtx.c
index 450fa8b0320..e1a0319c26f 100644
--- a/gcc/simplify-rtx.c
+++ b/gcc/simplify-rtx.c
@@ -4421,9 +4421,26 @@ simplify_plus_minus (enum rtx_code code, machine_mode mode, rtx op0,
n_ops = i;
}
- /* If nothing changed, fail. */
+ /* If nothing changed, check that rematerialization of rtl instructions
+ is still required. */
if (!canonicalized)
- return NULL_RTX;
+ {
+ /* Perform rematerialization if only all operands are registers and
+ all operations are PLUS. */
+ /* ??? Also disallow (non-global, non-frame) fixed registers to work
+ around rs6000 and how it uses the CA register. See PR67145. */
+ for (i = 0; i < n_ops; i++)
+ if (ops[i].neg
+ || !REG_P (ops[i].op)
+ || (REGNO (ops[i].op) < FIRST_PSEUDO_REGISTER
+ && fixed_regs[REGNO (ops[i].op)]
+ && !global_regs[REGNO (ops[i].op)]
+ && ops[i].op != frame_pointer_rtx
+ && ops[i].op != arg_pointer_rtx
+ && ops[i].op != stack_pointer_rtx))
+ return NULL_RTX;
+ goto gen_result;
+ }
/* Create (minus -C X) instead of (neg (const (plus X C))). */
if (n_ops == 2
@@ -4465,6 +4482,7 @@ simplify_plus_minus (enum rtx_code code, machine_mode mode, rtx op0,
}
/* Now make the result by performing the requested operations. */
+ gen_result:
result = ops[0].op;
for (i = 1; i < n_ops; i++)
result = gen_rtx_fmt_ee (ops[i].neg ? MINUS : PLUS,