On Wed, Jul 8, 2026 at 10:20 AM Andrew Pinski
<[email protected]> wrote:
>
> Since match and simplify can add unused statements to the sequence
> in some cases, we should remove them before call phiopt_early_allow.
> This is needed for 2 future patches. One is to allowing of comparisons,
> optionally with a cast and optional with a negative expression.
> The other is about supporting a way to handling
> cond_removal_in_builtin_zero_pattern in match and also adding a new match
> pattern to fix PR 126035 (ctz split back into one).
>
> Bootstrapped and tested on x86_64-linux-gnu.
>
> gcc/ChangeLog:
>
> * tree-ssa-phiopt.cc (remove_unused_stmts): New function.
> (gimple_simplify_phiopt): Call remove_unused_stmts before
> phiopt_early_allow.
>
> Signed-off-by: Andrew Pinski <[email protected]>
> ---
> gcc/tree-ssa-phiopt.cc | 48 ++++++++++++++++++++++++++++++++++++++++++
> 1 file changed, 48 insertions(+)
>
> diff --git a/gcc/tree-ssa-phiopt.cc b/gcc/tree-ssa-phiopt.cc
> index e12dc7a8b0c..fd173ec01f4 100644
> --- a/gcc/tree-ssa-phiopt.cc
> +++ b/gcc/tree-ssa-phiopt.cc
> @@ -688,6 +688,52 @@ phiopt_early_allow (gimple_seq &seq, gimple_match_op &op)
> }
> }
>
> +/* Remove unused statements in SEQ. That are used in OP.
> + This is needed for the way resimplify/match and simplify
> + works as it will place some unneeded statements in the sequence
> + which can get in the way of handling phiopt_early_allow. */
> +
> +static void
> +remove_unused_stmts (gimple_seq *seq, const gimple_match_op &op)
> +{
> + if (*seq == nullptr)
> + return;
> +
> + /* Since the sequence of statements are not part of
> + a basic block yet, have to manually go through the operands
> + to mark the uses. */
> + auto_bitmap uses;
> + for (unsigned i = 0; i < op.num_ops; i++)
> + {
> + tree use = op.ops[i];
> + if (TREE_CODE (use) == SSA_NAME)
> + bitmap_set_bit (uses, SSA_NAME_VERSION (use));
> + }
> + gimple_stmt_iterator gsi = gsi_last (*seq);
> + while (!gsi_end_p (gsi))
> + {
> + gimple *s = *gsi;
> + tree lhs = gimple_get_lhs (s);
> + if (bitmap_bit_p (uses, SSA_NAME_VERSION (lhs)))
> + {
> + for (unsigned i = 0; i < gimple_num_ops (s); i++)
> + {
> + tree use = gimple_op (s, i);
> + if (TREE_CODE (use) == SSA_NAME)
> + bitmap_set_bit (uses, SSA_NAME_VERSION (use));
I think this doesn't work on REALPART_EXPR and friends,
nor on &a[i_3]. Not sure the latter will appear, but for sure
the former will.
Walking SSA operands w/o SSA operands is ... hard (you
might want to dig out removed vectorizer code that needed
to do this for pattern stmts).
> + }
> + gsi_prev (&gsi);
> + continue;
> + }
> + gsi_remove (&gsi, true);
> + release_defs (s);
> + ggc_free (s);
> + /* If this was the last statement, start over. */
> + if (gsi_end_p (gsi))
> + gsi = gsi_last (*seq);
> + }
> +}
> +
> /* gimple_simplify_phiopt is like gimple_simplify but designed for PHIOPT.
> Return NULL if nothing can be simplified or the resulting simplified value
> with parts pushed if EARLY_P was true. Also rejects non allowed tree code
> @@ -729,6 +775,7 @@ gimple_simplify_phiopt (bool early_p, tree type, gimple
> *comp_stmt,
>
> if (op.resimplify (&seq1, follow_all_ssa_edges))
> {
> + remove_unused_stmts (&seq1, op);
> bool allowed = !early_p || phiopt_early_allow (seq1, op);
> tree result = maybe_push_res_to_seq (&op, &seq1);
> if (dump_file && (dump_flags & TDF_FOLDING))
> @@ -783,6 +830,7 @@ gimple_simplify_phiopt (bool early_p, tree type, gimple
> *comp_stmt,
>
> if (op1.resimplify (&seq1, follow_all_ssa_edges))
> {
> + remove_unused_stmts (&seq1, op1);
> bool allowed = !early_p || phiopt_early_allow (seq1, op1);
> tree result = maybe_push_res_to_seq (&op1, &seq1);
> if (dump_file && (dump_flags & TDF_FOLDING))
> --
> 2.43.0
>