https://gcc.gnu.org/g:7b313f53590ab6c404943a6487769540c1654d7b

commit r16-2570-g7b313f53590ab6c404943a6487769540c1654d7b
Author: Takayuki 'January June' Suwa <jjsuwa_sys3...@yahoo.co.jp>
Date:   Fri Jul 25 10:40:42 2025 +0900

    xtensa: Fix remaining inaccuracies in xtensa_is_insn_L32R_p()
    
    The previous fix also had some flaws:
    
    - The TARGET_CONST16 check was a bit premature
    - It didn't take into account the possibility of the RTL expression
       "(set (reg:SF gpr) (const_int))", especially when TARGET_AUTOLITPOOLS is
       configured
    
    This patch fixes the above.
    
    gcc/ChangeLog:
    
            * config/xtensa/xtensa.cc (xtensa_is_insn_L32R_p):
            Re-rewrite to more accurately capture insns that could be L32R 
machine
            instructions wherever possible, and add comments that help 
understand
            the intent of the process.

Diff:
---
 gcc/config/xtensa/xtensa.cc | 46 ++++++++++++++++++++++++++++++++++-----------
 1 file changed, 35 insertions(+), 11 deletions(-)

diff --git a/gcc/config/xtensa/xtensa.cc b/gcc/config/xtensa/xtensa.cc
index 02554c55687d..d75cba4b3fd3 100644
--- a/gcc/config/xtensa/xtensa.cc
+++ b/gcc/config/xtensa/xtensa.cc
@@ -4702,25 +4702,49 @@ static bool
 xtensa_is_insn_L32R_p (const rtx_insn *insn)
 {
   rtx pat, dest, src;
+  machine_mode mode;
 
-  /* "PATTERN (insn)" can be used without checking, see insn_cost()
-     in gcc/rtlanal.cc.  */
+  /* RTX insns that are not "(set (reg) ...)" cannot become L32R instructions:
+     - it is permitted to apply PATTERN() to the insn without validation.
+       See insn_cost() in gcc/rtlanal.cc.
+     - it is used register_operand() instead of REG() to identify things that
+       don't look like REGs but will eventually become so as well.  */
   if (GET_CODE (pat = PATTERN (insn)) != SET
       || ! register_operand (dest = SET_DEST (pat), VOIDmode))
     return false;
 
+  /* If the source is a reference to a literal pool entry, then the insn
+     obviously corresponds to an L32R instruction.  */
   if (constantpool_mem_p (src = SET_SRC (pat)))
     return true;
 
-  /* Return true if:
-     - CONST16 instruction is not configured, and
-     - the source is some constant, and also
-     - negation of "the source is integer and fits into the immediate
-       field".  */
-  return (!TARGET_CONST16
-         && CONSTANT_P (src)
-         && ! ((GET_MODE (dest) == SImode || GET_MODE (dest) == HImode)
-               && CONST_INT_P (src) && xtensa_simm12b (INTVAL (src))));
+  /* Similarly, an insn whose source is not a constant obviously does not
+     correspond to L32R.  */
+  if (! CONSTANT_P (src))
+    return false;
+
+  /* If the source is a CONST_INT whose value fits into signed 12 bits, then
+     the insn corresponds to a MOVI instruction (rather than an L32R one),
+     regardless of the configuration of TARGET_CONST16 or
+     TARGET_AUTOLITPOOLS.  Note that the destination register can be non-
+     SImode.  */
+  if (((mode = GET_MODE (dest)) == SImode
+       || mode == HImode || mode == SFmode)
+      && CONST_INT_P (src) && xtensa_simm12b (INTVAL (src)))
+    return false;
+
+  /* If TARGET_CONST16 is configured, constants of the remaining forms
+     correspond to pairs of CONST16 instructions, not L32R.  */
+  if (TARGET_CONST16)
+    return false;
+
+  /* The last remaining form of constant is one of the following:
+     - CONST_INTs with large values
+     - floating-point constants
+     - symbolic constants
+     and is all handled by a relaxed MOVI instruction, which is later
+     converted to an L32R instruction by the assembler.  */
+  return true;
 }
 
 /* Compute a relative costs of RTL insns.  This is necessary in order to

Reply via email to