diff mbox series

[committed,PR97701] LRA: Don't narrow class only for REG or MEM.

Message ID 1e48308d-ddad-f235-560d-276b292d647e@redhat.com
State New
Headers show
Series [committed,PR97701] LRA: Don't narrow class only for REG or MEM. | expand

Commit Message

Vladimir Makarov Jan. 29, 2021, 7:56 p.m. UTC
The following patch solves

    https://gcc.gnu.org/bugzilla/show_bug.cgi?id=97701

The patch was successfully bootstrapped and tested on x86-64, arm64, 
ppc64be.

This patch variant is only for trunk.  GCC-10 branch will have a bit 
different patch.
diff mbox series

Patch

commit 449f17f23a7b8c4a340cc9342d68303ffa35cacc (HEAD -> master)
Author: Vladimir N. Makarov <vmakarov@redhat.com>
Date:   Fri Jan 29 11:51:44 2021 -0500

    [PR97701] LRA: Don't narrow class only for REG or MEM.
    
    Reload pseudos of ALL_REGS class did not narrow class from constraint
    in insn (set (pseudo) (lo_sum ...)) because lo_sum is considered an
    object (OBJECT_P) although the insn is not a classic move.  To permit
    narrowing we are starting to use MEM_P and REG_P instead of OBJECT_P.
    
    gcc/ChangeLog:
    
            PR target/97701
            * lra-constraints.c (in_class_p): Don't narrow class only for REG
            or MEM.
    
    gcc/testsuite/ChangeLog:
    
            PR target/97701
            * gcc.target/aarch64/pr97701.c: New.

diff --git a/gcc/lra-constraints.c b/gcc/lra-constraints.c
index d716ee48e51..e739a466a0d 100644
--- a/gcc/lra-constraints.c
+++ b/gcc/lra-constraints.c
@@ -250,6 +250,7 @@  in_class_p (rtx reg, enum reg_class cl, enum reg_class *new_class,
 {
   enum reg_class rclass, common_class;
   machine_mode reg_mode;
+  rtx src;
   int class_size, hard_regno, nregs, i, j;
   int regno = REGNO (reg);
 
@@ -265,6 +266,7 @@  in_class_p (rtx reg, enum reg_class cl, enum reg_class *new_class,
     }
   reg_mode = GET_MODE (reg);
   rclass = get_reg_class (regno);
+  src = curr_insn_set != NULL ? SET_SRC (curr_insn_set) : NULL;
   if (regno < new_regno_start
       /* Do not allow the constraints for reload instructions to
 	 influence the classes of new pseudos.  These reloads are
@@ -273,12 +275,10 @@  in_class_p (rtx reg, enum reg_class cl, enum reg_class *new_class,
 	 where other reload pseudos are no longer allocatable.  */
       || (!allow_all_reload_class_changes_p
 	  && INSN_UID (curr_insn) >= new_insn_uid_start
-	  && curr_insn_set != NULL
-	  && ((OBJECT_P (SET_SRC (curr_insn_set))
-	       && ! CONSTANT_P (SET_SRC (curr_insn_set)))
-	      || (GET_CODE (SET_SRC (curr_insn_set)) == SUBREG
-		  && OBJECT_P (SUBREG_REG (SET_SRC (curr_insn_set)))
-		  && ! CONSTANT_P (SUBREG_REG (SET_SRC (curr_insn_set)))))))
+	  && src != NULL
+	  && ((REG_P (src) || MEM_P (src))
+	      || (GET_CODE (src) == SUBREG
+		  && (REG_P (SUBREG_REG (src)) || MEM_P (SUBREG_REG (src)))))))
     /* When we don't know what class will be used finally for reload
        pseudos, we use ALL_REGS.  */
     return ((regno >= new_regno_start && rclass == ALL_REGS)
diff --git a/gcc/testsuite/gcc.target/aarch64/pr97701.c b/gcc/testsuite/gcc.target/aarch64/pr97701.c
new file mode 100644
index 00000000000..ede3540c48d
--- /dev/null
+++ b/gcc/testsuite/gcc.target/aarch64/pr97701.c
@@ -0,0 +1,17 @@ 
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+extern char a[][12][18][17][17];
+extern short b[][12][18][17][17];
+extern int c[][2][8][7];
+short *d;
+void e(signed f, int g, char h, char i, char j) {
+  for (int k = 648; k; k += f)
+    for (short l; l < j; l += 9)
+      for (long m = f + 6LL; m < (h ? h : i); m += 2)
+        for (int n = 0; n < 16; n += 3LL) {
+          for (int o = g; o; o++)
+            a[k][l][m][n][o] = b[k][l][m][n][o] = d[k] ? 2 : 0;
+          c[k][l][m][0] = 0;
+        }
+}