1 // { dg-do run  }
2 // { dg-options "-fno-strict-aliasing" }
3 // Test various aspects of vtable layout.
4 // Origin: Mark Mitchell <mark@codesourcery.com>
5 
6 #if defined (__GXX_ABI_VERSION) && __GXX_ABI_VERSION >= 100
7 
8 struct S0
9 {
hS010   virtual void h ()
11   {
12   }
13 
14   int k;
15 };
16 
17 
18 struct S1
19 {
fS120   virtual void f ()
21   {
22   }
23 
24   int i;
25 };
26 
27 struct S2 : virtual public S0
28 {
gS229   virtual void g ()
30   {
31   }
32 
33   int j;
34 };
35 
36 struct S3
37 {
kS338   virtual void k ()
39   {
40   }
41 
42   int l;
43 };
44 
45 struct S4 : public virtual S1, public S2, public S3
46 {
47 };
48 
vtable(void * object)49 inline void* vtable (void *object)
50 {
51   // The vptr is always the first part of the object.
52   return * (void **) object;
53 }
54 
main()55 int main ()
56 {
57   // The vtable layout order for S4 should consist of S4's primary
58   // vtable (shared with S2), followed by the vtable for S3 (because
59   // it is a non-virtual base).  Then, these should be followed by the
60   // the vtables for S1 and S0, which are virtual.
61   S4 s4;
62   S0 *s0 = &s4;
63   S1 *s1 = &s4;
64   S2 *s2 = &s4;
65   S3 *s3 = &s4;
66 
67   if (vtable (&s4) != vtable (s2))
68     return 1;
69   if (vtable (s2) >= vtable (s3))
70     return 2;
71   if (vtable (s3) >= vtable (s1))
72     return 3;
73   if (vtable (s1) >= vtable (s0))
74     return 4;
75 }
76 
77 #else /* !(defined (__GXX_ABI_VERSION) && __GXX_ABI_VERSION >= 100) */
78 
main()79 int main ()
80 {
81 }
82 
83 #endif /* !(defined (__GXX_ABI_VERSION) && __GXX_ABI_VERSION >= 100) */
84