On Wed, Feb 12, 2025 at 4:04 AM Richard Biener <rguent...@suse.de> wrote: > > The PR indicates a very specific issue with regard to SSA coalescing > failures because there's a pre IV increment loop exit test. While > IVOPTs created the desired IL we later simplify the exit test into > the undesirable form again. The following fixes this up during RTL > expansion where we try to improve coalescing of IVs. That seems > easier that trying to avoid the simplification with some weird > heuristics (it could also have been written this way). > > Bootstrapped and tested on x86_64-unknown-linux-gnu. > > OK for trunk? > > Thanks, > Richard. > > PR tree-optimization/86270 > * tree-outof-ssa.cc (insert_backedge_copies): Pattern > match a single conflict in a loop condition and adjust > that avoiding the conflict if possible. > > * gcc.target/i386/pr86270.c: Adjust to check for no reg-reg > copies as well. > --- > gcc/testsuite/gcc.target/i386/pr86270.c | 3 ++ > gcc/tree-outof-ssa.cc | 49 ++++++++++++++++++++++--- > 2 files changed, 47 insertions(+), 5 deletions(-) > > diff --git a/gcc/testsuite/gcc.target/i386/pr86270.c > b/gcc/testsuite/gcc.target/i386/pr86270.c > index 68562446fa4..89b9aeb317a 100644 > --- a/gcc/testsuite/gcc.target/i386/pr86270.c > +++ b/gcc/testsuite/gcc.target/i386/pr86270.c > @@ -13,3 +13,6 @@ test () > > /* Check we do not split the backedge but keep nice loop form. */ > /* { dg-final { scan-assembler-times "L\[0-9\]+:" 2 } } */ > +/* Check we do not end up with reg-reg moves from a pre-increment IV > + exit test. */ > +/* { dg-final { scan-assembler-not "mov\[lq\]\?\t%\?\[er\].x, %\?\[er\].x" } > } */ > diff --git a/gcc/tree-outof-ssa.cc b/gcc/tree-outof-ssa.cc > index d340d4ba529..f285c81599e 100644 > --- a/gcc/tree-outof-ssa.cc > +++ b/gcc/tree-outof-ssa.cc > @@ -1259,10 +1259,9 @@ insert_backedge_copies (void) > if (gimple_nop_p (def) > || gimple_code (def) == GIMPLE_PHI) > continue; > - tree name = copy_ssa_name (result); > - gimple *stmt = gimple_build_assign (name, result); > imm_use_iterator imm_iter; > gimple *use_stmt; > + auto_vec<use_operand_p, 8> uses; > /* The following matches trivially_conflicts_p. */ > FOR_EACH_IMM_USE_STMT (use_stmt, imm_iter, result) > { > @@ -1273,11 +1272,51 @@ insert_backedge_copies (void) > { > use_operand_p use; > FOR_EACH_IMM_USE_ON_STMT (use, imm_iter) > - SET_USE (use, name); > + uses.safe_push (use); > } > } > - gimple_stmt_iterator gsi = gsi_for_stmt (def); > - gsi_insert_before (&gsi, stmt, GSI_SAME_STMT); > + /* When there is just a conflicting statement try to > + adjust that to refer to the new definition. > + In particular for now handle a conflict with the > + use in a (exit) condition with a NE compare, > + replacing a pre-IV-increment compare with a > + post-IV-increment one. */ > + if (uses.length () == 1 > + && is_a <gcond *> (USE_STMT (uses[0])) > + && gimple_cond_code (USE_STMT (uses[0])) == NE_EXPR > + && is_gimple_assign (def) > + && gimple_assign_rhs1 (def) == result > + && (gimple_assign_rhs_code (def) == PLUS_EXPR > + || gimple_assign_rhs_code (def) == MINUS_EXPR > + || gimple_assign_rhs_code (def) == > POINTER_PLUS_EXPR) > + && TREE_CODE (gimple_assign_rhs2 (def)) == INTEGER_CST) > + { > + gcond *cond = as_a <gcond *> (USE_STMT (uses[0])); > + tree *adj; > + if (gimple_cond_lhs (cond) == result) > + adj = gimple_cond_rhs_ptr (cond); > + else > + adj = gimple_cond_lhs_ptr (cond); > + tree name = copy_ssa_name (result);
Should this be `copy_ssa_name (*adj)`? Since the new name is based on `*adj` rather than based on the result. Thanks, Andrew Pinski > + gimple *stmt > + = gimple_build_assign (name, > + gimple_assign_rhs_code (def), > + *adj, gimple_assign_rhs2 > (def)); > + gimple_stmt_iterator gsi = gsi_for_stmt (cond); > + gsi_insert_before (&gsi, stmt, GSI_SAME_STMT); > + *adj = name; > + SET_USE (uses[0], arg); > + update_stmt (cond); > + } > + else > + { > + tree name = copy_ssa_name (result); > + gimple *stmt = gimple_build_assign (name, result); > + gimple_stmt_iterator gsi = gsi_for_stmt (def); > + gsi_insert_before (&gsi, stmt, GSI_SAME_STMT); > + for (auto use : uses) > + SET_USE (use, name); > + } > } > } > } > -- > 2.43.0