diff options
author | Richard Biener <rguenther@suse.de> | 2018-11-07 15:01:09 +0000 |
---|---|---|
committer | Richard Biener <rguenth@gcc.gnu.org> | 2018-11-07 15:01:09 +0000 |
commit | 5a951baaf1b789281bf62b852d24a4ab8cf3e714 (patch) | |
tree | 0c036e96b195e6e1d15aa5359bf49a3c7372370d /gcc/tree-vect-stmts.c | |
parent | 7d3a67d7b0c01c0370226db7840c9ef6e054b56c (diff) | |
download | gcc-5a951baaf1b789281bf62b852d24a4ab8cf3e714.zip gcc-5a951baaf1b789281bf62b852d24a4ab8cf3e714.tar.gz gcc-5a951baaf1b789281bf62b852d24a4ab8cf3e714.tar.bz2 |
re PR tree-optimization/87914 (gcc fails to vectorize bitreverse code)
2018-11-07 Richard Biener <rguenther@suse.de>
PR tree-optimization/87914
* tree-vect-loop.c (vect_is_simple_reduction): Improve detection
of nested cycles.
(vectorizable_reduction): Handle shifts and rotates by dispatching
to vectorizable_shift.
* tree-vect-stmts.c (vect_get_vec_def_for_operand_1): Handle
in-loop uses of vect_nested_cycle defs. Merge cycle and internal
def cases.
(vectorizable_shift): Export and handle being called as
vect_nested_cycle.
(vect_analyze_stmt): Call vectorizable_shift after
vectorizable_reduction.
* tree-vectorizer.h (vectorizable_shift): Declare.
* lib/target-supports.exp (check_effective_target_vect_var_shift): New.
(check_avx2_available): Likewise.
* g++.dg/vect/pr87914.cc: New testcase.
From-SVN: r265876
Diffstat (limited to 'gcc/tree-vect-stmts.c')
-rw-r--r-- | gcc/tree-vect-stmts.c | 35 |
1 files changed, 15 insertions, 20 deletions
diff --git a/gcc/tree-vect-stmts.c b/gcc/tree-vect-stmts.c index 7127c17..8133149 100644 --- a/gcc/tree-vect-stmts.c +++ b/gcc/tree-vect-stmts.c @@ -1461,6 +1461,16 @@ vect_get_vec_def_for_operand_1 (stmt_vec_info def_stmt_info, /* Code should use vect_get_vec_def_for_operand. */ gcc_unreachable (); + /* Operand is defined by a loop header phi. In case of nested + cycles we also may have uses of the backedge def. */ + case vect_reduction_def: + case vect_double_reduction_def: + case vect_nested_cycle: + case vect_induction_def: + gcc_assert (gimple_code (def_stmt_info->stmt) == GIMPLE_PHI + || dt == vect_nested_cycle); + /* Fallthru. */ + /* operand is defined inside the loop. */ case vect_internal_def: { @@ -1480,23 +1490,6 @@ vect_get_vec_def_for_operand_1 (stmt_vec_info def_stmt_info, return vec_oprnd; } - /* operand is defined by a loop header phi. */ - case vect_reduction_def: - case vect_double_reduction_def: - case vect_nested_cycle: - case vect_induction_def: - { - gcc_assert (gimple_code (def_stmt_info->stmt) == GIMPLE_PHI); - - /* Get the def from the vectorized stmt. */ - vec_stmt_info = STMT_VINFO_VEC_STMT (def_stmt_info); - if (gphi *phi = dyn_cast <gphi *> (vec_stmt_info->stmt)) - vec_oprnd = PHI_RESULT (phi); - else - vec_oprnd = gimple_get_lhs (vec_stmt_info->stmt); - return vec_oprnd; - } - default: gcc_unreachable (); } @@ -5363,7 +5356,7 @@ vect_supportable_shift (enum tree_code code, tree scalar_type) stmt to replace it, put it in VEC_STMT, and insert it at GSI. Return true if STMT_INFO is vectorizable in this way. */ -static bool +bool vectorizable_shift (stmt_vec_info stmt_info, gimple_stmt_iterator *gsi, stmt_vec_info *vec_stmt, slp_tree slp_node, stmt_vector_for_cost *cost_vec) @@ -5401,6 +5394,7 @@ vectorizable_shift (stmt_vec_info stmt_info, gimple_stmt_iterator *gsi, return false; if (STMT_VINFO_DEF_TYPE (stmt_info) != vect_internal_def + && STMT_VINFO_DEF_TYPE (stmt_info) != vect_nested_cycle && ! vec_stmt) return false; @@ -5480,7 +5474,8 @@ vectorizable_shift (stmt_vec_info stmt_info, gimple_stmt_iterator *gsi, shift/rotate amount is a vector, use the vector/vector shift optabs. */ if ((dt[1] == vect_internal_def - || dt[1] == vect_induction_def) + || dt[1] == vect_induction_def + || dt[1] == vect_nested_cycle) && !slp_node) scalar_shift_arg = false; else if (dt[1] == vect_constant_def @@ -9540,7 +9535,6 @@ vect_analyze_stmt (stmt_vec_info stmt_info, bool *need_to_vectorize, || vectorizable_simd_clone_call (stmt_info, NULL, NULL, node, cost_vec) || vectorizable_conversion (stmt_info, NULL, NULL, node, cost_vec) - || vectorizable_shift (stmt_info, NULL, NULL, node, cost_vec) || vectorizable_operation (stmt_info, NULL, NULL, node, cost_vec) || vectorizable_assignment (stmt_info, NULL, NULL, node, cost_vec) || vectorizable_load (stmt_info, NULL, NULL, node, node_instance, @@ -9549,6 +9543,7 @@ vect_analyze_stmt (stmt_vec_info stmt_info, bool *need_to_vectorize, || vectorizable_reduction (stmt_info, NULL, NULL, node, node_instance, cost_vec) || vectorizable_induction (stmt_info, NULL, NULL, node, cost_vec) + || vectorizable_shift (stmt_info, NULL, NULL, node, cost_vec) || vectorizable_condition (stmt_info, NULL, NULL, NULL, 0, node, cost_vec) || vectorizable_comparison (stmt_info, NULL, NULL, NULL, node, |