From 1f00c1b9cda9e377e278314a6e3b50bc45157e22 Mon Sep 17 00:00:00 2001 From: Richard Biener Date: Mon, 10 Nov 2014 08:58:24 +0000 Subject: [PATCH] match.pd: Move rest of the conversion combining patterns from tree-ssa-forwprop.c. 2014-11-10 Richard Biener * match.pd: Move rest of the conversion combining patterns from tree-ssa-forwprop.c. * tree-ssa-forwprop.c (combine_conversions): Remove. (pass_forwprop::execute): Do not call it. From-SVN: r217279 --- gcc/ChangeLog | 7 +++ gcc/match.pd | 21 ++++++- gcc/tree-ssa-forwprop.c | 133 +++------------------------------------- 3 files changed, 35 insertions(+), 126 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 97fc20e6dd0..0e01ec7412a 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2014-11-10 Richard Biener + + * match.pd: Move rest of the conversion combining patterns + from tree-ssa-forwprop.c. + * tree-ssa-forwprop.c (combine_conversions): Remove. + (pass_forwprop::execute): Do not call it. + 2014-11-10 Eric Botcazou * gimple-low.c (lower_function_body): Clear the location of the first diff --git a/gcc/match.pd b/gcc/match.pd index a847e820f6d..04c657608bb 100644 --- a/gcc/match.pd +++ b/gcc/match.pd @@ -411,4 +411,23 @@ along with GCC; see the file COPYING3. If not see && ! (final_ptr && inside_prec != inter_prec) && ! (final_prec != GET_MODE_PRECISION (TYPE_MODE (type)) && TYPE_MODE (type) == TYPE_MODE (inter_type))) - (ocvt @0)))))) + (ocvt @0)) + + /* A truncation to an unsigned type (a zero-extension) should be + canonicalized as bitwise and of a mask. */ + (if (final_int && inter_int && inside_int + && final_prec == inside_prec + && final_prec > inter_prec + && inter_unsignedp) + (convert (bit_and @0 { wide_int_to_tree + (inside_type, + wi::mask (inter_prec, false, + TYPE_PRECISION (inside_type))); }))) + + /* If we are converting an integer to a floating-point that can + represent it exactly and back to an integer, we can skip the + floating-point conversion. */ + (if (inside_int && inter_float && final_int && + (unsigned) significand_size (TYPE_MODE (inter_type)) + >= inside_prec - !inside_unsignedp) + (convert @0)))))) diff --git a/gcc/tree-ssa-forwprop.c b/gcc/tree-ssa-forwprop.c index 2f4998cdb56..358dc4cf43a 100644 --- a/gcc/tree-ssa-forwprop.c +++ b/gcc/tree-ssa-forwprop.c @@ -2345,114 +2345,6 @@ out: return false; } -/* Combine two conversions in a row for the second conversion at *GSI. - Returns 1 if there were any changes made, 2 if cfg-cleanup needs to - run. Else it returns 0. */ - -static int -combine_conversions (gimple_stmt_iterator *gsi) -{ - gimple stmt = gsi_stmt (*gsi); - gimple def_stmt; - tree op0, lhs; - enum tree_code code = gimple_assign_rhs_code (stmt); - enum tree_code code2; - - gcc_checking_assert (CONVERT_EXPR_CODE_P (code) - || code == FLOAT_EXPR - || code == FIX_TRUNC_EXPR); - - lhs = gimple_assign_lhs (stmt); - op0 = gimple_assign_rhs1 (stmt); - if (useless_type_conversion_p (TREE_TYPE (lhs), TREE_TYPE (op0))) - { - gimple_assign_set_rhs_code (stmt, TREE_CODE (op0)); - return 1; - } - - if (TREE_CODE (op0) != SSA_NAME) - return 0; - - def_stmt = SSA_NAME_DEF_STMT (op0); - if (!is_gimple_assign (def_stmt)) - return 0; - - code2 = gimple_assign_rhs_code (def_stmt); - - if (CONVERT_EXPR_CODE_P (code2) || code2 == FLOAT_EXPR) - { - tree defop0 = gimple_assign_rhs1 (def_stmt); - tree type = TREE_TYPE (lhs); - tree inside_type = TREE_TYPE (defop0); - tree inter_type = TREE_TYPE (op0); - int inside_int = INTEGRAL_TYPE_P (inside_type); - unsigned int inside_prec = TYPE_PRECISION (inside_type); - int inside_unsignedp = TYPE_UNSIGNED (inside_type); - int inter_int = INTEGRAL_TYPE_P (inter_type); - int inter_float = FLOAT_TYPE_P (inter_type); - unsigned int inter_prec = TYPE_PRECISION (inter_type); - int inter_unsignedp = TYPE_UNSIGNED (inter_type); - int final_int = INTEGRAL_TYPE_P (type); - unsigned int final_prec = TYPE_PRECISION (type); - - /* Don't propagate ssa names that occur in abnormal phis. */ - if (TREE_CODE (defop0) == SSA_NAME - && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (defop0)) - return 0; - - /* A truncation to an unsigned type should be canonicalized as - bitwise and of a mask. */ - if (final_int && inter_int && inside_int - && final_prec == inside_prec - && final_prec > inter_prec - && inter_unsignedp) - { - tree tem; - tem = fold_build2 (BIT_AND_EXPR, inside_type, - defop0, - wide_int_to_tree - (inside_type, - wi::mask (inter_prec, false, - TYPE_PRECISION (inside_type)))); - if (!useless_type_conversion_p (type, inside_type)) - { - tem = force_gimple_operand_gsi (gsi, tem, true, NULL_TREE, true, - GSI_SAME_STMT); - gimple_assign_set_rhs1 (stmt, tem); - } - else - gimple_assign_set_rhs_from_tree (gsi, tem); - update_stmt (gsi_stmt (*gsi)); - return 1; - } - - /* If we are converting an integer to a floating-point that can - represent it exactly and back to an integer, we can skip the - floating-point conversion. */ - if (inside_int && inter_float && final_int && - (unsigned) significand_size (TYPE_MODE (inter_type)) - >= inside_prec - !inside_unsignedp) - { - if (useless_type_conversion_p (type, inside_type)) - { - gimple_assign_set_rhs1 (stmt, unshare_expr (defop0)); - gimple_assign_set_rhs_code (stmt, TREE_CODE (defop0)); - update_stmt (stmt); - return remove_prop_source_from_use (op0) ? 2 : 1; - } - else - { - gimple_assign_set_rhs1 (stmt, defop0); - gimple_assign_set_rhs_code (stmt, CONVERT_EXPR); - update_stmt (stmt); - return remove_prop_source_from_use (op0) ? 2 : 1; - } - } - } - - return 0; -} - /* Combine an element access with a shuffle. Returns true if there were any changes made, else it returns false. */ @@ -3052,28 +2944,19 @@ pass_forwprop::execute (function *fun) || code == FLOAT_EXPR || code == FIX_TRUNC_EXPR) { - int did_something = combine_conversions (&gsi); - if (did_something == 2) - cfg_changed = true; - /* If we have a narrowing conversion to an integral type that is fed by a BIT_AND_EXPR, we might be able to remove the BIT_AND_EXPR if it merely masks off bits outside the final type (and nothing else. */ - if (! did_something) - { - tree outer_type = TREE_TYPE (gimple_assign_lhs (stmt)); - tree inner_type = TREE_TYPE (gimple_assign_rhs1 (stmt)); - if (TREE_CODE (gimple_assign_rhs1 (stmt)) == SSA_NAME - && INTEGRAL_TYPE_P (outer_type) - && INTEGRAL_TYPE_P (inner_type) - && (TYPE_PRECISION (outer_type) - <= TYPE_PRECISION (inner_type))) - did_something = simplify_conversion_from_bitmask (&gsi); - } - - changed = did_something != 0; + tree outer_type = TREE_TYPE (gimple_assign_lhs (stmt)); + tree inner_type = TREE_TYPE (gimple_assign_rhs1 (stmt)); + if (TREE_CODE (gimple_assign_rhs1 (stmt)) == SSA_NAME + && INTEGRAL_TYPE_P (outer_type) + && INTEGRAL_TYPE_P (inner_type) + && (TYPE_PRECISION (outer_type) + <= TYPE_PRECISION (inner_type))) + changed = simplify_conversion_from_bitmask (&gsi); } else if (code == VEC_PERM_EXPR) { -- 2.30.2