summaryrefslogtreecommitdiff
path: root/gcc/ifcvt.c
diff options
context:
space:
mode:
authorktkachov <ktkachov@138bc75d-0d04-0410-961f-82ee72b054a4>2015-12-03 13:28:55 +0000
committerktkachov <ktkachov@138bc75d-0d04-0410-961f-82ee72b054a4>2015-12-03 13:28:55 +0000
commit4aa15f9c0742f6f0c24cd154e3a476c37afa960a (patch)
tree32df47c3ed9c329260ff1a9ba2646482cc84c212 /gcc/ifcvt.c
parentddf5be99b675731b34d76f16d4d123e23c594268 (diff)
downloadgcc-4aa15f9c0742f6f0c24cd154e3a476c37afa960a.tar.gz
[RTL-ifcvt] PR rtl-optimization/68624: Clean up logic that checks for clobbering conflicts across basic blocks
PR rtl-optimization/68624 * ifcvt.c (noce_try_cmove_arith): Check clobbers of temp regs in both blocks if they exist and simplify the logic choosing the order to emit them in. * gcc.c-torture/execute/pr68624.c: New test. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@231226 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/ifcvt.c')
-rw-r--r--gcc/ifcvt.c38
1 files changed, 19 insertions, 19 deletions
diff --git a/gcc/ifcvt.c b/gcc/ifcvt.c
index 8ece8734338..d474b3ba493 100644
--- a/gcc/ifcvt.c
+++ b/gcc/ifcvt.c
@@ -2172,10 +2172,6 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
}
}
- /* If insn to set up A clobbers any registers B depends on, try to
- swap insn that sets up A with the one that sets up B. If even
- that doesn't help, punt. */
-
modified_in_a = emit_a != NULL_RTX && modified_in_p (orig_b, emit_a);
if (tmp_b && then_bb)
{
@@ -2190,31 +2186,33 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
}
}
- if (emit_a || modified_in_a)
+
+ modified_in_b = emit_b != NULL_RTX && modified_in_p (orig_a, emit_b);
+ if (tmp_a && else_bb)
{
- modified_in_b = emit_b != NULL_RTX && modified_in_p (orig_a, emit_b);
- if (tmp_b && else_bb)
+ FOR_BB_INSNS (else_bb, tmp_insn)
+ /* Don't check inside insn_b. We will have changed it to emit_b
+ with a destination that doesn't conflict. */
+ if (!(insn_b && tmp_insn == insn_b)
+ && modified_in_p (orig_a, tmp_insn))
{
- FOR_BB_INSNS (else_bb, tmp_insn)
- /* Don't check inside insn_b. We will have changed it to emit_b
- with a destination that doesn't conflict. */
- if (!(insn_b && tmp_insn == insn_b)
- && modified_in_p (orig_a, tmp_insn))
- {
- modified_in_b = true;
- break;
- }
+ modified_in_b = true;
+ break;
}
- if (modified_in_b)
- goto end_seq_and_fail;
+ }
+ /* If insn to set up A clobbers any registers B depends on, try to
+ swap insn that sets up A with the one that sets up B. If even
+ that doesn't help, punt. */
+ if (modified_in_a && !modified_in_b)
+ {
if (!noce_emit_bb (emit_b, else_bb, b_simple))
goto end_seq_and_fail;
if (!noce_emit_bb (emit_a, then_bb, a_simple))
goto end_seq_and_fail;
}
- else
+ else if (!modified_in_a)
{
if (!noce_emit_bb (emit_a, then_bb, a_simple))
goto end_seq_and_fail;
@@ -2222,6 +2220,8 @@ noce_try_cmove_arith (struct noce_if_info *if_info)
if (!noce_emit_bb (emit_b, else_bb, b_simple))
goto end_seq_and_fail;
}
+ else
+ goto end_seq_and_fail;
target = noce_emit_cmove (if_info, x, code, XEXP (if_info->cond, 0),
XEXP (if_info->cond, 1), a, b);