blob: b69114d1e531ee2be1fa15f70d07e2b4cc258166 [file] [log] [blame]
Andrew Geissler82c905d2020-04-13 13:39:40 -05001From e75bcc2ec4f1e7e081ce18713f0a25913ba15340 Mon Sep 17 00:00:00 2001
2From: Vladimir Makarov <vmakarov@redhat.com>
3Date: Wed, 10 Jul 2019 16:07:10 +0000
4Subject: [PATCH 39/39] process_alt_operands: Don't match user defined regs
5 only if they are early clobbers
6
7PR target/91102 (aarch64 ICE on Linux kernel with -Os starting with r270266)
8
92019-07-10 Vladimir Makarov <vmakarov@redhat.com>
10
11 PR target/91102
12 * lra-constraints.c (process_alt_operands): Don't match user
13 defined regs only if they are early clobbers.
14
152019-07-10 Vladimir Makarov <vmakarov@redhat.com>
16
17 PR target/91102
18 * gcc.target/aarch64/pr91102.c: New test.
19
20From-SVN: r273357
21Upstream-Status: Backport [https://github.com/gcc-mirror/gcc/commit/613caed2feb9cfc8158308670b59df3d031ec629]
22[takondra: dropped conflicting ChangeLog changes]
23Signed-off-by: Taras Kondratiuk <takondra@cisco.com>
24---
25 gcc/lra-constraints.c | 17 ++++++++++----
26 gcc/testsuite/gcc.target/aarch64/pr91102.c | 26 ++++++++++++++++++++++
27 2 files changed, 39 insertions(+), 4 deletions(-)
28 create mode 100644 gcc/testsuite/gcc.target/aarch64/pr91102.c
29
30diff --git a/gcc/lra-constraints.c b/gcc/lra-constraints.c
31index cf33da8013e..6382dbf852b 100644
32--- a/gcc/lra-constraints.c
33+++ b/gcc/lra-constraints.c
34@@ -2172,8 +2172,9 @@ process_alt_operands (int only_alternative)
35 else
36 {
37 /* Operands don't match. If the operands are
38- different user defined explicit hard registers,
39- then we cannot make them match. */
40+ different user defined explicit hard
41+ registers, then we cannot make them match
42+ when one is early clobber operand. */
43 if ((REG_P (*curr_id->operand_loc[nop])
44 || SUBREG_P (*curr_id->operand_loc[nop]))
45 && (REG_P (*curr_id->operand_loc[m])
46@@ -2192,9 +2193,17 @@ process_alt_operands (int only_alternative)
47 && REG_P (m_reg)
48 && HARD_REGISTER_P (m_reg)
49 && REG_USERVAR_P (m_reg))
50- break;
51+ {
52+ int i;
53+
54+ for (i = 0; i < early_clobbered_regs_num; i++)
55+ if (m == early_clobbered_nops[i])
56+ break;
57+ if (i < early_clobbered_regs_num
58+ || early_clobber_p)
59+ break;
60+ }
61 }
62-
63 /* Both operands must allow a reload register,
64 otherwise we cannot make them match. */
65 if (curr_alt[m] == NO_REGS)
66diff --git a/gcc/testsuite/gcc.target/aarch64/pr91102.c b/gcc/testsuite/gcc.target/aarch64/pr91102.c
67new file mode 100644
68index 00000000000..70b99045a48
69--- /dev/null
70+++ b/gcc/testsuite/gcc.target/aarch64/pr91102.c
71@@ -0,0 +1,26 @@
72+/* PR target/91102 */
73+/* { dg-do compile } */
74+/* { dg-options "-O2" } */
75+
76+int
77+foo (long d, long l)
78+{
79+ register long e asm ("x1") = d;
80+ register long f asm("x2") = l;
81+ asm ("" : : "r" (e), "r" (f));
82+ return 3;
83+}
84+
85+struct T { int i; int j; };
86+union S { long h; struct T t; };
87+
88+void
89+bar (union S b)
90+{
91+ while (1)
92+ {
93+ union S c = b;
94+ c.t.j++;
95+ b.h = foo (b.h, c.h);
96+ }
97+}
98--
992.25.1
100