aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYuri Rumyantsev <ysrumyan@gmail.com>2016-01-11 12:07:31 +0000
committerIlya Enkovich <ienkovich@gcc.gnu.org>2016-01-11 12:07:31 +0000
commitca90b1ed9ac7e9aaacb3ef0eb055d2f594d30493 (patch)
treeaff7cf99fbd76cee5e9f06139145d6518bc63045
parentb4934671aed067e0a8c3ac3fcc5871dd27a706ed (diff)
downloadgcc-ca90b1ed9ac7e9aaacb3ef0eb055d2f594d30493.zip
gcc-ca90b1ed9ac7e9aaacb3ef0eb055d2f594d30493.tar.gz
gcc-ca90b1ed9ac7e9aaacb3ef0eb055d2f594d30493.tar.bz2
re PR rtl-optimization/68920 (Undesirable if-conversion for a rarely taken branch)
gcc/ 2016-01-11 Yuri Rumyantsev <ysrumyan@gmail.com> PR rtl-optimization/68920 * config/i386/i386.c (ix86_option_override_internal): Restrict number of conditional moves for RTL if-conversion to 1 for TARGET_ONE_IF_CONV_INSN. * config/i386/i386.h (TARGET_ONE_IF_CONV_INSN): New macros. * config/i386/x86-tune.def (X86_TUNE_ONE_IF_CONV_INSN): New macros. * params.def (PARAM_MAX_RTL_IF_CONVERSION_INSNS) : Introduce new parameter to restirct number of conditional moves for RTL if-conversion. * doc/invoke.texi (max-rtl-if-conversion-insns): Document it. * ifcvt.c (bb_ok_for_noce_convert_multiple_sets): Limit number of conditionl moves. gcc/testsuite/ 2016-01-11 Yuri Rumyantsev <ysrumyan@gmail.com> PR rtl-optimization/68920 * gcc.dg/ifcvt-4.c: Add "--param max-rtl-if-conversion-insns=3" option for ix86 targets. * gcc.dg/ifcvt-5.c: New test. From-SVN: r232220
-rw-r--r--gcc/ChangeLog15
-rw-r--r--gcc/config/i386/i386.c7
-rw-r--r--gcc/config/i386/i386.h2
-rw-r--r--gcc/config/i386/x86-tune.def5
-rw-r--r--gcc/doc/invoke.texi8
-rw-r--r--gcc/ifcvt.c9
-rw-r--r--gcc/params.def6
-rw-r--r--gcc/testsuite/ChangeLog7
-rw-r--r--gcc/testsuite/gcc.dg/ifcvt-4.c2
-rw-r--r--gcc/testsuite/gcc.dg/ifcvt-5.c17
10 files changed, 73 insertions, 5 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 71aac8e..0e7202b 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,18 @@
+2016-01-11 Yuri Rumyantsev <ysrumyan@gmail.com>
+
+ PR rtl-optimization/68920
+ * config/i386/i386.c (ix86_option_override_internal): Restrict number
+ of conditional moves for RTL if-conversion to 1 for
+ TARGET_ONE_IF_CONV_INSN.
+ * config/i386/i386.h (TARGET_ONE_IF_CONV_INSN): New macros.
+ * config/i386/x86-tune.def (X86_TUNE_ONE_IF_CONV_INSN): New macros.
+ * params.def (PARAM_MAX_RTL_IF_CONVERSION_INSNS) : Introduce new
+ parameter to restirct number of conditional moves for
+ RTL if-conversion.
+ * doc/invoke.texi (max-rtl-if-conversion-insns): Document it.
+ * ifcvt.c (bb_ok_for_noce_convert_multiple_sets): Limit number of
+ conditionl moves.
+
2016-01-11 Alexandre Oliva <aoliva@redhat.com>
PR bootstrap/69123
diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
index aac0847..c0b2cce 100644
--- a/gcc/config/i386/i386.c
+++ b/gcc/config/i386/i386.c
@@ -5343,6 +5343,13 @@ ix86_option_override_internal (bool main_args_p,
opts->x_param_values,
opts_set->x_param_values);
+ /* Restrict number of if-converted SET insns to 1. */
+ if (TARGET_ONE_IF_CONV_INSN)
+ maybe_set_param_value (PARAM_MAX_RTL_IF_CONVERSION_INSNS,
+ 1,
+ opts->x_param_values,
+ opts_set->x_param_values);
+
/* Enable sw prefetching at -O3 for CPUS that prefetching is helpful. */
if (opts->x_flag_prefetch_loop_arrays < 0
&& HAVE_prefetch
diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h
index befed85..dcaa011 100644
--- a/gcc/config/i386/i386.h
+++ b/gcc/config/i386/i386.h
@@ -499,6 +499,8 @@ extern unsigned char ix86_tune_features[X86_TUNE_LAST];
ix86_tune_features[X86_TUNE_ADJUST_UNROLL]
#define TARGET_AVOID_FALSE_DEP_FOR_BMI \
ix86_tune_features[X86_TUNE_AVOID_FALSE_DEP_FOR_BMI]
+#define TARGET_ONE_IF_CONV_INSN \
+ ix86_tune_features[X86_TUNE_ONE_IF_CONV_INSN]
/* Feature tests against the various architecture variations. */
enum ix86_arch_indices {
diff --git a/gcc/config/i386/x86-tune.def b/gcc/config/i386/x86-tune.def
index 88ed50a..9d25e51 100644
--- a/gcc/config/i386/x86-tune.def
+++ b/gcc/config/i386/x86-tune.def
@@ -550,3 +550,8 @@ DEF_TUNE (X86_TUNE_PROMOTE_QI_REGS, "promote_qi_regs", 0)
unrolling small loop less important. For, such architectures we adjust
the unroll factor so that the unrolled loop fits the loop buffer. */
DEF_TUNE (X86_TUNE_ADJUST_UNROLL, "adjust_unroll_factor", m_BDVER3 | m_BDVER4)
+
+/* X86_TUNE_ONE_IF_CONV_INSNS: Restrict a number of set insns to be
+ if-converted to one. */
+DEF_TUNE (X86_TUNE_ONE_IF_CONV_INSN, "one_if_conv_insn",
+ m_SILVERMONT | m_KNL | m_INTEL | m_CORE_ALL | m_GENERIC)
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index fc1dedf..77115a7 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -10365,6 +10365,14 @@ In each case, the @var{value} is an integer. The allowable choices for
When branch is predicted to be taken with probability lower than this threshold
(in percent), then it is considered well predictable. The default is 10.
+@item max-rtl-if-conversion-insns
+RTL if-conversion tries to remove conditional branches around a block and
+replace them with conditionally executed instructions. This parameter
+gives the maximum number of instructions in a block which should be
+considered for if-conversion. The default is 10, though the compiler will
+also use other heuristics to decide whether if-conversion is likely to be
+profitable.
+
@item max-crossjump-edges
The maximum number of incoming edges to consider for cross-jumping.
The algorithm used by @option{-fcrossjumping} is @math{O(N^2)} in
diff --git a/gcc/ifcvt.c b/gcc/ifcvt.c
index 67b10cf..723ea3e 100644
--- a/gcc/ifcvt.c
+++ b/gcc/ifcvt.c
@@ -44,6 +44,7 @@
#include "shrink-wrap.h"
#include "rtl-iter.h"
#include "ifcvt.h"
+#include "params.h"
#ifndef MAX_CONDITIONAL_EXECUTE
#define MAX_CONDITIONAL_EXECUTE \
@@ -3242,6 +3243,8 @@ bb_ok_for_noce_convert_multiple_sets (basic_block test_bb,
{
rtx_insn *insn;
unsigned count = 0;
+ unsigned param = PARAM_VALUE (PARAM_MAX_RTL_IF_CONVERSION_INSNS);
+ unsigned limit = MIN (ii->branch_cost, param);
FOR_BB_INSNS (test_bb, insn)
{
@@ -3277,8 +3280,8 @@ bb_ok_for_noce_convert_multiple_sets (basic_block test_bb,
/* FORNOW: Our cost model is a count of the number of instructions we
would if-convert. This is suboptimal, and should be improved as part
of a wider rework of branch_cost. */
- if (count > ii->branch_cost)
- return FALSE;
+ if (count > limit)
+ return false;
return count > 0;
}
@@ -3823,7 +3826,6 @@ cond_move_process_if_block (struct noce_if_info *if_info)
}
num_updated_if_blocks++;
-
success_p = TRUE;
done:
@@ -4810,7 +4812,6 @@ find_if_case_1 (basic_block test_bb, edge then_edge, edge else_edge)
num_true_changes++;
num_updated_if_blocks++;
-
return TRUE;
}
diff --git a/gcc/params.def b/gcc/params.def
index 472b20c..308844a 100644
--- a/gcc/params.def
+++ b/gcc/params.def
@@ -1177,6 +1177,12 @@ DEFPARAM (PARAM_MAX_SSA_NAME_QUERY_DEPTH,
"Maximum recursion depth allowed when querying a property of an"
" SSA name.",
2, 1, 0)
+
+DEFPARAM (PARAM_MAX_RTL_IF_CONVERSION_INSNS,
+ "max-rtl-if-conversion-insns",
+ "Maximum number of insns in a basic block to consider for RTL "
+ "if-conversion.",
+ 10, 0, 99)
/*
Local variables:
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 7095b45..c1ae6ef 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,10 @@
+2016-01-11 Yuri Rumyantsev <ysrumyan@gmail.com>
+
+ PR rtl-optimization/68920
+ * gcc.dg/ifcvt-4.c: Add "--param max-rtl-if-conversion-insns=3" option
+ for ix86 targets.
+ * gcc.dg/ifcvt-5.c: New test.
+
2016-01-11 Alexandre Oliva <aoliva@redhat.com>
PR bootstrap/69123
diff --git a/gcc/testsuite/gcc.dg/ifcvt-4.c b/gcc/testsuite/gcc.dg/ifcvt-4.c
index e1c81fb..9a91a19 100644
--- a/gcc/testsuite/gcc.dg/ifcvt-4.c
+++ b/gcc/testsuite/gcc.dg/ifcvt-4.c
@@ -1,4 +1,4 @@
-/* { dg-options "-fdump-rtl-ce1 -O2" } */
+/* { dg-options "-fdump-rtl-ce1 -O2 --param max-rtl-if-conversion-insns=3" } */
/* { dg-skip-if "Multiple set if-conversion not guaranteed on all subtargets" { "arm*-*-* powerpc64le*-*-*" } {"*"} { "" } } */
int
diff --git a/gcc/testsuite/gcc.dg/ifcvt-5.c b/gcc/testsuite/gcc.dg/ifcvt-5.c
new file mode 100644
index 0000000..0b73e54
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/ifcvt-5.c
@@ -0,0 +1,17 @@
+/* Check that multi-insn if-conversion is not done if the override
+ parameter would not allow it. */
+
+/* { dg-options "-fdump-rtl-ce1 -O2 --param max-rtl-if-conversion-insns=1" } */
+int
+foo (int x, int y, int a)
+{
+ int i = x;
+ int j = y;
+ if (x > y)
+ {
+ i = a;
+ j = i;
+ }
+ return i * j;
+}
+/* { dg-final { scan-rtl-dump "0 true changes made" "ce1" } } */