diff options
-rw-r--r-- | include/clang/AST/Decl.h | 18 | ||||
-rw-r--r-- | lib/Frontend/PCHReaderDecl.cpp | 1 | ||||
-rw-r--r-- | lib/Frontend/PCHWriterDecl.cpp | 1 | ||||
-rw-r--r-- | lib/Sema/SemaTemplateInstantiateDecl.cpp | 5 | ||||
-rw-r--r-- | test/SemaTemplate/instantiate-declref.cpp | 3 |
5 files changed, 23 insertions, 5 deletions
diff --git a/include/clang/AST/Decl.h b/include/clang/AST/Decl.h index a30cf0fbc5..eb38367436 100644 --- a/include/clang/AST/Decl.h +++ b/include/clang/AST/Decl.h @@ -1149,10 +1149,15 @@ class EnumDecl : public TagDecl { /// to for code generation purposes. Note that the enumerator constants may /// have a different type than this does. QualType IntegerType; - + + /// \brief If the enumeration was instantiated from an enumeration + /// within a class or function template, this pointer refers to the + /// enumeration declared within the template. + EnumDecl *InstantiatedFrom; + EnumDecl(DeclContext *DC, SourceLocation L, IdentifierInfo *Id) - : TagDecl(Enum, TK_enum, DC, L, Id) { + : TagDecl(Enum, TK_enum, DC, L, Id), InstantiatedFrom(0) { IntegerType = QualType(); } public: @@ -1188,6 +1193,15 @@ public: /// \brief Set the underlying integer type. void setIntegerType(QualType T) { IntegerType = T; } + /// \brief Returns the enumeration (declared within the template) + /// from which this enumeration type was instantiated, or NULL if + /// this enumeration was not instantiated from any template. + EnumDecl *getInstantiatedFromMemberEnum() const { + return InstantiatedFrom; + } + + void setInstantiationOfMemberEnum(EnumDecl *IF) { InstantiatedFrom = IF; } + static bool classof(const Decl *D) { return D->getKind() == Enum; } static bool classof(const EnumDecl *D) { return true; } }; diff --git a/lib/Frontend/PCHReaderDecl.cpp b/lib/Frontend/PCHReaderDecl.cpp index adf0d1155e..6856623e60 100644 --- a/lib/Frontend/PCHReaderDecl.cpp +++ b/lib/Frontend/PCHReaderDecl.cpp @@ -120,6 +120,7 @@ void PCHDeclReader::VisitTagDecl(TagDecl *TD) { void PCHDeclReader::VisitEnumDecl(EnumDecl *ED) { VisitTagDecl(ED); ED->setIntegerType(Reader.GetType(Record[Idx++])); + // FIXME: C++ InstantiatedFrom } void PCHDeclReader::VisitRecordDecl(RecordDecl *RD) { diff --git a/lib/Frontend/PCHWriterDecl.cpp b/lib/Frontend/PCHWriterDecl.cpp index 5d08334dee..ef04104316 100644 --- a/lib/Frontend/PCHWriterDecl.cpp +++ b/lib/Frontend/PCHWriterDecl.cpp @@ -116,6 +116,7 @@ void PCHDeclWriter::VisitTagDecl(TagDecl *D) { void PCHDeclWriter::VisitEnumDecl(EnumDecl *D) { VisitTagDecl(D); Writer.AddTypeRef(D->getIntegerType(), Record); + // FIXME: C++ InstantiatedFrom Code = pch::DECL_ENUM; } diff --git a/lib/Sema/SemaTemplateInstantiateDecl.cpp b/lib/Sema/SemaTemplateInstantiateDecl.cpp index a5eb7793b8..41c1944b54 100644 --- a/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -208,6 +208,7 @@ Decl *TemplateDeclInstantiator::VisitEnumDecl(EnumDecl *D) { EnumDecl *Enum = EnumDecl::Create(SemaRef.Context, Owner, D->getLocation(), D->getIdentifier(), /*PrevDecl=*/0); + Enum->setInstantiationOfMemberEnum(D); Enum->setAccess(D->getAccess()); Owner->addDecl(SemaRef.Context, Enum); Enum->startDefinition(); @@ -648,7 +649,9 @@ static bool isInstantiationOf(ASTContext &Ctx, NamedDecl *D, Decl *Other) { return Ctx.getCanonicalDecl(Function->getInstantiatedFromMemberFunction()) == Ctx.getCanonicalDecl(D); - // FIXME: Need something similar to the above for EnumDecls. + if (EnumDecl *Enum = dyn_cast<EnumDecl>(Other)) + return Ctx.getCanonicalDecl(Enum->getInstantiatedFromMemberEnum()) + == Ctx.getCanonicalDecl(D); // FIXME: How can we find instantiations of anonymous unions? diff --git a/test/SemaTemplate/instantiate-declref.cpp b/test/SemaTemplate/instantiate-declref.cpp index 2512df15b1..cceaed00e6 100644 --- a/test/SemaTemplate/instantiate-declref.cpp +++ b/test/SemaTemplate/instantiate-declref.cpp @@ -9,8 +9,7 @@ namespace N { typedef T type; static enum K1 { K1Val = sizeof(T) } Kind1; - // FIXME: Remove the name K2, below - static enum K2 { K2Val = sizeof(T)*2 } Kind2; + static enum { K2Val = sizeof(T)*2 } Kind2; void foo() { K1 k1 = K1Val; |