aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2020-04-07 00:27:10 +0200
committerJakub Jelinek <jakub@redhat.com>2020-04-07 00:27:10 +0200
commit8662d0593438ecd498ab7591ad0d2810886eb6da (patch)
treed872bb10743b0bcf082839852c8a36a7342f1141 /gcc
parente0fd9ce257c9033d885d9393bc4dc07da1eab16e (diff)
downloadgcc-8662d0593438ecd498ab7591ad0d2810886eb6da.zip
gcc-8662d0593438ecd498ab7591ad0d2810886eb6da.tar.gz
gcc-8662d0593438ecd498ab7591ad0d2810886eb6da.tar.bz2
cselib: Fix endless cselib loop on (plus:P (reg) (const_int 0))
getopt.c hangs the compiler on h8300-elf with -O2 -g, because the IL contains addition of constant 0, the first PLUS operand is determined to have the SP_DERIVED_VALUE_P and the new code in cselib recurses indefinitely on seeing SP_DERIVED_VALUE_P with locs of (plus:P SP_DERIVED_VALUE_P (const_int 0)). Fixed by making sure cselib_subst_to_values canonicalizes it, hashing already hashes it the same too. 2020-04-06 Jakub Jelinek <jakub@redhat.com> * cselib.c (cselib_subst_to_values): For SP_DERIVED_VALUE_P + const0_rtx return the SP_DERIVED_VALUE_P.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog5
-rw-r--r--gcc/cselib.c18
2 files changed, 16 insertions, 7 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 258e9db..4070732 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,8 @@
+2020-04-06 Jakub Jelinek <jakub@redhat.com>
+
+ * cselib.c (cselib_subst_to_values): For SP_DERIVED_VALUE_P
+ + const0_rtx return the SP_DERIVED_VALUE_P.
+
2020-04-06 Richard Sandiford <richard.sandiford@arm.com>
PR rtl-optimization/92989
diff --git a/gcc/cselib.c b/gcc/cselib.c
index 256bd78..69c9ca5 100644
--- a/gcc/cselib.c
+++ b/gcc/cselib.c
@@ -2090,13 +2090,17 @@ cselib_subst_to_values (rtx x, machine_mode memmode)
{
rtx t = cselib_subst_to_values (XEXP (x, 0), memmode);
if (GET_CODE (t) == VALUE)
- for (struct elt_loc_list *l = CSELIB_VAL_PTR (t)->locs;
- l; l = l->next)
- if (GET_CODE (l->loc) == PLUS
- && GET_CODE (XEXP (l->loc, 0)) == VALUE
- && SP_DERIVED_VALUE_P (XEXP (l->loc, 0))
- && CONST_INT_P (XEXP (l->loc, 1)))
- return plus_constant (Pmode, l->loc, INTVAL (XEXP (x, 1)));
+ {
+ if (SP_DERIVED_VALUE_P (t) && XEXP (x, 1) == const0_rtx)
+ return t;
+ for (struct elt_loc_list *l = CSELIB_VAL_PTR (t)->locs;
+ l; l = l->next)
+ if (GET_CODE (l->loc) == PLUS
+ && GET_CODE (XEXP (l->loc, 0)) == VALUE
+ && SP_DERIVED_VALUE_P (XEXP (l->loc, 0))
+ && CONST_INT_P (XEXP (l->loc, 1)))
+ return plus_constant (Pmode, l->loc, INTVAL (XEXP (x, 1)));
+ }
if (t != XEXP (x, 0))
{
copy = shallow_copy_rtx (x);