]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
aarch64: Fix condition accepted by mov<GPF>cc
authorKarl Meakin <karl.meakin@arm.com>
Tue, 30 Sep 2025 12:05:00 +0000 (12:05 +0000)
committerAndrew Pinski <andrew.pinski@oss.qualcomm.com>
Sat, 15 Nov 2025 05:15:53 +0000 (21:15 -0800)
Apply the same fix from bc11cbff9e648fdda2798bfa2d7151d5cd164b87
("aarch64: Fix condition accepted by mov<ALLI>cc") to `MOV<GPF>cc`.
Fixes ICEs when compiling code such as `cmpbr-4.c` and `cmpbr-5.c` with `+cmpbr`.

gcc/ChangeLog:

* config/aarch64/aarch64.md(mov<GPF>cc): Accept MODE_CC
conditions directly; reject QI/HImode conditions.

gcc/testsuite/ChangeLog:

* gcc.target/aarch64/cmpbr-4.c: New test.
* gcc.target/aarch64/cmpbr-5.c: New test.

gcc/config/aarch64/aarch64.md
gcc/testsuite/gcc.target/aarch64/cmpbr-4.c [new file with mode: 0644]
gcc/testsuite/gcc.target/aarch64/cmpbr-5.c [new file with mode: 0644]

index 98c65a74c8ed113dcfa1601fc18393c203b04c1c..e2b8d5d3af969d70f6fbf70e7b4d969cf62a046b 100644 (file)
                          (match_operand:GPF 3 "register_operand")))]
   ""
   {
-    rtx ccreg;
     enum rtx_code code = GET_CODE (operands[1]);
-
     if (code == UNEQ || code == LTGT)
       FAIL;
 
-    ccreg = aarch64_gen_compare_reg (code, XEXP (operands[1], 0),
-                                 XEXP (operands[1], 1));
-    operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+    rtx ccreg = XEXP (operands[1], 0);
+    enum machine_mode ccmode = GET_MODE (ccreg);
+    if (GET_MODE_CLASS (ccmode) == MODE_CC)
+      gcc_assert (XEXP (operands[1], 1) == const0_rtx);
+    else if (ccmode == QImode || ccmode == HImode)
+      FAIL;
+    else
+      {
+       ccreg = aarch64_gen_compare_reg (code, ccreg, XEXP (operands[1], 1));
+       operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+      }
   }
 )
 
                          (match_operand:GPF 3 "register_operand")))]
   ""
   {
-    rtx ccreg;
     enum rtx_code code = GET_CODE (operands[1]);
-
     if (code == UNEQ || code == LTGT)
       FAIL;
 
-    ccreg = aarch64_gen_compare_reg (code, XEXP (operands[1], 0),
-                                 XEXP (operands[1], 1));
-    operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+    rtx ccreg = XEXP (operands[1], 0);
+    enum machine_mode ccmode = GET_MODE (ccreg);
+    if (GET_MODE_CLASS (ccmode) == MODE_CC)
+      gcc_assert (XEXP (operands[1], 1) == const0_rtx);
+    else if (ccmode == QImode || ccmode == HImode)
+      FAIL;
+    else
+      {
+       ccreg = aarch64_gen_compare_reg (code, ccreg, XEXP (operands[1], 1));
+       operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+      }
   }
 )
 
                          (match_operand:GPI 3 "register_operand")))]
   ""
   {
-    rtx ccreg;
     enum rtx_code code = GET_CODE (operands[1]);
-
     if (code == UNEQ || code == LTGT)
       FAIL;
 
-    ccreg = aarch64_gen_compare_reg (code, XEXP (operands[1], 0),
-                                     XEXP (operands[1], 1));
-    operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+    rtx ccreg = XEXP (operands[1], 0);
+    enum machine_mode ccmode = GET_MODE (ccreg);
+    if (GET_MODE_CLASS (ccmode) == MODE_CC)
+      gcc_assert (XEXP (operands[1], 1) == const0_rtx);
+    else if (ccmode == QImode || ccmode == HImode)
+      FAIL;
+    else
+      {
+       ccreg = aarch64_gen_compare_reg (code, ccreg, XEXP (operands[1], 1));
+       operands[1] = gen_rtx_fmt_ee (code, VOIDmode, ccreg, const0_rtx);
+      }
   }
 )
 
diff --git a/gcc/testsuite/gcc.target/aarch64/cmpbr-4.c b/gcc/testsuite/gcc.target/aarch64/cmpbr-4.c
new file mode 100644 (file)
index 0000000..e266ce1
--- /dev/null
@@ -0,0 +1,12 @@
+// { dg-do compile }
+// { dg-options "-O2" }
+
+#pragma GCC target "+cmpbr"
+
+typedef unsigned short Quantum;
+
+double MagickMax(double x, double y) { return x > y ? x : y; }
+
+void ConvertRGBToHCL(Quantum red, Quantum green) {
+    if (red == MagickMax(red, green)) __builtin_abort();
+}
diff --git a/gcc/testsuite/gcc.target/aarch64/cmpbr-5.c b/gcc/testsuite/gcc.target/aarch64/cmpbr-5.c
new file mode 100644 (file)
index 0000000..049e8c1
--- /dev/null
@@ -0,0 +1,13 @@
+/* { dg-do compile } */
+/* { dg-options "-fgimple -O1" } */
+#pragma GCC target "+cmpbr"
+typedef unsigned short us;
+__GIMPLE double
+f (us x, us y, double a, double b)
+{
+  bool c;
+  double d;
+  c = x == y;
+  d = c ? a : b;
+  return d;
+}