1 // RUN: %clang_cc1 -fno-rtti -emit-llvm %s -o - -cxx-abi microsoft -triple=i386-pc-win32 >%t 2>&1 2 // RUN: FileCheck --check-prefix=MANGLING %s < %t 3 // RUN: FileCheck --check-prefix=XMANGLING %s < %t 4 // RUN: FileCheck --check-prefix=CODEGEN %s < %t 5 // RUN: %clang_cc1 -fno-rtti -emit-llvm %s -o - -cxx-abi microsoft -triple=x86_64-pc-win32 2>&1 | FileCheck --check-prefix=MANGLING-X64 %s 6 7 void foo(void *); 8 9 struct A { 10 virtual ~A(); 11 virtual void public_f(); 12 // Make sure we don't emit unneeded thunks: 13 // XMANGLING-NOT: @"\01?public_f@A@@QAEXXZ" 14 protected: 15 virtual void protected_f(); 16 private: 17 virtual void private_f(); 18 }; 19 20 struct B { 21 virtual ~B(); 22 virtual void public_f(); 23 protected: 24 virtual void protected_f(); 25 private: 26 virtual void private_f(); 27 }; 28 29 30 struct C : A, B { 31 C(); 32 33 virtual ~C(); 34 // MANGLING-DAG: @"\01??1C@@UAE@XZ" 35 // MANGLING-DAG: @"\01??_GC@@UAEPAXI@Z" 36 // MANGLING-DAG: @"\01??_EC@@W3AEPAXI@Z" 37 // MANGLING-X64-DAG: @"\01??1C@@UEAA@XZ" 38 // MANGLING-X64-DAG: @"\01??_GC@@UEAAPEAXI@Z" 39 // MANGLING-X64-DAG: @"\01??_EC@@W7EAAPEAXI@Z" 40 41 // Overrides public_f() of two subobjects with distinct vfptrs, thus needs a thunk. 42 virtual void public_f(); 43 // MANGLING-DAG: @"\01?public_f@C@@UAEXXZ" 44 // MANGLING-DAG: @"\01?public_f@C@@W3AEXXZ" 45 // MANGLING-X64-DAG: @"\01?public_f@C@@UEAAXXZ" 46 // MANGLING-X64-DAG: @"\01?public_f@C@@W7EAAXXZ" 47 protected: 48 virtual void protected_f(); 49 // MANGLING-DAG: @"\01?protected_f@C@@MAEXXZ" 50 // MANGLING-DAG: @"\01?protected_f@C@@O3AEXXZ" 51 // MANGLING-X64-DAG: @"\01?protected_f@C@@MEAAXXZ" 52 // MANGLING-X64-DAG: @"\01?protected_f@C@@O7EAAXXZ" 53 54 private: 55 virtual void private_f(); 56 // MANGLING-DAG: @"\01?private_f@C@@EAEXXZ" 57 // MANGLING-DAG: @"\01?private_f@C@@G3AEXXZ" 58 // MANGLING-X64-DAG: @"\01?private_f@C@@EEAAXXZ" 59 // MANGLING-X64-DAG: @"\01?private_f@C@@G7EAAXXZ" 60 }; 61 62 C::C() {} // Emits vftable and forces thunk generation. 63 64 // CODEGEN: define weak x86_thiscallcc void @"\01??_EC@@W3AEPAXI@Z"(%struct.C* %this, i32 %should_call_delete) 65 // CODEGEN: getelementptr inbounds i8* {{.*}}, i64 -4 66 // FIXME: should actually call _EC, not _GC. 67 // CODEGEN: call x86_thiscallcc void @"\01??_GC@@UAEPAXI@Z" 68 // CODEGEN: ret 69 70 // CODEGEN: define weak x86_thiscallcc void @"\01?public_f@C@@W3AEXXZ"(%struct.C* 71 // CODEGEN: getelementptr inbounds i8* {{.*}}, i64 -4 72 // CODEGEN: call x86_thiscallcc void @"\01?public_f@C@@UAEXXZ"(%struct.C* 73 // CODEGEN: ret 74 75 void zoo(C* obj) { 76 delete obj; 77 } 78 79 struct D { 80 virtual B* goo(); 81 }; 82 83 struct E : D { 84 virtual C* goo(); 85 // MANGLING-DAG: @"\01?goo@E@@UAEPAUC@@XZ" 86 // MANGLING-DAG: @"\01?goo@E@@QAEPAUB@@XZ" 87 // MANGLING-X64-DAG: @"\01?goo@E@@UEAAPEAUC@@XZ" 88 // MANGLING-X64-DAG: @"\01?goo@E@@QEAAPEAUB@@XZ" 89 }; 90 91 E e; // Emits vftable and forces thunk generation. 92 93 // CODEGEN: define weak x86_thiscallcc %struct.C* @"\01?goo@E@@QAEPAUB@@XZ" 94 // CODEGEN: call x86_thiscallcc %struct.C* @"\01?goo@E@@UAEPAUC@@XZ" 95 // CODEGEN: getelementptr inbounds i8* {{.*}}, i64 4 96 // CODEGEN: ret 97 98 struct F : virtual A, virtual B { 99 virtual ~F(); 100 }; 101 102 F f; // Just make sure we don't crash, e.g. mangling the complete dtor. 103 104 struct G : C { }; 105 106 struct H : E { 107 virtual G* goo(); 108 // MANGLING-DAG: @"\01?goo@H@@UAEPAUG@@XZ" 109 // MANGLING-DAG: @"\01?goo@H@@QAEPAUB@@XZ" 110 // MANGLING-DAG: @"\01?goo@H@@QAEPAUC@@XZ" 111 // MANGLING-X64-DAG: @"\01?goo@H@@UEAAPEAUG@@XZ" 112 // MANGLING-X64-DAG: @"\01?goo@H@@QEAAPEAUB@@XZ" 113 // MANGLING-X64-DAG: @"\01?goo@H@@QEAAPEAUC@@XZ" 114 }; 115 116 H h; 117 118 // FIXME: Write vtordisp adjusting thunk tests 119 120 namespace CrashOnThunksForAttributedType { 121 // We used to crash on this because the type of foo is an AttributedType, not 122 // FunctionType, and we had to look through the sugar. 123 struct A { 124 virtual void __stdcall foo(); 125 }; 126 struct B { 127 virtual void __stdcall foo(); 128 }; 129 struct C : A, B { 130 virtual void __stdcall foo(); 131 }; 132 C c; 133 } 134