]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
[to-be-committed][RISC-V] Handle 32bit operands in condition for conditional moves
authorJeff Law <jlaw@ventanamicro.com>
Sat, 7 Jun 2025 13:48:46 +0000 (07:48 -0600)
committerJeff Law <jlaw@ventanamicro.com>
Sat, 7 Jun 2025 13:48:46 +0000 (07:48 -0600)
So here's the next chunk of conditional move work from Shreya.

It's been a long standing wart that the conditional move expander does not
support sub-word operands in the comparison.  Particularly since we have
support routines to handle the necessary extensions for that case.

This patch adjusts the expander to use riscv_extend_comparands rather than fail
for that case.  I've built spec2017 before/after this and we definitely get
more conditional moves and they look sensible from a performance standpoint.
None are likely hitting terribly hot code, so I wouldn't expect any performance
jumps.

Waiting on pre-commit testing to do its thing.

* config/riscv/riscv.cc (riscv_expand_conditional_move): Use
riscv_extend_comparands to extend sub-word comparison arguments.

Co-authored-by: Jeff Law <jlaw@ventanamicro.com>
gcc/config/riscv/riscv.cc

index 99eeba64b6f975ee790610fd682c0428ba6cc0aa..dd29059412b18ada2340793c524d0f080974f06f 100644 (file)
@@ -5436,13 +5436,18 @@ riscv_expand_conditional_move (rtx dest, rtx op, rtx cons, rtx alt)
       machine_mode mode0 = GET_MODE (op0);
       machine_mode mode1 = GET_MODE (op1);
 
-      /* An integer comparison must be comparing WORD_MODE objects.  We
-        must enforce that so that we don't strip away a sign_extension
-        thinking it is unnecessary.  We might consider using
-        riscv_extend_operands if they are not already properly extended.  */
+      /* An integer comparison must be comparing WORD_MODE objects.
+        Extend the comparison arguments as necessary.  */
       if ((INTEGRAL_MODE_P (mode0) && mode0 != word_mode)
          || (INTEGRAL_MODE_P (mode1) && mode1 != word_mode))
-       return false;
+       riscv_extend_comparands (code, &op0, &op1);
+
+      /* We might have been handed back a SUBREG.  Just to make things
+        easy, force it into a REG.  */
+      if (!REG_P (op0) && !CONST_INT_P (op0))
+       op0 = force_reg (word_mode, op0);
+      if (!REG_P (op1) && !CONST_INT_P (op1))
+       op1 = force_reg (word_mode, op1);
 
       /* In the fallback generic case use MODE rather than WORD_MODE for
         the output of the SCC instruction, to match the mode of the NEG