1 /* PR rtl-optimization/9771 */
2 /* { dg-do run } */
3 /* { dg-require-effective-target ia32 } */
4 /* { dg-options "-O2 -fomit-frame-pointer -ffixed-ebp" } */
5 
6 extern void abort(void);
7 extern void exit(int);
8 
9 register long *B asm ("ebp");
10 
11 long x = 10;
12 long y = 20;
13 
bar(void)14 void bar(void)
15 {
16   B = &y;
17 }
18 
foo()19 void foo()
20 {
21   long *adr = B;
22   long save = *adr;
23 
24   *adr = 123;
25 
26   bar();
27 
28   *adr = save;
29 }
30 
31 /* This must not be inlined because main() requires the frame pointer
32    for stack alignment.  */
33 void test(void) __attribute__((noinline));
test(void)34 void test(void)
35 {
36   B = &x;
37 
38   foo();
39 
40   if (x != 10 || y != 20)
41     abort();
42 
43   /* We can't return, as our caller may assume %ebp is preserved!  */
44   /* We could save/restore it (like foo), but its easier to exit.  */
45   exit(0);
46 }
47 
48 /* main usually performs dynamic realignment of the stack in case
49    _start would fail to properly align the stack, but for dynamic
50    stack realignment we need frame pointer which is incompatible
51    with -ffixed-ebp and the global register var.  So, cheat here
52    and hide from the compiler that main is really main.  */
53 #define ASMNAME(cname)  ASMNAME2 (__USER_LABEL_PREFIX__, cname)
54 #define ASMNAME2(prefix, cname) STRING (prefix) cname
55 #define STRING(x)    #x
56 int real_main() __asm (ASMNAME ("main"));
57 
real_main()58 int real_main()
59 {
60   test();
61   return 0;
62 
63 }
64