111
|
1 /* { dg-options "-O2 -fno-inline-functions" } */
|
|
2 /* { dg-do run } */
|
|
3
|
|
4 /* Gimplification problem exposed by zsh. All the side-effects in
|
|
5 function arguments and in the called expression should happen
|
|
6 before the actual function call. */
|
|
7 extern void abort (void);
|
|
8 int A;
|
|
9
|
|
10 typedef void (*fnptr) (void);
|
|
11 fnptr *F;
|
|
12
|
|
13 void
|
|
14 foo (int x)
|
|
15 {
|
|
16 if (A == x)
|
|
17 abort ();
|
|
18 }
|
|
19
|
|
20 void
|
|
21 bar (int x, int y)
|
|
22 {
|
|
23 if (x == 5 || y != 3)
|
|
24 abort ();
|
|
25 }
|
|
26
|
|
27 void
|
|
28 boz (void)
|
|
29 {
|
|
30 abort ();
|
|
31 }
|
|
32
|
|
33 void
|
|
34 baz (void)
|
|
35 {
|
|
36 if (*F != boz)
|
|
37 abort ();
|
|
38 }
|
|
39
|
|
40 fnptr B[2] = { baz, boz };
|
|
41
|
|
42 int
|
|
43 main ()
|
|
44 {
|
|
45 int b, c;
|
|
46
|
|
47 /* The gimplifier was emitting A++ after the call to foo. */
|
|
48 A = 5;
|
|
49 foo (A++);
|
|
50
|
|
51 /* The increment to 'b' and 'c' must happen before the call. However,
|
|
52 the first argument to bar() must be the original value of 'b', while
|
|
53 the second argument must be the new value of 'c'. */
|
|
54 b = 4;
|
|
55 c = 2;
|
|
56 bar (b++, ++c);
|
|
57
|
|
58 /* This call via function pointer *F should go to baz, but F should
|
|
59 be incremented before the actual call (i.e., right before the
|
|
60 call F should be pointing to boz). */
|
|
61 F = &B[0];
|
|
62 (*F++) ();
|
|
63
|
|
64 return 0;
|
|
65 }
|