From 948514b3ec0ea302ca10dee6e8a6333d2ecacc2b Mon Sep 17 00:00:00 2001 From: Rafael Espindola Date: Mon, 15 Sep 2014 18:46:13 +0000 Subject: [PATCH] Create a emitCXXStructor function and make the existing emitCXXConstructor and emitCXXDestructor static helpers. A next patch will make it a helper in CGCXXABI. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@217804 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/CodeGen/CGCXX.cpp | 79 ++++++++++++++++++++--------------- lib/CodeGen/CodeGenModule.cpp | 4 +- lib/CodeGen/CodeGenModule.h | 24 +++++------ 3 files changed, 58 insertions(+), 49 deletions(-) diff --git a/lib/CodeGen/CGCXX.cpp b/lib/CodeGen/CGCXX.cpp index 6244c3b3d2..aa53691d77 100644 --- a/lib/CodeGen/CGCXX.cpp +++ b/lib/CodeGen/CGCXX.cpp @@ -196,33 +196,35 @@ bool CodeGenModule::TryEmitDefinitionAsAlias(GlobalDecl AliasDecl, return false; } -void CodeGenModule::EmitCXXConstructor(const CXXConstructorDecl *ctor, - CXXCtorType ctorType) { - if (!getTarget().getCXXABI().hasConstructorVariants()) { - // If there are no constructor variants, always emit the complete destructor. - ctorType = Ctor_Complete; +static void emitCXXConstructor(CodeGenModule &CGM, + const CXXConstructorDecl *ctor, + StructorType ctorType) { + if (!CGM.getTarget().getCXXABI().hasConstructorVariants()) { + // If there are no constructor variants, always emit the complete + // destructor. + ctorType = StructorType::Complete; } else if (!ctor->getParent()->getNumVBases() && - (ctorType == Ctor_Complete || ctorType == Ctor_Base)) { + (ctorType == StructorType::Complete || + ctorType == StructorType::Base)) { // The complete constructor is equivalent to the base constructor // for classes with no virtual bases. Try to emit it as an alias. - bool ProducedAlias = - !TryEmitDefinitionAsAlias(GlobalDecl(ctor, Ctor_Complete), - GlobalDecl(ctor, Ctor_Base), true); - if (ctorType == Ctor_Complete && ProducedAlias) + bool ProducedAlias = !CGM.TryEmitDefinitionAsAlias( + GlobalDecl(ctor, Ctor_Complete), GlobalDecl(ctor, Ctor_Base), true); + if (ctorType == StructorType::Complete && ProducedAlias) return; } const CGFunctionInfo &fnInfo = - getTypes().arrangeCXXStructorDeclaration(ctor, getFromCtorType(ctorType)); + CGM.getTypes().arrangeCXXStructorDeclaration(ctor, ctorType); - auto *fn = cast(getAddrOfCXXStructor( - ctor, getFromCtorType(ctorType), &fnInfo, nullptr, true)); - setFunctionLinkage(GlobalDecl(ctor, ctorType), fn); + auto *fn = cast( + CGM.getAddrOfCXXStructor(ctor, ctorType, &fnInfo, nullptr, true)); + GlobalDecl GD(ctor, toCXXCtorType(ctorType)); + CGM.setFunctionLinkage(GD, fn); + CodeGenFunction(CGM).GenerateCode(GD, fn, fnInfo); - CodeGenFunction(*this).GenerateCode(GlobalDecl(ctor, ctorType), fn, fnInfo); - - setFunctionDefinitionAttributes(ctor, fn); - SetLLVMFunctionAttributesForDefinition(ctor, fn); + CGM.setFunctionDefinitionAttributes(ctor, fn); + CGM.SetLLVMFunctionAttributesForDefinition(ctor, fn); } llvm::GlobalValue *CodeGenModule::getAddrOfCXXStructor( @@ -251,20 +253,19 @@ llvm::GlobalValue *CodeGenModule::getAddrOfCXXStructor( DontDefer)); } -void CodeGenModule::EmitCXXDestructor(const CXXDestructorDecl *dtor, - CXXDtorType dtorType) { +static void emitCXXDestructor(CodeGenModule &CGM, const CXXDestructorDecl *dtor, + StructorType dtorType) { // The complete destructor is equivalent to the base destructor for // classes with no virtual bases, so try to emit it as an alias. if (!dtor->getParent()->getNumVBases() && - (dtorType == Dtor_Complete || dtorType == Dtor_Base)) { - bool ProducedAlias = - !TryEmitDefinitionAsAlias(GlobalDecl(dtor, Dtor_Complete), - GlobalDecl(dtor, Dtor_Base), true); + (dtorType == StructorType::Complete || dtorType == StructorType::Base)) { + bool ProducedAlias = !CGM.TryEmitDefinitionAsAlias( + GlobalDecl(dtor, Dtor_Complete), GlobalDecl(dtor, Dtor_Base), true); if (ProducedAlias) { - if (dtorType == Dtor_Complete) + if (dtorType == StructorType::Complete) return; if (dtor->isVirtual()) - getVTables().EmitThunks(GlobalDecl(dtor, Dtor_Complete)); + CGM.getVTables().EmitThunks(GlobalDecl(dtor, Dtor_Complete)); } } @@ -272,20 +273,30 @@ void CodeGenModule::EmitCXXDestructor(const CXXDestructorDecl *dtor, // base class if there is exactly one non-virtual base class with a // non-trivial destructor, there are no fields with a non-trivial // destructor, and the body of the destructor is trivial. - if (dtorType == Dtor_Base && !TryEmitBaseDestructorAsAlias(dtor)) + if (dtorType == StructorType::Base && !CGM.TryEmitBaseDestructorAsAlias(dtor)) return; const CGFunctionInfo &fnInfo = - getTypes().arrangeCXXStructorDeclaration(dtor, getFromDtorType(dtorType)); + CGM.getTypes().arrangeCXXStructorDeclaration(dtor, dtorType); + + auto *fn = cast( + CGM.getAddrOfCXXStructor(dtor, dtorType, &fnInfo, nullptr, true)); - auto *fn = cast(getAddrOfCXXStructor( - dtor, getFromDtorType(dtorType), &fnInfo, nullptr, true)); - setFunctionLinkage(GlobalDecl(dtor, dtorType), fn); + GlobalDecl GD(dtor, toCXXDtorType(dtorType)); + CGM.setFunctionLinkage(GD, fn); + CodeGenFunction(CGM).GenerateCode(GD, fn, fnInfo); - CodeGenFunction(*this).GenerateCode(GlobalDecl(dtor, dtorType), fn, fnInfo); + CGM.setFunctionDefinitionAttributes(dtor, fn); + CGM.SetLLVMFunctionAttributesForDefinition(dtor, fn); +} - setFunctionDefinitionAttributes(dtor, fn); - SetLLVMFunctionAttributesForDefinition(dtor, fn); +void CodeGenModule::emitCXXStructor(const CXXMethodDecl *MD, + StructorType Type) { + if (auto *CD = dyn_cast(MD)) { + emitCXXConstructor(*this, CD, Type); + return; + } + emitCXXDestructor(*this, cast(MD), Type); } static llvm::Value *BuildAppleKextVirtualCall(CodeGenFunction &CGF, diff --git a/lib/CodeGen/CodeGenModule.cpp b/lib/CodeGen/CodeGenModule.cpp index 7ea787db37..b9986fc179 100644 --- a/lib/CodeGen/CodeGenModule.cpp +++ b/lib/CodeGen/CodeGenModule.cpp @@ -1404,9 +1404,9 @@ void CodeGenModule::EmitGlobalDefinition(GlobalDecl GD, llvm::GlobalValue *GV) { // Make sure to emit the definition(s) before we emit the thunks. // This is necessary for the generation of certain thunks. if (const auto *CD = dyn_cast(Method)) - EmitCXXConstructor(CD, GD.getCtorType()); + emitCXXStructor(CD, getFromCtorType(GD.getCtorType())); else if (const auto *DD = dyn_cast(Method)) - EmitCXXDestructor(DD, GD.getDtorType()); + emitCXXStructor(DD, getFromDtorType(GD.getDtorType())); else EmitGlobalFunctionDefinition(GD, GV); diff --git a/lib/CodeGen/CodeGenModule.h b/lib/CodeGen/CodeGenModule.h index 3b4417b351..1ae09c84cc 100644 --- a/lib/CodeGen/CodeGenModule.h +++ b/lib/CodeGen/CodeGenModule.h @@ -1044,6 +1044,14 @@ public: /// are emitted lazily. void EmitGlobal(GlobalDecl D); + bool TryEmitDefinitionAsAlias(GlobalDecl Alias, GlobalDecl Target, + bool InEveryTU); + bool TryEmitBaseDestructorAsAlias(const CXXDestructorDecl *D); + + /// Set attributes for a global definition. + void setFunctionDefinitionAttributes(const FunctionDecl *D, + llvm::Function *F); + private: llvm::GlobalValue *GetGlobalValue(StringRef Ref); @@ -1064,10 +1072,6 @@ private: void setNonAliasAttributes(const Decl *D, llvm::GlobalObject *GO); - /// Set attributes for a global definition. - void setFunctionDefinitionAttributes(const FunctionDecl *D, - llvm::Function *F); - /// Set function attributes for a function declaration. void SetFunctionAttributes(GlobalDecl GD, llvm::Function *F, @@ -1083,19 +1087,13 @@ private: // C++ related functions. - bool TryEmitDefinitionAsAlias(GlobalDecl Alias, GlobalDecl Target, - bool InEveryTU); - bool TryEmitBaseDestructorAsAlias(const CXXDestructorDecl *D); - void EmitNamespace(const NamespaceDecl *D); void EmitLinkageSpec(const LinkageSpecDecl *D); void CompleteDIClassType(const CXXMethodDecl* D); - /// Emit a single constructor with the given type from a C++ constructor Decl. - void EmitCXXConstructor(const CXXConstructorDecl *D, CXXCtorType Type); - - /// Emit a single destructor with the given type from a C++ destructor Decl. - void EmitCXXDestructor(const CXXDestructorDecl *D, CXXDtorType Type); + /// Emit a single constructor/destructor with the given type from a C++ + /// constructor Decl. + void emitCXXStructor(const CXXMethodDecl *D, StructorType Type); /// \brief Emit the function that initializes C++ thread_local variables. void EmitCXXThreadLocalInitFunc(); -- 2.40.0