1*67e74705SXin Li // RUN: %clang_cc1 %s -fno-rtti -triple=i386-pc-win32 -emit-llvm -o %t.ll -fdump-vtable-layouts >%t
2*67e74705SXin Li // RUN: FileCheck %s < %t
3*67e74705SXin Li 
4*67e74705SXin Li struct A {
5*67e74705SXin Li   virtual ~A();
6*67e74705SXin Li   virtual void z1();
7*67e74705SXin Li };
8*67e74705SXin Li 
9*67e74705SXin Li struct B {
10*67e74705SXin Li   virtual ~B();
11*67e74705SXin Li };
12*67e74705SXin Li 
13*67e74705SXin Li struct C : A, B {
14*67e74705SXin Li   // CHECK-LABEL: VFTable for 'A' in 'C' (2 entries).
15*67e74705SXin Li   // CHECK-NEXT:   0 | C::~C() [scalar deleting]
16*67e74705SXin Li   // CHECK-NEXT:   1 | void A::z1()
17*67e74705SXin Li 
18*67e74705SXin Li   // CHECK-LABEL: VFTable for 'B' in 'C' (1 entry).
19*67e74705SXin Li   // CHECK-NEXT:   0 | C::~C() [scalar deleting]
20*67e74705SXin Li   // CHECK-NEXT:       [this adjustment: -4 non-virtual]
21*67e74705SXin Li 
22*67e74705SXin Li   // CHECK-LABEL: Thunks for 'C::~C()' (1 entry).
23*67e74705SXin Li   // CHECK-NEXT:   0 | [this adjustment: -4 non-virtual]
24*67e74705SXin Li 
25*67e74705SXin Li   // CHECK-LABEL: VFTable indices for 'C' (1 entry).
26*67e74705SXin Li   // CHECK-NEXT:   0 | C::~C() [scalar deleting]
27*67e74705SXin Li   virtual ~C();
28*67e74705SXin Li };
29*67e74705SXin Li 
build_vftable(C * obj)30*67e74705SXin Li void build_vftable(C *obj) { delete obj; }
31*67e74705SXin Li 
32*67e74705SXin Li struct D {
33*67e74705SXin Li   // No virtual destructor here!
34*67e74705SXin Li   virtual void z4();
35*67e74705SXin Li };
36*67e74705SXin Li 
37*67e74705SXin Li struct E : D, B {
38*67e74705SXin Li   // Implicit virtual dtor here!
39*67e74705SXin Li 
40*67e74705SXin Li   // CHECK-LABEL: VFTable for 'D' in 'E' (1 entry).
41*67e74705SXin Li   // CHECK-NEXT:   0 | void D::z4()
42*67e74705SXin Li 
43*67e74705SXin Li   // CHECK-LABEL: VFTable for 'B' in 'E' (1 entry).
44*67e74705SXin Li   // CHECK-NEXT:   0 | E::~E() [scalar deleting]
45*67e74705SXin Li   // CHECK-NEXT:       [this adjustment: -4 non-virtual]
46*67e74705SXin Li 
47*67e74705SXin Li   // CHECK-LABEL: Thunks for 'E::~E()' (1 entry).
48*67e74705SXin Li   // CHECK-NEXT:   0 | [this adjustment: -4 non-virtual]
49*67e74705SXin Li 
50*67e74705SXin Li   // CHECK-LABEL: VFTable indices for 'E' (1 entry).
51*67e74705SXin Li   // CHECK-NEXT:   -- accessible via vfptr at offset 4 --
52*67e74705SXin Li   // CHECK-NEXT:   0 | E::~E() [scalar deleting]
53*67e74705SXin Li };
54*67e74705SXin Li 
build_vftable(E * obj)55*67e74705SXin Li void build_vftable(E *obj) { delete obj; }
56*67e74705SXin Li 
57*67e74705SXin Li struct F : D, B {
58*67e74705SXin Li   // Implicit virtual dtor here!
59*67e74705SXin Li 
60*67e74705SXin Li   // CHECK-LABEL: VFTable for 'D' in 'F' (1 entry).
61*67e74705SXin Li   // CHECK-NEXT:   0 | void D::z4()
62*67e74705SXin Li 
63*67e74705SXin Li   // CHECK-LABEL: VFTable for 'B' in 'F' (1 entry).
64*67e74705SXin Li   // CHECK-NEXT:   0 | F::~F() [scalar deleting]
65*67e74705SXin Li   // CHECK-NEXT:       [this adjustment: -4 non-virtual]
66*67e74705SXin Li 
67*67e74705SXin Li   // CHECK-LABEL: Thunks for 'F::~F()' (1 entry).
68*67e74705SXin Li   // CHECK-NEXT:   0 | [this adjustment: -4 non-virtual]
69*67e74705SXin Li 
70*67e74705SXin Li   // CHECK-LABEL: VFTable indices for 'F' (1 entry).
71*67e74705SXin Li   // CHECK-NEXT:   -- accessible via vfptr at offset 4 --
72*67e74705SXin Li   // CHECK-NEXT:   0 | F::~F() [scalar deleting]
73*67e74705SXin Li };
74*67e74705SXin Li 
build_vftable(F * obj)75*67e74705SXin Li void build_vftable(F *obj) { delete obj; }
76*67e74705SXin Li 
77*67e74705SXin Li struct G : F {
78*67e74705SXin Li   // CHECK-LABEL: VFTable for 'D' in 'F' in 'G' (1 entry).
79*67e74705SXin Li   // CHECK-NEXT:   0 | void D::z4()
80*67e74705SXin Li 
81*67e74705SXin Li   // CHECK-LABEL: VFTable for 'B' in 'F' in 'G' (1 entry).
82*67e74705SXin Li   // CHECK-NEXT:   0 | G::~G() [scalar deleting]
83*67e74705SXin Li   // CHECK-NEXT:       [this adjustment: -4 non-virtual]
84*67e74705SXin Li 
85*67e74705SXin Li   // CHECK-LABEL: Thunks for 'G::~G()' (1 entry).
86*67e74705SXin Li   // CHECK-NEXT:   0 | [this adjustment: -4 non-virtual]
87*67e74705SXin Li 
88*67e74705SXin Li   // CHECK-LABEL: VFTable indices for 'G' (1 entry).
89*67e74705SXin Li   // CHECK-NEXT:   -- accessible via vfptr at offset 4 --
90*67e74705SXin Li   // CHECK-NEXT:   0 | G::~G() [scalar deleting]
91*67e74705SXin Li   virtual ~G();
92*67e74705SXin Li };
93*67e74705SXin Li 
build_vftable(G * obj)94*67e74705SXin Li void build_vftable(G *obj) { delete obj; }
95