On Fri, 2025-06-27 at 10:51 -0300, Raphael Moreira Zinsly wrote: > A right shift of 31 will become 0 or 1, this can be checked for > treg_set_expr_not_const01 to avoid matching addc_t_r as this > can expand to a 3 insn sequence instead. > This improves tests 023 to 026 from gcc.target/sh/pr54236-2.c, e.g.: > test_023: > shll r5 > mov #0,r1 > mov r4,r0 > rts > addc r1,r0 > > With this change: > test_023: > shll r5 > movt r0 > rts > add r4,r0 > > We noticed this while evaluating a patch to improve how we handle > selecting between two constants based on the output of a LT/GE 0 > test. > > gcc/ChangeLog: > * config/sh/predicates.md > (treg_set_expr_not_const01): call sh_recog_treg_set_expr_not_01 > * config/sh/sh-protos.h > (sh_recog_treg_set_expr_not_01): New function > config/sh/sh.cc (sh_recog_treg_set_expr_not_01): Likewise > > gcc/testsuite/ChangeLog: > * gcc.target/sh/pr54236-2.c: Fix comments and expected output
Assuming that this passes the usual regression tests, it looks OK to me. Please apply. Best regards, Oleg Endo > --- > gcc/config/sh/predicates.md | 4 +--- > gcc/config/sh/sh-protos.h | 1 + > gcc/config/sh/sh.cc | 17 +++++++++++++++++ > gcc/testsuite/gcc.target/sh/pr54236-2.c | 14 +++++++------- > 4 files changed, 26 insertions(+), 10 deletions(-) > > diff --git a/gcc/config/sh/predicates.md b/gcc/config/sh/predicates.md > index 7349c97a2b5..e67ec8a2320 100644 > --- a/gcc/config/sh/predicates.md > +++ b/gcc/config/sh/predicates.md > @@ -630,9 +630,7 @@ > ;; Same as treg_set_expr but disallow constants 0 and 1 which can be loaded > ;; into the T bit. > (define_predicate "treg_set_expr_not_const01" > - (and (match_test "op != const0_rtx") > - (match_test "op != const1_rtx") > - (match_operand 0 "treg_set_expr"))) > + (match_test "sh_recog_treg_set_expr_not_01 (op, mode)")) > > ;; A predicate describing the T bit register in any form. > (define_predicate "t_reg_operand" > diff --git a/gcc/config/sh/sh-protos.h b/gcc/config/sh/sh-protos.h > index c8cc19f4dc7..e78b6697a2b 100644 > --- a/gcc/config/sh/sh-protos.h > +++ b/gcc/config/sh/sh-protos.h > @@ -261,6 +261,7 @@ extern rtx_insn* sh_peephole_emit_move_insn (rtx dst, rtx > src); > > extern bool sh_in_recog_treg_set_expr (void); > extern bool sh_recog_treg_set_expr (rtx op, machine_mode mode); > +extern bool sh_recog_treg_set_expr_not_01 (rtx op, machine_mode mode); > > /* Result value of sh_split_treg_set_expr. Contains the first insn emitted > and the optional trailing nott insn. */ > diff --git a/gcc/config/sh/sh.cc b/gcc/config/sh/sh.cc > index 1bc34e0a3e3..09e4ff77c20 100644 > --- a/gcc/config/sh/sh.cc > +++ b/gcc/config/sh/sh.cc > @@ -12348,6 +12348,23 @@ sh_recog_treg_set_expr (rtx op, machine_mode mode) > return result >= 0; > } > > +/* Return TRUE if OP is an expression for which there is a pattern to > + set the T bit unless the expression is trivially loadable into > + the T bit, FALSE otherwise. */ > +bool > +sh_recog_treg_set_expr_not_01 (rtx op, machine_mode mode) > +{ > + if (op == const0_rtx || op == const1_rtx) > + return false; > + > + /* A right shift of 31 will return 0 or 1. */ > + if ((GET_CODE (op) == LSHIFTRT || GET_CODE (op) == ASHIFTRT) > + && INTVAL (XEXP (op, 1)) == 31) > + return false; > + > + return sh_recog_treg_set_expr (op, mode); > +} > + > /* Returns true when recog of a 'treg_set_expr' is currently in progress. > This can be used as a condition for insn/split patterns to allow certain > T bit setting patters only to be matched as sub expressions of other > diff --git a/gcc/testsuite/gcc.target/sh/pr54236-2.c > b/gcc/testsuite/gcc.target/sh/pr54236-2.c > index 1e2f3bbcb56..78befe43770 100644 > --- a/gcc/testsuite/gcc.target/sh/pr54236-2.c > +++ b/gcc/testsuite/gcc.target/sh/pr54236-2.c > @@ -4,10 +4,10 @@ > /* { dg-do compile } */ > /* { dg-options "-O1" } */ > > -/* { dg-final { scan-assembler-times "addc" 36 } } */ > +/* { dg-final { scan-assembler-times "addc" 32 } } */ > /* { dg-final { scan-assembler-times "shll" 14 } } */ > -/* { dg-final { scan-assembler-times "add\tr" 12 } } */ > -/* { dg-final { scan-assembler-not "movt" } } */ > +/* { dg-final { scan-assembler-times "add\tr" 16 } } */ > +/* { dg-final { scan-assembler-times "movt" 4 } } */ > > /* { dg-final { scan-assembler-times "add\t#1" 1 } } */ > > @@ -184,28 +184,28 @@ test_022 (int a, int b, int c, int d) > int > test_023 (int a, int b, int c, int d) > { > - // 1x shll, 1x addc > + // 1x shll, 1x add > return a + ((b >> 31) & 1); > } > > int > test_024 (int a, int b, int c, int d) > { > - // 1x shll, 1x addc > + // 1x shll, 1x add > return ((b >> 31) & 1) + a; > } > > int > test_025 (int a, int b, int c, int d) > { > - // 1x shll, 1x addc > + // 1x shll, 1x add > return ((a >> 31) & 1) + a; > } > > int > test_026 (int a, int b, int c, int d) > { > - // 1x shll, 1x addc > + // 1x shll, 1x add > return a + ((a >> 31) & 1); > } > > -- > 2.47.0 >