On Mon, September 19, 2011 15:43, Douglas Gregor wrote: > On Sep 18, 2011, at 5:11 AM, Richard Smith wrote: >> Author: rsmith >> Date: Sun Sep 18 07:11:43 2011 >> New Revision: 139997 >> >> >> URL: http://llvm.org/viewvc/llvm-project?rev=139997&view=rev >> Log: >> PR10304: Do not call destructors for data members from union destructors. >> Prior to C++11, this >> has no effect since any such destructors must be trivial, and in C++11 such >> destructors must not be called. > > Do we also have to worry about anonymous unions in non-class scope?
We just directly call the destructor for the implicit anonymous union object at the end of its lifetime, so this patch covers such cases too. Also, if the anonymous union contains a data member with a non-trivial destructor, the code is ill-formed anyway (since the union's implicit destructor is defined deleted, and it's not possible to explicitly define a destructor) -- but clang does not yet implement that rule. >> Added: >> cfe/trunk/test/CodeGenCXX/union-dtor.cpp Modified: >> cfe/trunk/lib/CodeGen/CGClass.cpp cfe/trunk/lib/Sema/SemaDeclCXX.cpp >> >> Modified: cfe/trunk/lib/CodeGen/CGClass.cpp >> URL: >> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CGClass.cpp?rev=1 >> 39997&r1=139996&r2=139997&view=diff >> ============================================================================ >> == >> --- cfe/trunk/lib/CodeGen/CGClass.cpp (original) >> +++ cfe/trunk/lib/CodeGen/CGClass.cpp Sun Sep 18 07:11:43 2011 >> @@ -980,6 +980,10 @@ >> >> >> const CXXRecordDecl *ClassDecl = DD->getParent(); >> >> + // Unions have no bases and do not call field destructors. >> + if (ClassDecl->isUnion()) >> + return; >> + >> // The complete-destructor phase just destructs all the virtual bases. >> if (DtorType == Dtor_Complete) { >> >> >> Modified: cfe/trunk/lib/Sema/SemaDeclCXX.cpp >> URL: >> http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclCXX.cpp?rev= >> 139997&r1=139996&r2=139997&view=diff >> ============================================================================ >> == >> --- cfe/trunk/lib/Sema/SemaDeclCXX.cpp (original) >> +++ cfe/trunk/lib/Sema/SemaDeclCXX.cpp Sun Sep 18 07:11:43 2011 >> @@ -2767,8 +2767,9 @@ >> void Sema::MarkBaseAndMemberDestructorsReferenced(SourceLocation Location, >> CXXRecordDecl *ClassDecl) { >> - // Ignore dependent contexts. >> - if (ClassDecl->isDependentContext()) >> + // Ignore dependent contexts. Also ignore unions, since their members >> never + // have destructors implicitly called. >> + if (ClassDecl->isDependentContext() || ClassDecl->isUnion()) >> return; >> >> // FIXME: all the access-control diagnostics are positioned on the >> >> >> Added: cfe/trunk/test/CodeGenCXX/union-dtor.cpp >> URL: >> http://llvm.org/viewvc/llvm-project/cfe/trunk/test/CodeGenCXX/union-dtor.cp >> p?rev=139997&view=auto >> =========================================================================== >> === >> --- cfe/trunk/test/CodeGenCXX/union-dtor.cpp (added) >> +++ cfe/trunk/test/CodeGenCXX/union-dtor.cpp Sun Sep 18 07:11:43 2011 >> @@ -0,0 +1,42 @@ >> +// RUN: %clang_cc1 -std=c++0x %s -S -o - -emit-llvm | FileCheck %s >> + >> +// PR10304: destructors should not call destructors for variant members. >> + >> +template<bool b = false> >> +struct Foo { >> + Foo() { static_assert(b, "Foo::Foo used"); } >> + ~Foo() { static_assert(b, "Foo::~Foo used"); } >> +}; >> + >> +struct Bar { >> + Bar(); >> + ~Bar(); >> +}; >> + >> +union FooBar { >> + FooBar() {} >> + ~FooBar() {} >> + Foo<> foo; >> + Bar bar; >> +}; >> + >> +struct Variant { >> + Variant() {} >> + ~Variant() {} >> + union { >> + Foo<> foo; >> + Bar bar; >> + }; >> +}; >> + >> +FooBar foobar; >> +Variant variant; >> + >> +// The ctor and dtor of Foo<> and Bar should not be mentioned in the >> resulting +// code. >> +// >> +// CHECK-NOT: 3FooILb1EEC1 >> +// CHECK-NOT: 3BarC1 >> +// >> +// CHECK-NOT: 3FooILb1EED1 >> +// CHECK-NOT: 3BarD1 _______________________________________________ cfe-commits mailing list [email protected] http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits
