1/* PR target/36533 */ 2/* { dg-do run { target { { i?86-*-linux* x86_64-*-linux* } && ilp32 } } } */ 3/* { dg-options "-Os" } */ 4#include <string.h> 5#include <sys/mman.h> 6#ifndef MAP_ANONYMOUS 7#define MAP_ANONYMOUS MAP_ANON 8#endif 9 10typedef struct S1 11{ 12 unsigned long s1; 13 struct S1 *s2; 14 char *s3; 15} S1; 16 17typedef struct 18{ 19 unsigned int s4; 20 unsigned int s5; 21 int s6; 22 unsigned int *s7; 23} S2; 24 25typedef struct 26{ 27 unsigned int s8; 28 unsigned short s9; 29 unsigned char s10; 30 unsigned char s11; 31 char s12[255]; 32} S3; 33 34typedef struct 35{ 36 unsigned int s4; 37 unsigned short s13; 38 unsigned short s14; 39} S4; 40 41typedef struct 42{ 43 char s15[16]; 44 unsigned long s16; 45} S5; 46 47typedef struct 48{ 49 char s15[48]; 50 S5 *s17; 51} S6; 52 53typedef struct 54{ 55 S1 *s18; 56} S7; 57 58__attribute__((regparm (3), noinline)) int 59fn1 (const char *x, void *y, S1 *z) 60{ 61 asm volatile ("" : : : "memory"); 62 return *x + (y != 0); 63} 64 65__attribute__((regparm (3), noinline)) int 66fn2 (const char *x, int y, S2 *z) 67{ 68 asm volatile ("" : : : "memory"); 69 return 0; 70} 71 72static inline __attribute__ ((always_inline)) unsigned int 73fn4 (unsigned short x) 74{ 75 unsigned len = x; 76 if (len == ((1 << 16) - 1)) 77 return 1 << 16; 78 return len; 79} 80 81static inline __attribute__ ((always_inline)) S3 * 82fn3 (S3 *p) 83{ 84 return (S3 *) ((char *) p + fn4 (p->s9)); 85} 86 87__attribute__((regparm (3), noinline)) int 88fn5 (void) 89{ 90 asm volatile ("" : : : "memory"); 91 return 0; 92} 93 94static inline __attribute__ ((always_inline)) int 95fn6 (S3 *w, int x, S2 *y, S4 *z) 96{ 97 int a = 2; 98 char *b = (char *) w; 99 S2 c = *y; 100 101 while ((char *) w < b + x - 2 * sizeof (S4)) 102 { 103 if (w->s10 && w->s8) 104 { 105 fn2 (w->s12, w->s10, &c); 106 z--; 107 z->s4 = c.s4; 108 z->s13 = (unsigned short) ((char *) w - b); 109 z->s14 = w->s9; 110 a++; 111 fn5 (); 112 } 113 114 w = fn3 (w); 115 } 116 return a; 117} 118 119__attribute__((regparm (3), noinline)) unsigned int 120test (void *u, S6 *v, S1 **w, S7 *x, S2 *y, S1 *z) 121{ 122 unsigned b = v->s17->s16; 123 unsigned a; 124 S4 *c; 125 unsigned d, e, f, i; 126 127 fn1 (__func__, u, x->s18); 128 c = (S4 *) (z->s3 + b); 129 a = fn6 ((S3 *) (*w)->s3, b, y, c); 130 c -= a; 131 f = 0; 132 e = 2; 133 for (i = a - 1; ; i--) 134 { 135 if (f + (unsigned short) (c[i].s14 / 2) > b / 2) 136 break; 137 f += c[i].s14; 138 e++; 139 } 140 d = a - e; 141 return c[d].s4; 142} 143 144int main (void) 145{ 146 char *p = mmap (NULL, 131072, PROT_READ | PROT_WRITE, 147 MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 148 S1 wb, z, *w; 149 S6 v; 150 S7 x; 151 S2 y; 152 S5 vb; 153 S4 s4; 154 if (p == MAP_FAILED) 155 return 0; 156 if (munmap (p + 65536, 65536) < 0) 157 return 0; 158 memset (&wb, 0, sizeof (wb)); 159 memset (&z, 0, sizeof (z)); 160 memset (&v, 0, sizeof (v)); 161 memset (&x, 0, sizeof (x)); 162 memset (&y, 0, sizeof (y)); 163 memset (&vb, 0, sizeof (vb)); 164 memset (&s4, 0, sizeof (s4)); 165 s4.s14 = 254; 166 z.s3 = p + 65536 - 2 * sizeof (S4); 167 w = &wb; 168 v.s17 = &vb; 169 vb.s16 = 2 * sizeof (S4); 170 memcpy (z.s3, &s4, sizeof (s4)); 171 memcpy (z.s3 + sizeof (s4), &s4, sizeof (s4)); 172 test ((void *) 0, &v, &w, &x, &y, &z); 173 return 0; 174} 175