On Thu, 9 Feb 2017, Jakub Jelinek wrote: > Hi! > > This is a big hammer approach for (ab) SSA_NAME issues in reassoc, on > the following testcase we extend the lifetime of (ab) SSA_NAME and ICE > because it can't be coalesced anymore. In theory we could try to be careful > and whenever changing something that could extend (ab) lifetime, instead > insert a non-(ab) SSA_NAME to copy the (ab) SSA_NAME to at the point of use > and then use the temporary later on, but after looking for a while, it would > mean changing way too many places, so this patch just punts on them or > stops linearing when seeing them, so the ops vectors should not contain > (ab) SSA_NAMEs, the various negations/undistributions etc. should also avoid > them etc. > > Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
Ok. I suppose at the point we add the ability to associate undefined-overflow ops (and have to be careful to not introduce new undefined-overflow cases) we'll have enough infrastructure in place to improve on this. Like for undefined-overflow re-writing everything to unsigned arithmetic and for the abnormal case inserting copies at the original point of uses. (both less than ideal but working) Thanks, Richard. > 2017-02-09 Jakub Jelinek <ja...@redhat.com> > > PR tree-optimization/79411 > * tree-ssa-reassoc.c (is_reassociable_op): Return false if > stmt operands are SSA_NAMEs used in abnormal phis. > (can_reassociate_p): Return false if op is SSA_NAME used in abnormal > phis. > > * gcc.c-torture/compile/pr79411.c: New test. > > --- gcc/tree-ssa-reassoc.c.jj 2017-01-24 23:29:09.000000000 +0100 > +++ gcc/tree-ssa-reassoc.c 2017-02-09 13:14:23.711878845 +0100 > @@ -605,7 +605,18 @@ is_reassociable_op (gimple *stmt, enum t > if (is_gimple_assign (stmt) > && gimple_assign_rhs_code (stmt) == code > && has_single_use (gimple_assign_lhs (stmt))) > - return true; > + { > + tree rhs1 = gimple_assign_rhs1 (stmt); > + tree rhs2 = gimple_assign_rhs1 (stmt); > + if (TREE_CODE (rhs1) == SSA_NAME > + && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (rhs1)) > + return false; > + if (rhs2 > + && TREE_CODE (rhs2) == SSA_NAME > + && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (rhs2)) > + return false; > + return true; > + } > > return false; > } > @@ -4989,6 +5000,8 @@ static bool > can_reassociate_p (tree op) > { > tree type = TREE_TYPE (op); > + if (TREE_CODE (op) == SSA_NAME && SSA_NAME_OCCURS_IN_ABNORMAL_PHI (op)) > + return false; > if ((ANY_INTEGRAL_TYPE_P (type) && TYPE_OVERFLOW_WRAPS (type)) > || NON_SAT_FIXED_POINT_TYPE_P (type) > || (flag_associative_math && FLOAT_TYPE_P (type))) > --- gcc/testsuite/gcc.c-torture/compile/pr79411.c.jj 2017-02-09 > 13:34:06.016485562 +0100 > +++ gcc/testsuite/gcc.c-torture/compile/pr79411.c 2017-02-09 > 13:33:53.000000000 +0100 > @@ -0,0 +1,22 @@ > +/* PR tree-optimization/79411 */ > + > +typedef struct __jmp_buf_tag { char buf[1024]; } jmp_buf[1]; > +extern int setjmp (jmp_buf); > +extern int bar (unsigned int *); > +extern jmp_buf *baz (void); > +struct C { int c1; unsigned int c2, c3, c4; }; > + > +void > +foo (struct C *x, const int *y, unsigned int *z, unsigned int e, unsigned > int g) > +{ > + unsigned int d = 0; > + unsigned long f; > + setjmp (*baz ()); > + f = 1 + d; > + if ((x->c1 || x->c2) && g && (!e || d >= 8)) > + d = 16; > + else > + d = 8; > + if ((!x->c3 && !x->c4 || *y == 0) && !e && bar (z)) > + *z = 1 + f; > +} > > Jakub > > -- Richard Biener <rguent...@suse.de> SUSE LINUX GmbH, GF: Felix Imendoerffer, Jane Smithard, Graham Norton, HRB 21284 (AG Nuernberg)