re PR rtl-optimization/69691 (wrong code at -O2 on x86_64-linux-gnu)
authorJakub Jelinek <jakub@redhat.com>
Fri, 5 Feb 2016 21:13:43 +0000 (22:13 +0100)
committerJakub Jelinek <jakub@gcc.gnu.org>
Fri, 5 Feb 2016 21:13:43 +0000 (22:13 +0100)
PR rtl-optimization/69691
* lra-eliminations.c (move_plus_up): Don't add the addend twice.

* gcc.c-torture/execute/pr69691.c: New test.

From-SVN: r233187

gcc/ChangeLog
gcc/lra-eliminations.c
gcc/testsuite/ChangeLog
gcc/testsuite/gcc.c-torture/execute/pr69691.c [new file with mode: 0644]

index 1e166ae60d14fec05e85ca83a3f4528cb741b7db..5ad69839f8892f7050c78914480ed22f1ea84600 100644 (file)
@@ -1,3 +1,8 @@
+2016-02-05  Jakub Jelinek  <jakub@redhat.com>
+
+       PR rtl-optimization/69691
+       * lra-eliminations.c (move_plus_up): Don't add the addend twice.
+
 2016-02-05  Pat Haugen  <pthaugen@us.ibm.com>
 
        * config/rs6000/crypto.md (crypto_vpermxor_<mode>): Correct insn type.
index 1494263c06f80a52b9ce42a644ec46ab06e9dd77..9ae5cfea5ab8d3faa0f9517bb59bd4d4836a0010 100644 (file)
@@ -303,7 +303,8 @@ move_plus_up (rtx x)
                                 subreg_lowpart_offset (x_mode,
                                                        subreg_reg_mode));
       if (cst && CONSTANT_P (cst))
-       return gen_rtx_PLUS (x_mode, lowpart_subreg (x_mode, subreg_reg,
+       return gen_rtx_PLUS (x_mode, lowpart_subreg (x_mode,
+                                                    XEXP (subreg_reg, 0),
                                                     subreg_reg_mode), cst);
     }
   return x;
index 7876edab43596dac14c6c2e795e4c2bb738a6085..abd315653795b6271b14daa0dcd94bc27d4b66a7 100644 (file)
@@ -1,5 +1,8 @@
 2016-02-05  Jakub Jelinek  <jakub@redhat.com>
 
+       PR rtl-optimization/69691
+       * gcc.c-torture/execute/pr69691.c: New test.
+
        PR c++/69628
        * g++.dg/parse/pr69628.C: New test.
 
diff --git a/gcc/testsuite/gcc.c-torture/execute/pr69691.c b/gcc/testsuite/gcc.c-torture/execute/pr69691.c
new file mode 100644 (file)
index 0000000..16b5556
--- /dev/null
@@ -0,0 +1,127 @@
+/* PR rtl-optimization/69691 */
+
+char u[] = { 46, 97, 99, 104, 52, 0 };
+char *v[] = { u, 0 };
+struct S { char a[10]; struct S *b[31]; };
+struct S r[7], *r2 = r;
+static struct S *w = 0;
+
+__attribute__((noinline, noclone)) int
+fn (int x)
+{
+  if (__builtin_strchr (u, x) || x == 96)
+    return x;
+  __builtin_abort ();
+}
+
+__attribute__((noinline, noclone)) int
+foo (char x)
+{
+  if (x == 0)
+    __builtin_abort ();
+  if (fn (x) >= 96 && fn (x) <= 122)
+    return (fn (x) - 96);
+  else if (x == 46)
+    return 0;
+  else
+    {
+      __builtin_printf ("foo %d\n", x);
+      return -1;
+    }
+}
+
+__attribute__((noinline, noclone)) void
+bar (char **x)
+{
+  char **b, c, *d, e[500], *f, g[10];
+  int z, l, h, i;
+  struct S *s;
+
+  w = r2++;
+  for (b = x; *b; b++)
+    {
+      __builtin_strcpy (e, *b);
+      f = e;
+      do
+       {
+         d = __builtin_strchr (f, 32);
+         if (d)
+           *d = 0;
+         l = __builtin_strlen (f);
+         h = 0;
+         s = w;
+         __builtin_memset (g, 0, sizeof (g));
+         for (z = 0; z < l; z++)
+           {
+             c = f[z];
+             if (c >= 48 && c <= 57)
+               g[h] = c - 48;
+             else
+               {
+                 i = foo (c);
+                 if (!s->b[i])
+                   {
+                     s->b[i] = r2++;
+                     if (r2 == &r[7])
+                       __builtin_abort ();
+                   }
+                 s = s->b[i];
+                 h++;
+               }
+           }
+         __builtin_memcpy (s->a, g, 10);
+         if (d)
+           f = d + 1;
+       }
+      while (d);
+    }
+}
+
+__attribute__((noinline, noclone)) void
+baz (char *x)
+{
+  char a[300], b[300];
+  int z, y, t, l;
+  struct S *s;
+
+  l = __builtin_strlen (x);
+  *a = 96;
+  for (z = 0; z < l; z++)
+    {
+      a[z + 1] = fn ((unsigned int) x[z]);
+      if (foo (a[z + 1]) <= 0)
+       return;
+    }
+  a[l + 1] = 96;
+  l += 2;
+  __builtin_memset (b, 0, l + 2);
+
+  if (!w)
+    return;
+
+  for (z = 0; z < l; z++)
+    {
+      s = w;
+      for (y = z; y < l; y++)
+       {
+         s = s->b[foo (a[y])];
+         if (!s)
+           break;
+         for (t = 0; t <= y - z + 2; t++)
+           if (s->a[t] > b[z + t])
+             b[z + t] = s->a[t];
+       }
+    }
+  for (z = 3; z < l - 2; z++)
+    if ((b[z] & 1) == 1)
+     asm ("");
+}
+
+int
+main ()
+{
+  bar (v);
+  char c[] = { 97, 97, 97, 97, 97, 0 };
+  baz (c);
+  return 0;
+}