> Am 21.08.2025 um 16:56 schrieb Richard Sandiford <richard.sandif...@arm.com>:
> 
> This PR is another bug in the rtl-ssa code to manage live-out uses.
> It seems that this didn't get much coverage until recently.
> 
> In the testcase, late-combine first removed a register-to-register
> move by substituting into all uses, some of which were in other EBBs.
> This was done after checking make_uses_available, which (as expected)
> says that single dominating definitions are available everywhere
> that the definition dominates.  But the update failed to add
> appropriate live-out uses, so a later parallelisation attempt
> tried to move the new destination into a later block.
> 
> Sorry that this seems to be a recurring source of bugs.
> I'll try to think of a way of testing and structuring it better.
> 
> Tested on aarch64-linux-gnu & x86_64-linux-gnu.  OK to install?

Ok.  Does this also fix the arm32 bootstrap issue?

Thanks,
Richard 

> Richard
> 
> 
> gcc/
>    PR rtl-optimization/121619
>    * rtl-ssa/functions.h (function_info::commit_make_use_available):
>    Declare.
>    * rtl-ssa/functions.cc (function_info::commit_make_use_available):
>    New function.
>    * rtl-ssa/changes.cc (function_info::apply_changes_to_insn): Use it.
> 
> gcc/testsuite/
>    PR rtl-optimization/121619
>    * gcc.dg/pr121619.c: New test.
> ---
> gcc/rtl-ssa/blocks.cc           | 35 +++++++++++++++++++++++++++++++++
> gcc/rtl-ssa/changes.cc          |  6 +++++-
> gcc/rtl-ssa/functions.h         |  1 +
> gcc/testsuite/gcc.dg/pr121619.c | 33 +++++++++++++++++++++++++++++++
> 4 files changed, 74 insertions(+), 1 deletion(-)
> create mode 100644 gcc/testsuite/gcc.dg/pr121619.c
> 
> diff --git a/gcc/rtl-ssa/blocks.cc b/gcc/rtl-ssa/blocks.cc
> index a57b9e15f13..568f9658540 100644
> --- a/gcc/rtl-ssa/blocks.cc
> +++ b/gcc/rtl-ssa/blocks.cc
> @@ -359,6 +359,41 @@ function_info::live_out_value (bb_info *bb, set_info 
> *set)
>   return set;
> }
> 
> +// Make USE's definition available at USE, if it isn't already.  Assume that
> +// the caller has properly used make_use_available to check that this is
> +// possible.
> +void
> +function_info::commit_make_use_available (use_info *use)
> +{
> +  // We only need to handle single dominating definitions here.
> +  // Other cases are handled by degenerate phis, with create_degenerate_phi
> +  // creating any necessary live-out uses.
> +  set_info *def = use->def ();
> +  if (def
> +      && use->is_reg ()
> +      && is_single_dominating_def (def)
> +      && use->ebb () != def->ebb ())
> +    {
> +      // If USE's EBB has DEF's EBB as its single predecessor, it's enough
> +      // to add a live-out use to the former's predecessor block.  Otherwise,
> +      // conservatively add a live-out use at the end of DEF's block, so that
> +      // DEF cannot move further down.  Doing a minimal yet accurate update
> +      // would be an O(n.log(n)) operation in the worst case.
> +      auto ebb_cfg_bb = def->ebb ()->first_bb ()->cfg_bb ();
> +      if (single_pred_p (ebb_cfg_bb))
> +    {
> +      bb_info *pred_bb = this->bb (single_pred (ebb_cfg_bb));
> +      if (pred_bb->ebb () == def->ebb ())
> +        {
> +          add_live_out_use (pred_bb, def);
> +          return;
> +        }
> +    }
> +      add_live_out_use (def->bb (), def);
> +      return;
> +    }
> +}
> +
> // Add PHI to EBB and enter it into the function's hash table.
> void
> function_info::append_phi (ebb_info *ebb, phi_info *phi)
> diff --git a/gcc/rtl-ssa/changes.cc b/gcc/rtl-ssa/changes.cc
> index 00e6c318564..f2fc9826c4f 100644
> --- a/gcc/rtl-ssa/changes.cc
> +++ b/gcc/rtl-ssa/changes.cc
> @@ -713,7 +713,11 @@ function_info::apply_changes_to_insn (insn_change 
> &change,
> 
>   // Add all uses, now that their position is final.
>   for (use_info *use : change.new_uses)
> -    add_use (use);
> +    {
> +      if (use->def ())
> +    commit_make_use_available (use);
> +      add_use (use);
> +    }
> 
>   // Copy the uses and definitions.
>   unsigned int num_defs = change.new_defs.size ();
> diff --git a/gcc/rtl-ssa/functions.h b/gcc/rtl-ssa/functions.h
> index 27cbc18178a..ba805072ba4 100644
> --- a/gcc/rtl-ssa/functions.h
> +++ b/gcc/rtl-ssa/functions.h
> @@ -309,6 +309,7 @@ private:
> 
>   void add_live_out_use (bb_info *, set_info *);
>   set_info *live_out_value (bb_info *, set_info *);
> +  void commit_make_use_available (use_info *);
> 
>   void append_phi (ebb_info *, phi_info *);
>   void remove_phi (phi_info *);
> diff --git a/gcc/testsuite/gcc.dg/pr121619.c b/gcc/testsuite/gcc.dg/pr121619.c
> new file mode 100644
> index 00000000000..a63896d244a
> --- /dev/null
> +++ b/gcc/testsuite/gcc.dg/pr121619.c
> @@ -0,0 +1,33 @@
> +/* { dg-do run } */
> +/* { dg-options "-O3 -fno-gcse -fno-tree-ter -fno-guess-branch-probability 
> -fno-forward-propagate" } */
> +
> +int printf(const char *, ...);
> +long a, c, d;
> +char b;
> +int main() {
> +f : {
> +  short g = 100;
> +  int h = 1;
> +  while (1) {
> +    char i = 0;
> +    if (a)
> +      i = h = -b;
> +    short j = g;
> +    c = h ^ g;
> +    g = ~(-h / c + 1);
> +    if (b > 6) {
> +      a = g && -1;
> +      goto f;
> +    }
> +    if (j < 100)
> +      printf("%ld\n", d);
> +    if (g - 1)
> +      break;
> +    b = i;
> +  }
> +  int k = 2L % g;
> +  if (k)
> +    goto f;
> +  }
> +  return 0;
> +}
> --
> 2.43.0
> 

Reply via email to