diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index c59a7a13847..321c87e2787 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2016-03-02 Jakub Jelinek + + PR middle-end/70025 + * gcc.dg/torture/pr70025.c: New test. + 2016-03-02 Venkataramanan Kumar PR tree-optimization/68621 diff --git a/gcc/testsuite/gcc.dg/torture/pr70025.c b/gcc/testsuite/gcc.dg/torture/pr70025.c new file mode 100644 index 00000000000..dafae0b777e --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/pr70025.c @@ -0,0 +1,81 @@ +/* PR middle-end/70025 */ +/* { dg-do run } */ +/* { dg-additional-options "-mtune=z10" { target s390*-*-* } } */ + +typedef char (*F) (unsigned long, void *); +typedef union { struct A { char a1, a2, a3, a4; unsigned long a5; F a6; void *a7; } b; char c[1]; } B; +struct C { const char *c1; unsigned long c2; }; +typedef struct D { unsigned long d1; int d2; const char *d3; unsigned long d4, d5; struct C d6[49]; char d7[8]; } E[1]; + +__attribute__ ((noinline, noclone)) +void foo (register E p) +{ + asm volatile ("" : : "r" (p) : "memory"); +} + +__attribute__ ((noinline, noclone)) +void bar (register E p) +{ + register unsigned long k = p[0].d1 + 1; + register struct C *l = &p[0].d6[p[0].d2]; + register const char *m = l->c1; + p[0].d1 = k; + if (*m == '\0') + { + register struct A *f = &((B *) m)->b; + register unsigned long n = l->c2; + register unsigned long o = n + f->a5; + if (k < o) + { + register unsigned long i; + register unsigned long q = k + 8; + register F a6 = f->a6; + register void *a7 = f->a7; + if (q > o) + q = o; + for (i = k; i < q; i++) + p[0].d7[i - k] = (*a6) (i - n, a7); + p[0].d4 = k; + p[0].d3 = p[0].d7; + p[0].d5 = q; + return; + } + } + while (p[0].d2 > 0 && l[0].c2 != l[-1].c2) + { + p[0].d2--; + l--; + } + if (p[0].d2 == 0) + { + p[0].d2 = 0x55555555; + return; + } + p[0].d2--; + foo (p); +} + +char +baz (unsigned long i, void *j) +{ + if (j != 0) + __builtin_abort (); + return (char) i; +} + +int +main () +{ + struct D p; + struct A f; + __builtin_memset (&f, 0, sizeof (f)); + f.a2 = 4; + f.a5 = 13; + f.a6 = baz; + __builtin_memset (&p, 0, sizeof (p)); + p.d6[0].c1 = (const char *) &f; + bar (&p); + if (p.d4 != 1 || p.d5 != 9 || p.d3 != p.d7) + __builtin_abort (); + return 0; +}