On Mon, Mar 11, 2019 at 12:39 PM Richard Biener <rguent...@suse.de> wrote: > > > The following fixes a missed vectorization of std::min() when > only one argument is a temporary. The following patch is the least > intrusive and safest one - PRE already performs the necessary > work to make this vectorizable, it's just that we end up with > a dead store and clobber of a stack-local that the vectorizer is > not happy about. The easiest fix is to schedule an update-address-taken > phase at the right spot which rewrites it into SSA and then DCE > can get rid of it. DSE would also do the job but is more expensive. > Since PRE/VN have the chance to expose things that can be written > into SSA doing so before loop opts sounds like a good idea in any case. > > Bootstrap & regtest running on x86_64-unknown-linux-gnu. > > Queued for GCC 10 for which I also have a fix for phiprop which > usually deals with std::min/max if-conversion. The one below > is quite safe but it's not a regression unfortunately.
Applied as r270800. Richard. > Richard. > > 2019-03-11 Richard Biener <rguent...@suse.de> > > PR tree-optimization/89653 > * tree-ssa-loop.c (pass_data_tree_loop_init): Execute > update-address-taken before the pass. > * passes.def (pass_tree_loop_init): Put comment before it. > > * g++.dg/vect/pr89653.cc: New testcase. > > Index: gcc/tree-ssa-loop.c > =================================================================== > --- gcc/tree-ssa-loop.c (revision 269569) > +++ gcc/tree-ssa-loop.c (working copy) > @@ -330,7 +330,7 @@ const pass_data pass_data_tree_loop_init > PROP_cfg, /* properties_required */ > 0, /* properties_provided */ > 0, /* properties_destroyed */ > - 0, /* todo_flags_start */ > + TODO_update_address_taken, /* todo_flags_start */ > 0, /* todo_flags_finish */ > }; > > Index: gcc/passes.def > =================================================================== > --- gcc/passes.def (revision 269569) > +++ gcc/passes.def (working copy) > @@ -261,6 +261,8 @@ along with GCC; see the file COPYING3. > NEXT_PASS (pass_fix_loops); > NEXT_PASS (pass_tree_loop); > PUSH_INSERT_PASSES_WITHIN (pass_tree_loop) > + /* Before loop_init we rewrite no longer addressed locals into SSA > + form if possible. */ > NEXT_PASS (pass_tree_loop_init); > NEXT_PASS (pass_tree_unswitch); > NEXT_PASS (pass_scev_cprop); > Index: gcc/testsuite/g++.dg/vect/pr89653.cc > =================================================================== > --- gcc/testsuite/g++.dg/vect/pr89653.cc (nonexistent) > +++ gcc/testsuite/g++.dg/vect/pr89653.cc (working copy) > @@ -0,0 +1,12 @@ > +// { dg-do compile } > +// { dg-require-effective-target vect_double } > + > +#include <algorithm> > + > +void loop1(double * const __restrict__ vec, double x, int end) > +{ > + for (int i = 0; i < end; ++i) > + vec[i] = std::min(vec[i], vec[i]/x); > +} > + > +// { dg-final { scan-tree-dump "vectorized 1 loops" "vect" } }