diff options
author | Fariborz Jahanian <fjahanian@apple.com> | 2009-09-03 21:32:41 +0000 |
---|---|---|
committer | Fariborz Jahanian <fjahanian@apple.com> | 2009-09-03 21:32:41 +0000 |
commit | 9d436205be3e4c05854530134be61b46b13136ff (patch) | |
tree | 3051e49b2fed607ea4ca044b5b1ae441766a6d8f | |
parent | 80545ad0f9b8e52177a8c37bd140bae0ffbd0cc6 (diff) |
Mark constructors used in initialization of base(s) and fields
as referecned with location where they are used. Still
need to look at destructor aspects of them.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@80950 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/Sema/SemaDeclCXX.cpp | 62 | ||||
-rw-r--r-- | test/CodeGenCXX/constructor-template.cpp | 14 |
2 files changed, 48 insertions, 28 deletions
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 7c854be1dd..075c945456 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -948,17 +948,27 @@ Sema::setBaseOrMemberInitializers(CXXConstructorDecl *Constructor, if (VBase->getType()->isDependentType()) continue; if (CXXBaseOrMemberInitializer *Value = - AllBaseFields.lookup(VBase->getType()->getAs<RecordType>())) + AllBaseFields.lookup(VBase->getType()->getAs<RecordType>())) { + CXXRecordDecl *BaseDecl = + cast<CXXRecordDecl>(VBase->getType()->getAs<RecordType>()->getDecl()); + assert(BaseDecl && "setBaseOrMemberInitializers - BaseDecl null"); + if (CXXConstructorDecl *Ctor = BaseDecl->getDefaultConstructor(Context)) + MarkDeclarationReferenced(Value->getSourceLocation(), Ctor); AllToInit.push_back(Value); + } else { CXXRecordDecl *VBaseDecl = cast<CXXRecordDecl>(VBase->getType()->getAs<RecordType>()->getDecl()); assert(VBaseDecl && "setBaseOrMemberInitializers - VBaseDecl null"); - if (!VBaseDecl->getDefaultConstructor(Context)) + CXXConstructorDecl *Ctor = VBaseDecl->getDefaultConstructor(Context); + if (!Ctor) Bases.push_back(VBase); + else + MarkDeclarationReferenced(Constructor->getLocation(), Ctor); + CXXBaseOrMemberInitializer *Member = new (Context) CXXBaseOrMemberInitializer(VBase->getType(), 0, 0, - VBaseDecl->getDefaultConstructor(Context), + Ctor, SourceLocation(), SourceLocation()); AllToInit.push_back(Member); @@ -975,14 +985,24 @@ Sema::setBaseOrMemberInitializers(CXXConstructorDecl *Constructor, if (Base->getType()->isDependentType()) continue; if (CXXBaseOrMemberInitializer *Value = - AllBaseFields.lookup(Base->getType()->getAs<RecordType>())) + AllBaseFields.lookup(Base->getType()->getAs<RecordType>())) { + CXXRecordDecl *BaseDecl = + cast<CXXRecordDecl>(Base->getType()->getAs<RecordType>()->getDecl()); + assert(BaseDecl && "setBaseOrMemberInitializers - BaseDecl null"); + if (CXXConstructorDecl *Ctor = BaseDecl->getDefaultConstructor(Context)) + MarkDeclarationReferenced(Value->getSourceLocation(), Ctor); AllToInit.push_back(Value); + } else { CXXRecordDecl *BaseDecl = - cast<CXXRecordDecl>(Base->getType()->getAs<RecordType>()->getDecl()); + cast<CXXRecordDecl>(Base->getType()->getAs<RecordType>()->getDecl()); assert(BaseDecl && "setBaseOrMemberInitializers - BaseDecl null"); - if (!BaseDecl->getDefaultConstructor(Context)) + CXXConstructorDecl *Ctor = BaseDecl->getDefaultConstructor(Context); + if (!Ctor) Bases.push_back(Base); + else + MarkDeclarationReferenced(Constructor->getLocation(), Ctor); + CXXBaseOrMemberInitializer *Member = new (Context) CXXBaseOrMemberInitializer(Base->getType(), 0, 0, BaseDecl->getDefaultConstructor(Context), @@ -1017,6 +1037,14 @@ Sema::setBaseOrMemberInitializers(CXXConstructorDecl *Constructor, continue; } if (CXXBaseOrMemberInitializer *Value = AllBaseFields.lookup(*Field)) { + QualType FT = (*Field)->getType(); + if (const RecordType* RT = FT->getAs<RecordType>()) { + CXXRecordDecl *FieldRecDecl = cast<CXXRecordDecl>(RT->getDecl()); + assert(FieldRecDecl && "setBaseOrMemberInitializers - BaseDecl null"); + if (CXXConstructorDecl *Ctor = + FieldRecDecl->getDefaultConstructor(Context)) + MarkDeclarationReferenced(Value->getSourceLocation(), Ctor); + } AllToInit.push_back(Value); continue; } @@ -1033,6 +1061,8 @@ Sema::setBaseOrMemberInitializers(CXXConstructorDecl *Constructor, SourceLocation(), SourceLocation()); AllToInit.push_back(Member); + if (Ctor) + MarkDeclarationReferenced(Constructor->getLocation(), Ctor); if (FT.isConstQualified() && (!Ctor || Ctor->isTrivial())) { Diag(Constructor->getLocation(), diag::err_unintialized_member_in_ctor) << Context.getTagDeclType(ClassDecl) << 1 << (*Field)->getDeclName(); @@ -1176,25 +1206,7 @@ void Sema::ActOnMemInitializers(DeclPtrTy ConstructorDecl, if (Constructor->isDependentContext()) return; - // Mark all constructors used in initialization of class's members - // as referenced. - // FIXME. We can do this while building the initializer list. But - // MarkDeclarationReferenced is not accessible in ASTContext. - for (CXXConstructorDecl::init_const_iterator B = Constructor->init_begin(), - E = Constructor->init_end(); - B != E; ++B) { - CXXBaseOrMemberInitializer *Member = (*B); - if (!Member->isMemberInitializer()) - continue; - FieldDecl *Field = Member->getMember(); - QualType FT = Context.getBaseElementType(Field->getType()); - if (FT->isDependentType()) - continue; - if (const RecordType* RT = FT->getAs<RecordType>()) - if (CXXConstructorDecl *Ctor = - cast<CXXRecordDecl>(RT->getDecl())->getDefaultConstructor(Context)) - MarkDeclarationReferenced(Ctor->getLocation(), Ctor); - } + if (Diags.getDiagnosticLevel(diag::warn_base_initialized) == Diagnostic::Ignored && Diags.getDiagnosticLevel(diag::warn_field_initialized) == diff --git a/test/CodeGenCXX/constructor-template.cpp b/test/CodeGenCXX/constructor-template.cpp index 43abda435b..5fc6c2dfab 100644 --- a/test/CodeGenCXX/constructor-template.cpp +++ b/test/CodeGenCXX/constructor-template.cpp @@ -24,7 +24,14 @@ public: List(){ } // List<BinomialNode<int>*>::List() remains undefined. }; -template<typename T> class BinomialNode { +template <typename T> class Node { + int i; +public: + Node(){ } // Node<BinomialNode<int>*>::Node() remains undefined. +}; + + +template<typename T> class BinomialNode : Node<BinomialNode<T>*> { public: BinomialNode(T value) {} List<BinomialNode<T>*> nodes; @@ -35,7 +42,8 @@ int main() { BinomialNode<int> *node = new BinomialNode<int>(1); } +// CHECK-LP64: __ZN4NodeIP12BinomialNodeIiEEC1Ev: // CHECK-LP64: __ZN4ListIP12BinomialNodeIiEEC1Ev: -// CHECK-LP32:__ZN4ListIP12BinomialNodeIiEEC1Ev: - +// CHECK-LP32: __ZN4NodeIP12BinomialNodeIiEEC1Ev: +// CHECK-LP32: __ZN4ListIP12BinomialNodeIiEEC1Ev: |