auto_vec<tree> vect_defs;
auto_vec<gimple *> phis;
int vec_num;
- tree def0, def1, tem, op0, op1 = NULL_TREE;
+ tree def0, def1, tem, op1 = NULL_TREE;
bool first_p = true;
tree cr_index_scalar_type = NULL_TREE, cr_index_vector_type = NULL_TREE;
tree cond_reduc_val = NULL_TREE, const_cond_cmp = NULL_TREE;
/* Handle uses. */
if (j == 0)
{
- op0 = ops[!reduc_index];
- if (op_type == ternary_op)
- {
- if (reduc_index == 0)
- op1 = ops[2];
- else
- op1 = ops[1];
- }
+ if (slp_node)
+ {
+ /* Get vec defs for all the operands except the reduction index,
+ ensuring the ordering of the ops in the vector is kept. */
+ auto_vec<tree, 3> slp_ops;
+ auto_vec<vec<tree>, 3> vec_defs;
- if (slp_node)
- vect_get_vec_defs (op0, op1, stmt, &vec_oprnds0, &vec_oprnds1,
- slp_node, -1);
+ slp_ops.quick_push ((reduc_index == 0) ? NULL : ops[0]);
+ slp_ops.quick_push ((reduc_index == 1) ? NULL : ops[1]);
+ if (op_type == ternary_op)
+ slp_ops.quick_push ((reduc_index == 2) ? NULL : ops[2]);
+
+ vect_get_slp_defs (slp_ops, slp_node, &vec_defs, -1);
+
+ vec_oprnds0.safe_splice (vec_defs[(reduc_index == 0) ? 1 : 0]);
+ if (op_type == ternary_op)
+ vec_oprnds1.safe_splice (vec_defs[(reduc_index == 2) ? 1 : 2]);
+ }
else
- {
+ {
loop_vec_def0 = vect_get_vec_def_for_operand (ops[!reduc_index],
stmt);
vec_oprnds0.quick_push (loop_vec_def0);
if (op_type == ternary_op)
{
+ op1 = (reduc_index == 0) ? ops[2] : ops[1];
loop_vec_def1 = vect_get_vec_def_for_operand (op1, stmt);
vec_oprnds1.quick_push (loop_vec_def1);
}
- }
+ }
}
else
{
{
gimple *first_stmt;
int number_of_vects = 0, i;
- unsigned int child_index = 0;
HOST_WIDE_INT lhs_size_unit, rhs_size_unit;
slp_tree child = NULL;
vec<tree> vec_defs;
tree oprnd;
- bool vectorized_defs;
+ bool first_iteration = true;
first_stmt = SLP_TREE_SCALAR_STMTS (slp_node)[0];
FOR_EACH_VEC_ELT (ops, i, oprnd)
{
+ bool vectorized_defs = false;
+
+ if (oprnd == NULL)
+ {
+ vec_defs = vNULL;
+ vec_defs.create (0);
+ vec_oprnds->quick_push (vec_defs);
+ continue;
+ }
+
/* For each operand we check if it has vectorized definitions in a child
node or we need to create them (for invariants and constants). We
check if the LHS of the first stmt of the next child matches OPRND.
If it does, we found the correct child. Otherwise, we call
- vect_get_constant_vectors (), and not advance CHILD_INDEX in order
- to check this child node for the next operand. */
- vectorized_defs = false;
- if (SLP_TREE_CHILDREN (slp_node).length () > child_index)
+ vect_get_constant_vectors (). */
+ for (unsigned int child_index = 0;
+ child_index < SLP_TREE_CHILDREN (slp_node).length (); child_index++)
{
child = SLP_TREE_CHILDREN (slp_node)[child_index];
statements. */
number_of_vects = SLP_TREE_NUMBER_OF_VEC_STMTS (child);
vectorized_defs = true;
- child_index++;
+ break;
}
}
- else
- child_index++;
}
- if (!vectorized_defs)
- {
- if (i == 0)
- {
- number_of_vects = SLP_TREE_NUMBER_OF_VEC_STMTS (slp_node);
- /* Number of vector stmts was calculated according to LHS in
- vect_schedule_slp_instance (), fix it by replacing LHS with
- RHS, if necessary. See vect_get_smallest_scalar_type () for
- details. */
- vect_get_smallest_scalar_type (first_stmt, &lhs_size_unit,
- &rhs_size_unit);
- if (rhs_size_unit != lhs_size_unit)
- {
- number_of_vects *= rhs_size_unit;
- number_of_vects /= lhs_size_unit;
- }
- }
+ if (!vectorized_defs && first_iteration)
+ {
+ number_of_vects = SLP_TREE_NUMBER_OF_VEC_STMTS (slp_node);
+ /* Number of vector stmts was calculated according to LHS in
+ vect_schedule_slp_instance (), fix it by replacing LHS with
+ RHS, if necessary. See vect_get_smallest_scalar_type () for
+ details. */
+ vect_get_smallest_scalar_type (first_stmt, &lhs_size_unit,
+ &rhs_size_unit);
+ if (rhs_size_unit != lhs_size_unit)
+ {
+ number_of_vects *= rhs_size_unit;
+ number_of_vects /= lhs_size_unit;
+ }
}
/* Allocate memory for vectorized defs. */
/* For reductions, we only need initial values. */
if (reduc_index != -1)
return;
+
+ first_iteration = false;
}
}