diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 98c6462794d..98feb2c2314 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,13 @@ +2013-04-10 Richard Biener + + * tree-vectorizer.h (struct _slp_oprnd_info): Remove + first_const_oprnd field, rename first_def_type to first_op_type. + * tree-vect-slp.c (vect_create_oprnd_info): Adjust. + (vect_get_and_check_slp_defs): Always use the type of the + operand. Allow mixed vect_external_def, vect_constant_def types. + (vect_get_constant_vectors): Handle mixed vect_external_def, + vect_constant_def types. + 2013-04-10 Joern Rennecke PR tree-optimization/55524 diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index aacd0094a09..debc2aba16b 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2013-04-10 Richard Biener + + * gcc.dg/vect/slp-39.c: New testcase. + 2013-04-10 Joern Rennecke PR tree-optimization/55524 diff --git a/gcc/testsuite/gcc.dg/vect/slp-39.c b/gcc/testsuite/gcc.dg/vect/slp-39.c new file mode 100644 index 00000000000..b3c278a5fe3 --- /dev/null +++ b/gcc/testsuite/gcc.dg/vect/slp-39.c @@ -0,0 +1,25 @@ +/* { dg-do compile } */ +/* { dg-require-effective-target vect_double } */ + +double x[1024], y[1024], z[1024]; +void foo (double w) +{ + int i; + for (i = 0; i < 1023; i+=2) + { + z[i] = x[i] + 1; + z[i+1] = x[i+1] + w; + } +} +void bar (double w) +{ + int i; + for (i = 0; i < 1023; i+=2) + { + z[i] = x[i] + w; + z[i+1] = x[i+1] + 1; + } +} + +/* { dg-final { scan-tree-dump-times "vectorizing stmts using SLP" 2 "vect" } } */ +/* { dg-final { cleanup-tree-dump "vect" } } */ diff --git a/gcc/tree-vect-slp.c b/gcc/tree-vect-slp.c index a06eeb73073..108a87a27ee 100644 --- a/gcc/tree-vect-slp.c +++ b/gcc/tree-vect-slp.c @@ -140,8 +140,7 @@ vect_create_oprnd_info (int nops, int group_size) oprnd_info = XNEW (struct _slp_oprnd_info); oprnd_info->def_stmts.create (group_size); oprnd_info->first_dt = vect_uninitialized_def; - oprnd_info->first_def_type = NULL_TREE; - oprnd_info->first_const_oprnd = NULL_TREE; + oprnd_info->first_op_type = NULL_TREE; oprnd_info->first_pattern = false; oprnds_info.quick_push (oprnd_info); } @@ -321,16 +320,7 @@ vect_get_and_check_slp_defs (loop_vec_info loop_vinfo, bb_vec_info bb_vinfo, { oprnd_info->first_dt = dt; oprnd_info->first_pattern = pattern; - if (def) - { - oprnd_info->first_def_type = TREE_TYPE (def); - oprnd_info->first_const_oprnd = NULL_TREE; - } - else - { - oprnd_info->first_def_type = NULL_TREE; - oprnd_info->first_const_oprnd = oprnd; - } + oprnd_info->first_op_type = TREE_TYPE (oprnd); } else { @@ -341,14 +331,13 @@ vect_get_and_check_slp_defs (loop_vec_info loop_vinfo, bb_vec_info bb_vinfo, vect_internal_def. */ if (((oprnd_info->first_dt != dt && !(oprnd_info->first_dt == vect_reduction_def - && dt == vect_internal_def)) - || (oprnd_info->first_def_type != NULL_TREE - && def - && !types_compatible_p (oprnd_info->first_def_type, - TREE_TYPE (def)))) - || (!def - && !types_compatible_p (TREE_TYPE (oprnd_info->first_const_oprnd), - TREE_TYPE (oprnd)))) + && dt == vect_internal_def) + && !((oprnd_info->first_dt == vect_external_def + || oprnd_info->first_dt == vect_constant_def) + && (dt == vect_external_def + || dt == vect_constant_def))) + || !types_compatible_p (oprnd_info->first_op_type, + TREE_TYPE (oprnd)))) { if (dump_enabled_p ()) dump_printf_loc (MSG_MISSED_OPTIMIZATION, vect_location, @@ -2471,7 +2460,7 @@ vect_get_constant_vectors (tree op, slp_tree slp_node, the lhs, so make sure the scalar is the right type if we are dealing with vectors of long long/long/short/char. */ - if (op_num == 1 && constant_p) + if (op_num == 1 && TREE_CODE (op) == INTEGER_CST) op = fold_convert (TREE_TYPE (vector_type), op); break; @@ -2504,7 +2493,7 @@ vect_get_constant_vectors (tree op, slp_tree slp_node, number_of_places_left_in_vector--; if (!types_compatible_p (TREE_TYPE (vector_type), TREE_TYPE (op))) { - if (constant_p) + if (CONSTANT_CLASS_P (op)) { op = fold_unary (VIEW_CONVERT_EXPR, TREE_TYPE (vector_type), op); @@ -2525,6 +2514,8 @@ vect_get_constant_vectors (tree op, slp_tree slp_node, } } elts[number_of_places_left_in_vector] = op; + if (!CONSTANT_CLASS_P (op)) + constant_p = false; if (number_of_places_left_in_vector == 0) { diff --git a/gcc/tree-vectorizer.h b/gcc/tree-vectorizer.h index 1a233a01fa2..0f1a02a2e37 100644 --- a/gcc/tree-vectorizer.h +++ b/gcc/tree-vectorizer.h @@ -169,8 +169,7 @@ typedef struct _slp_oprnd_info operand itself in case it's constant, and an indication if it's a pattern stmt. */ enum vect_def_type first_dt; - tree first_def_type; - tree first_const_oprnd; + tree first_op_type; bool first_pattern; } *slp_oprnd_info;