aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorAndrew MacLeod <amacleod@redhat.com>2021-11-04 11:07:28 -0400
committerAndrew MacLeod <amacleod@redhat.com>2021-11-04 13:15:36 -0400
commit004afb984beb6efbe25f44a5857b1c27ebc2ec82 (patch)
tree6f9c5a694d125164cad695d5ef02fcd44d551fdb /gcc
parent1ece90ffa9ce63b416296bd662b8117d9b538913 (diff)
downloadgcc-004afb984beb6efbe25f44a5857b1c27ebc2ec82.zip
gcc-004afb984beb6efbe25f44a5857b1c27ebc2ec82.tar.gz
gcc-004afb984beb6efbe25f44a5857b1c27ebc2ec82.tar.bz2
Treat undefined operands as varying in GORI.
If the LHS is UNDEFINED simply stop calculating. Treat op1 and op2 as VARYING if they are UNDEFINED. PR tree-optimization/103079 gcc/ * gimple-range-gori.cc (gimple_range_calc_op1): Treat undefined as varying. (gimple_range_calc_op2): Ditto. gcc/testsuite/ * gcc.dg/pr103079.c: New.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/gimple-range-gori.cc40
-rw-r--r--gcc/testsuite/gcc.dg/pr103079.c20
2 files changed, 45 insertions, 15 deletions
diff --git a/gcc/gimple-range-gori.cc b/gcc/gimple-range-gori.cc
index 4e45c59..2e58c23 100644
--- a/gcc/gimple-range-gori.cc
+++ b/gcc/gimple-range-gori.cc
@@ -37,16 +37,13 @@ bool
gimple_range_calc_op1 (irange &r, const gimple *stmt, const irange &lhs_range)
{
gcc_checking_assert (gimple_num_ops (stmt) < 3);
-
- // An empty range is viral.
- tree type = TREE_TYPE (gimple_range_operand1 (stmt));
+ // Give up on empty ranges.
if (lhs_range.undefined_p ())
- {
- r.set_undefined ();
- return true;
- }
+ return false;
+
// Unary operations require the type of the first operand in the
// second range position.
+ tree type = TREE_TYPE (gimple_range_operand1 (stmt));
int_range<2> type_range (type);
return gimple_range_handler (stmt)->op1_range (r, type, lhs_range,
type_range);
@@ -61,15 +58,23 @@ bool
gimple_range_calc_op1 (irange &r, const gimple *stmt,
const irange &lhs_range, const irange &op2_range)
{
+ // Give up on empty ranges.
+ if (lhs_range.undefined_p ())
+ return false;
+
// Unary operation are allowed to pass a range in for second operand
// as there are often additional restrictions beyond the type which
// can be imposed. See operator_cast::op1_range().
tree type = TREE_TYPE (gimple_range_operand1 (stmt));
- // An empty range is viral.
- if (op2_range.undefined_p () || lhs_range.undefined_p ())
+ // If op2 is undefined, solve as if it is varying.
+ if (op2_range.undefined_p ())
{
- r.set_undefined ();
- return true;
+ // This is sometimes invoked on single operand stmts.
+ if (gimple_num_ops (stmt) < 3)
+ return false;
+ int_range<2> trange (TREE_TYPE (gimple_range_operand2 (stmt)));
+ return gimple_range_handler (stmt)->op1_range (r, type, lhs_range,
+ trange);
}
return gimple_range_handler (stmt)->op1_range (r, type, lhs_range,
op2_range);
@@ -84,12 +89,17 @@ bool
gimple_range_calc_op2 (irange &r, const gimple *stmt,
const irange &lhs_range, const irange &op1_range)
{
+ // Give up on empty ranges.
+ if (lhs_range.undefined_p ())
+ return false;
+
tree type = TREE_TYPE (gimple_range_operand2 (stmt));
- // An empty range is viral.
- if (op1_range.undefined_p () || lhs_range.undefined_p ())
+ // If op1 is undefined, solve as if it is varying.
+ if (op1_range.undefined_p ())
{
- r.set_undefined ();
- return true;
+ int_range<2> trange (TREE_TYPE (gimple_range_operand1 (stmt)));
+ return gimple_range_handler (stmt)->op2_range (r, type, lhs_range,
+ trange);
}
return gimple_range_handler (stmt)->op2_range (r, type, lhs_range,
op1_range);
diff --git a/gcc/testsuite/gcc.dg/pr103079.c b/gcc/testsuite/gcc.dg/pr103079.c
new file mode 100644
index 0000000..7f6632f
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr103079.c
@@ -0,0 +1,20 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fdump-tree-vrp2" } */
+
+int a, b = -2;
+int main() {
+ int d = 0;
+ int t;
+ if (b)
+ goto t1;
+ if (t) {
+t1:
+ if (!a)
+ d = b;
+ while (d > -1)
+ ;
+ }
+ return 0;
+}
+/* { dg-final { scan-tree-dump "PHI" "vrp2" } } */
+