// RUN: %clang_cc1 -std=c++11 %s -emit-llvm -o - | FileCheck %s namespace Test1 { struct A { virtual int f() final; }; // CHECK: define i32 @_ZN5Test11fEPNS_1AE int f(A *a) { // CHECK: call i32 @_ZN5Test11A1fEv return a->f(); } } namespace Test2 { struct A final { virtual int f(); }; // CHECK: define i32 @_ZN5Test21fEPNS_1AE int f(A *a) { // CHECK: call i32 @_ZN5Test21A1fEv return a->f(); } } namespace Test3 { struct A { virtual int f(); }; struct B final : A { }; // CHECK: define i32 @_ZN5Test31fEPNS_1BE int f(B *b) { // CHECK: call i32 @_ZN5Test31A1fEv return b->f(); } // CHECK: define i32 @_ZN5Test31fERNS_1BE int f(B &b) { // CHECK: call i32 @_ZN5Test31A1fEv return b.f(); } // CHECK: define i32 @_ZN5Test31fEPv int f(void *v) { // CHECK: call i32 @_ZN5Test31A1fEv return static_cast(v)->f(); } } namespace Test4 { struct A { virtual void f(); }; struct B final : A { virtual void f(); }; // CHECK: define void @_ZN5Test41fEPNS_1BE void f(B* d) { // CHECK: call void @_ZN5Test41B1fEv static_cast(d)->f(); } } namespace Test5 { struct A { virtual void f(); }; struct B : A { virtual void f(); }; struct C final : B { }; // CHECK: define void @_ZN5Test51fEPNS_1CE void f(C* d) { // CHECK: call void @_ZN5Test51B1fEv static_cast(d)->f(); } } namespace Test6 { struct A { virtual ~A(); }; struct B : public A { virtual ~B(); }; struct C { virtual ~C(); }; struct D final : public C, public B { }; // CHECK: define void @_ZN5Test61fEPNS_1DE void f(D* d) { // CHECK: call void @_ZN5Test61DD1Ev static_cast(d)->~A(); } }