From ff49a9ba7b528078691a9f4e811bcdd4e9f99cdd Mon Sep 17 00:00:00 2001 From: Oleg Endo Date: Wed, 17 Dec 2014 22:52:21 +0000 Subject: [PATCH] re PR target/51244 ([SH] Inefficient conditional branch and code around T bit) gcc/ PR target/51244 * config/sh/sh_treg_combine.cc (sh_treg_combine::try_optimize_cbranch): Combine ccreg inversion and cbranch into inverted cbranch. From-SVN: r218847 --- gcc/ChangeLog | 6 ++++++ gcc/config/sh/sh_treg_combine.cc | 23 ++++++++++++++++++++++- 2 files changed, 28 insertions(+), 1 deletion(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 87940a24a4e..00b37280adc 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,9 @@ +2014-12-17 Oleg Endo + + PR target/51244 + * config/sh/sh_treg_combine.cc (sh_treg_combine::try_optimize_cbranch): + Combine ccreg inversion and cbranch into inverted cbranch. + 2014-12-17 Vladimir Makarov * lra-constraints.c (process_alt_operands): Remove non diff --git a/gcc/config/sh/sh_treg_combine.cc b/gcc/config/sh/sh_treg_combine.cc index 68c7fc1cc6d..62392d81f1b 100644 --- a/gcc/config/sh/sh_treg_combine.cc +++ b/gcc/config/sh/sh_treg_combine.cc @@ -1339,9 +1339,17 @@ sh_treg_combine::try_optimize_cbranch (rtx_insn *insn) // for now we limit the search to the current basic block. trace.setcc = find_set_of_reg_bb (m_ccreg, prev_nonnote_insn_bb (insn)); - if (!is_cmp_eq_zero (trace.setcc.set_src ())) + if (trace.setcc.set_src () == NULL_RTX) log_return_void ("could not find set of ccreg in current BB\n"); + if (!is_cmp_eq_zero (trace.setcc.set_src ()) + && !is_inverted_ccreg (trace.setcc.set_src ())) + { + log_msg ("unsupported set of ccreg in current BB: "); + log_rtx (trace.setcc.set_src ()); + log_return_void ("\n"); + } + rtx trace_reg = XEXP (trace.setcc.set_src (), 0); log_msg ("set of ccreg:\n"); @@ -1358,6 +1366,19 @@ sh_treg_combine::try_optimize_cbranch (rtx_insn *insn) log_return_void ("\nbecause it's volatile\n"); } + // If the ccreg is inverted before cbranch try inverting the branch + // condition. + if (is_inverted_ccreg (trace.setcc.set_src ())) + { + if (!trace.can_invert_condition ()) + log_return_void ("branch condition can't be inverted - aborting\n"); + + if (try_invert_branch_condition (trace)) + delete_insn (trace.setcc.insn); + + return; + } + // Now that we have an insn which tests some reg and sets the condition // reg before the conditional branch, try to figure out how that tested // reg was formed, i.e. find all the insns that set the tested reg in -- 2.30.2