r370597 - [clang] Devirtualization for classes with destructors marked as 'final'
David Bolvansky via cfe-commits
cfe-commits at lists.llvm.org
Sat Aug 31 11:52:45 PDT 2019
Author: xbolva00
Date: Sat Aug 31 11:52:44 2019
New Revision: 370597
URL: http://llvm.org/viewvc/llvm-project?rev=370597&view=rev
Log:
[clang] Devirtualization for classes with destructors marked as 'final'
A class with a destructor marked final cannot be derived from, so it should afford the same devirtualization opportunities as marking the entire class final.
Patch by logan-5 (Logan Smith)
Reviewed by rsmith
Differential Revision: https://reviews.llvm.org/D66621
Modified:
cfe/trunk/lib/AST/DeclCXX.cpp
cfe/trunk/test/CodeGenCXX/devirtualize-virtual-function-calls-final.cpp
Modified: cfe/trunk/lib/AST/DeclCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclCXX.cpp?rev=370597&r1=370596&r2=370597&view=diff
==============================================================================
--- cfe/trunk/lib/AST/DeclCXX.cpp (original)
+++ cfe/trunk/lib/AST/DeclCXX.cpp Sat Aug 31 11:52:44 2019
@@ -2067,10 +2067,15 @@ CXXMethodDecl *CXXMethodDecl::getDevirtu
if (DevirtualizedMethod->hasAttr<FinalAttr>())
return DevirtualizedMethod;
- // Similarly, if the class itself is marked 'final' it can't be overridden
- // and we can therefore devirtualize the member function call.
+ // Similarly, if the class itself or its destructor is marked 'final',
+ // the class can't be derived from and we can therefore devirtualize the
+ // member function call.
if (BestDynamicDecl->hasAttr<FinalAttr>())
return DevirtualizedMethod;
+ if (const auto *dtor = BestDynamicDecl->getDestructor()) {
+ if (dtor->hasAttr<FinalAttr>())
+ return DevirtualizedMethod;
+ }
if (const auto *DRE = dyn_cast<DeclRefExpr>(Base)) {
if (const auto *VD = dyn_cast<VarDecl>(DRE->getDecl()))
Modified: cfe/trunk/test/CodeGenCXX/devirtualize-virtual-function-calls-final.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/devirtualize-virtual-function-calls-final.cpp?rev=370597&r1=370596&r2=370597&view=diff
==============================================================================
--- cfe/trunk/test/CodeGenCXX/devirtualize-virtual-function-calls-final.cpp (original)
+++ cfe/trunk/test/CodeGenCXX/devirtualize-virtual-function-calls-final.cpp Sat Aug 31 11:52:44 2019
@@ -24,11 +24,24 @@ namespace Test2 {
}
}
-namespace Test3 {
+namespace Test2a {
struct A {
+ virtual ~A() final {}
virtual int f();
};
+ // CHECK-LABEL: define i32 @_ZN6Test2a1fEPNS_1AE
+ int f(A *a) {
+ // CHECK: call i32 @_ZN6Test2a1A1fEv
+ return a->f();
+ }
+}
+
+
+namespace Test3 {
+ struct A {
+ virtual int f(); };
+
struct B final : A { };
// CHECK-LABEL: define i32 @_ZN5Test31fEPNS_1BE
More information about the cfe-commits
mailing list