From 2ee05f1e9be5f02d4c874262d27e1eff96a301f0 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Wed, 1 Jul 2015 13:18:49 +0000 Subject: [PATCH] fold-const.c (fold_comparison): Move X - Y CMP 0 -> X CMP Y... 2015-07-01 Richard Biener * fold-const.c (fold_comparison): Move X - Y CMP 0 -> X CMP Y, X * C1 CMP 0 -> X CMP 0, X CMP X, ~X CMP ~Y -> Y CMP X and ~X CMP C -> X CMP' ~C to ... * match.pd: ... patterns here. From-SVN: r225249 --- gcc/ChangeLog | 7 ++++ gcc/fold-const.c | 105 ----------------------------------------------- gcc/match.pd | 63 ++++++++++++++++++++++++++++ 3 files changed, 70 insertions(+), 105 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index a70facd154b..f53f3786b57 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2015-07-01 Richard Biener + + * fold-const.c (fold_comparison): Move X - Y CMP 0 -> X CMP Y, + X * C1 CMP 0 -> X CMP 0, X CMP X, ~X CMP ~Y -> Y CMP X and + ~X CMP C -> X CMP' ~C to ... + * match.pd: ... patterns here. + 2015-07-01 Nick Clifton * config/msp430/msp430.md (zero_extendhipsi2): Use MOVX.A to store diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 5da6ed3e5d3..b5b0b71741d 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -8783,23 +8783,6 @@ fold_comparison (location_t loc, enum tree_code code, tree type, } } - /* Transform comparisons of the form X - Y CMP 0 to X CMP Y. */ - if (TREE_CODE (arg0) == MINUS_EXPR - && equality_code - && integer_zerop (arg1)) - { - /* ??? The transformation is valid for the other operators if overflow - is undefined for the type, but performing it here badly interacts - with the transformation in fold_cond_expr_with_comparison which - attempts to synthetize ABS_EXPR. */ - if (!equality_code) - fold_overflow_warning ("assuming signed overflow does not occur " - "when changing X - Y cmp 0 to X cmp Y", - WARN_STRICT_OVERFLOW_COMPARISON); - return fold_build2_loc (loc, code, type, TREE_OPERAND (arg0, 0), - TREE_OPERAND (arg0, 1)); - } - /* For comparisons of pointers we can decompose it to a compile time comparison of the base objects and the offsets into the object. This requires at least one operand being an ADDR_EXPR or a @@ -9088,38 +9071,6 @@ fold_comparison (location_t loc, enum tree_code code, tree type, } } - /* Transform comparisons of the form X * C1 CMP 0 to X CMP 0 in the - signed arithmetic case. That form is created by the compiler - often enough for folding it to be of value. One example is in - computing loop trip counts after Operator Strength Reduction. */ - if (ANY_INTEGRAL_TYPE_P (TREE_TYPE (arg0)) - && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (arg0)) - && TREE_CODE (arg0) == MULT_EXPR - && (TREE_CODE (TREE_OPERAND (arg0, 1)) == INTEGER_CST - && !TREE_OVERFLOW (TREE_OPERAND (arg0, 1))) - && integer_zerop (arg1)) - { - tree const1 = TREE_OPERAND (arg0, 1); - tree const2 = arg1; /* zero */ - tree variable1 = TREE_OPERAND (arg0, 0); - enum tree_code cmp_code = code; - - /* Handle unfolded multiplication by zero. */ - if (integer_zerop (const1)) - return fold_build2_loc (loc, cmp_code, type, const1, const2); - - fold_overflow_warning (("assuming signed overflow does not occur when " - "eliminating multiplication in comparison " - "with zero"), - WARN_STRICT_OVERFLOW_COMPARISON); - - /* If const1 is negative we swap the sense of the comparison. */ - if (tree_int_cst_sgn (const1) < 0) - cmp_code = swap_tree_comparison (cmp_code); - - return fold_build2_loc (loc, cmp_code, type, variable1, const2); - } - tem = maybe_canonicalize_comparison (loc, code, type, arg0, arg1); if (tem) return tem; @@ -9241,40 +9192,6 @@ fold_comparison (location_t loc, enum tree_code code, tree type, return tem; } - /* Simplify comparison of something with itself. (For IEEE - floating-point, we can only do some of these simplifications.) */ - if (operand_equal_p (arg0, arg1, 0)) - { - switch (code) - { - case EQ_EXPR: - if (! FLOAT_TYPE_P (TREE_TYPE (arg0)) - || ! HONOR_NANS (arg0)) - return constant_boolean_node (1, type); - break; - - case GE_EXPR: - case LE_EXPR: - if (! FLOAT_TYPE_P (TREE_TYPE (arg0)) - || ! HONOR_NANS (arg0)) - return constant_boolean_node (1, type); - return fold_build2_loc (loc, EQ_EXPR, type, arg0, arg1); - - case NE_EXPR: - /* For NE, we can only do this simplification if integer - or we don't honor IEEE floating point NaNs. */ - if (FLOAT_TYPE_P (TREE_TYPE (arg0)) - && HONOR_NANS (arg0)) - break; - /* ... fall through ... */ - case GT_EXPR: - case LT_EXPR: - return constant_boolean_node (0, type); - default: - gcc_unreachable (); - } - } - /* If we are comparing an expression that just has comparisons of two integer values, arithmetic expressions of those comparisons, and constants, we can simplify it. There are only three cases @@ -9392,28 +9309,6 @@ fold_comparison (location_t loc, enum tree_code code, tree type, return tem; } - /* Fold ~X op ~Y as Y op X. */ - if (TREE_CODE (arg0) == BIT_NOT_EXPR - && TREE_CODE (arg1) == BIT_NOT_EXPR) - { - tree cmp_type = TREE_TYPE (TREE_OPERAND (arg0, 0)); - return fold_build2_loc (loc, code, type, - fold_convert_loc (loc, cmp_type, - TREE_OPERAND (arg1, 0)), - TREE_OPERAND (arg0, 0)); - } - - /* Fold ~X op C as X op' ~C, where op' is the swapped comparison. */ - if (TREE_CODE (arg0) == BIT_NOT_EXPR - && (TREE_CODE (arg1) == INTEGER_CST || TREE_CODE (arg1) == VECTOR_CST)) - { - tree cmp_type = TREE_TYPE (TREE_OPERAND (arg0, 0)); - return fold_build2_loc (loc, swap_tree_comparison (code), type, - TREE_OPERAND (arg0, 0), - fold_build1_loc (loc, BIT_NOT_EXPR, cmp_type, - fold_convert_loc (loc, cmp_type, arg1))); - } - return NULL_TREE; } diff --git a/gcc/match.pd b/gcc/match.pd index f013adc60f1..6c138390aca 100644 --- a/gcc/match.pd +++ b/gcc/match.pd @@ -1262,6 +1262,7 @@ along with GCC; see the file COPYING3. If not see == TYPE_MODE (TREE_TYPE (TREE_TYPE (@0))))) (plus @3 (view_convert @0)))) + /* Simplifications of comparisons. */ /* We can simplify a logical negation of a comparison to the @@ -1299,6 +1300,68 @@ along with GCC; see the file COPYING3. If not see (if (ic == ncmp) (ncmp @0 @1))))) +/* Transform comparisons of the form X - Y CMP 0 to X CMP Y. + ??? The transformation is valid for the other operators if overflow + is undefined for the type, but performing it here badly interacts + with the transformation in fold_cond_expr_with_comparison which + attempts to synthetize ABS_EXPR. */ +(for cmp (eq ne) + (simplify + (cmp (minus @0 @1) integer_zerop) + (cmp @0 @1))) + +/* Transform comparisons of the form X * C1 CMP 0 to X CMP 0 in the + signed arithmetic case. That form is created by the compiler + often enough for folding it to be of value. One example is in + computing loop trip counts after Operator Strength Reduction. */ +(for cmp (tcc_comparison) + scmp (swapped_tcc_comparison) + (simplify + (cmp (mult @0 INTEGER_CST@1) integer_zerop@2) + /* Handle unfolded multiplication by zero. */ + (if (integer_zerop (@1)) + (cmp @1 @2)) + (if (ANY_INTEGRAL_TYPE_P (TREE_TYPE (@0)) + && TYPE_OVERFLOW_UNDEFINED (TREE_TYPE (@0))) + /* If @1 is negative we swap the sense of the comparison. */ + (if (tree_int_cst_sgn (@1) < 0) + (scmp @0 @2)) + (cmp @0 @2)))) + +/* Simplify comparison of something with itself. For IEEE + floating-point, we can only do some of these simplifications. */ +(simplify + (eq @0 @0) + (if (! FLOAT_TYPE_P (TREE_TYPE (@0)) + || ! HONOR_NANS (TYPE_MODE (TREE_TYPE (@0)))) + { constant_boolean_node (true, type); })) +(for cmp (ge le) + (simplify + (cmp @0 @0) + (eq @0 @0))) +(for cmp (ne gt lt) + (simplify + (cmp @0 @0) + (if (cmp != NE_EXPR + || ! FLOAT_TYPE_P (TREE_TYPE (@0)) + || ! HONOR_NANS (TYPE_MODE (TREE_TYPE (@0)))) + { constant_boolean_node (false, type); }))) + +/* Fold ~X op ~Y as Y op X. */ +(for cmp (tcc_comparison) + (simplify + (cmp (bit_not @0) (bit_not @1)) + (cmp @1 @0))) + +/* Fold ~X op C as X op' ~C, where op' is the swapped comparison. */ +(for cmp (tcc_comparison) + scmp (swapped_tcc_comparison) + (simplify + (cmp (bit_not @0) CONSTANT_CLASS_P@1) + (if (TREE_CODE (@1) == INTEGER_CST || TREE_CODE (@1) == VECTOR_CST) + (scmp @0 (bit_not @1))))) + + /* Unordered tests if either argument is a NaN. */ (simplify (bit_ior (unordered @0 @0) (unordered @1 @1)) -- 2.30.2