This fixes re-use of the reduction value in epilogue vectorization when a conversion from/to variable lenght vectors is required.
Bootstrapped and tested on x86_64-unknown-linux-gnu, pushed. 2021-09-07 Richard Biener <rguent...@suse.de> PR tree-optimization/102226 * tree-vect-loop.c (vect_transform_cycle_phi): Record the converted value for the epilogue PHI use. * g++.dg/vect/pr102226.cc: New testcase. --- gcc/testsuite/g++.dg/vect/pr102226.cc | 29 +++++++++++++++++++++++++++ gcc/tree-vect-loop.c | 4 ++-- 2 files changed, 31 insertions(+), 2 deletions(-) create mode 100644 gcc/testsuite/g++.dg/vect/pr102226.cc diff --git a/gcc/testsuite/g++.dg/vect/pr102226.cc b/gcc/testsuite/g++.dg/vect/pr102226.cc new file mode 100644 index 00000000000..ddf5e460c28 --- /dev/null +++ b/gcc/testsuite/g++.dg/vect/pr102226.cc @@ -0,0 +1,29 @@ +// { dg-do compile } +// { dg-require-effective-target c++11 } +// { dg-additional-options "-msve-vector-bits=128" { target aarch64_sve } } + +template <typename a> struct b { using c = a; }; +template <typename a, template <typename> class> using f = b<a>; +template <typename a, template <typename> class g> +using h = typename f<a, g>::c; +struct i { + template <typename j> using k = typename j::l; +}; +struct m : i { + using l = h<char *, k>; +}; +class n { +public: + char operator[](long o) { + m::l s; + return s[o]; + } +} p; +n r; +int q() { + long d; + for (long e; e; e++) + if (p[e] == r[e]) + d++; + return d; +} diff --git a/gcc/tree-vect-loop.c b/gcc/tree-vect-loop.c index 0c8d992624b..c9dcc647d2c 100644 --- a/gcc/tree-vect-loop.c +++ b/gcc/tree-vect-loop.c @@ -7755,11 +7755,11 @@ vect_transform_cycle_phi (loop_vec_info loop_vinfo, (reduc_info), &stmts); } + if (!useless_type_conversion_p (vectype_out, TREE_TYPE (def))) + def = gimple_convert (&stmts, vectype_out, def); /* Adjust the input so we pick up the partially reduced value for the skip edge in vect_create_epilog_for_reduction. */ accumulator->reduc_input = def; - if (!useless_type_conversion_p (vectype_out, TREE_TYPE (def))) - def = gimple_convert (&stmts, vectype_out, def); if (loop_vinfo->main_loop_edge) { /* While we'd like to insert on the edge this will split -- 2.31.1