[cfe-commits] r63899 - in /cfe/trunk: include/clang/AST/ASTContext.h include/clang/AST/Decl.h include/clang/AST/DeclTemplate.h include/clang/AST/Type.h lib/AST/ASTContext.cpp lib/AST/DeclSerialization.cpp lib/AST/DeclTemplate.cpp lib/AST/Type.cpp lib/AST/TypeSerialization.cpp
Douglas Gregor
dgregor at apple.com
Thu Feb 5 15:33:38 PST 2009
Author: dgregor
Date: Thu Feb 5 17:33:38 2009
New Revision: 63899
URL: http://llvm.org/viewvc/llvm-project?rev=63899&view=rev
Log:
Improve the representation of template type parameters. We now
canonicalize by template parameter depth, index, and name, and the
unnamed version of a template parameter serves as the canonical.
TemplateTypeParmDecl no longer needs to inherit from
TemplateParmPosition, since depth and index information is present
within the type.
Modified:
cfe/trunk/include/clang/AST/ASTContext.h
cfe/trunk/include/clang/AST/Decl.h
cfe/trunk/include/clang/AST/DeclTemplate.h
cfe/trunk/include/clang/AST/Type.h
cfe/trunk/lib/AST/ASTContext.cpp
cfe/trunk/lib/AST/DeclSerialization.cpp
cfe/trunk/lib/AST/DeclTemplate.cpp
cfe/trunk/lib/AST/Type.cpp
cfe/trunk/lib/AST/TypeSerialization.cpp
Modified: cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Thu Feb 5 17:33:38 2009
@@ -68,6 +68,7 @@
llvm::FoldingSet<VectorType> VectorTypes;
llvm::FoldingSet<FunctionTypeNoProto> FunctionTypeNoProtos;
llvm::FoldingSet<FunctionTypeProto> FunctionTypeProtos;
+ llvm::FoldingSet<TemplateTypeParmType> TemplateTypeParmTypes;
llvm::FoldingSet<ObjCQualifiedInterfaceType> ObjCQualifiedInterfaceTypes;
llvm::FoldingSet<ObjCQualifiedIdType> ObjCQualifiedIdTypes;
/// ASTRecordLayouts - A cache mapping from RecordDecls to ASTRecordLayouts.
@@ -256,9 +257,11 @@
/// getTypedefType - Return the unique reference to the type for the
/// specified typename decl.
QualType getTypedefType(TypedefDecl *Decl);
- QualType getTemplateTypeParmType(TemplateTypeParmDecl *Decl);
QualType getObjCInterfaceType(ObjCInterfaceDecl *Decl);
-
+
+ QualType getTemplateTypeParmType(unsigned Depth, unsigned Index,
+ IdentifierInfo *Name = 0);
+
/// getObjCQualifiedInterfaceType - Return a
/// ObjCQualifiedInterfaceType type for the given interface decl and
/// the conforming protocol list.
Modified: cfe/trunk/include/clang/AST/Decl.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Decl.h?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/Decl.h (original)
+++ cfe/trunk/include/clang/AST/Decl.h Thu Feb 5 17:33:38 2009
@@ -762,13 +762,15 @@
/// TypeDecl - Represents a declaration of a type.
///
class TypeDecl : public NamedDecl {
- /// TypeForDecl - This indicates the Type object that represents this
- /// TypeDecl. It is a cache maintained by ASTContext::getTypedefType,
- /// ASTContext::getTagDeclType, and ASTContext::getTemplateTypeParmType.
+ /// TypeForDecl - This indicates the Type object that represents
+ /// this TypeDecl. It is a cache maintained by
+ /// ASTContext::getTypedefType, ASTContext::getTagDeclType, and
+ /// ASTContext::getTemplateTypeParmType, and TemplateTypeParmDecl.
Type *TypeForDecl;
friend class ASTContext;
friend class DeclContext;
friend class TagDecl;
+ friend class TemplateTypeParmDecl;
protected:
TypeDecl(Kind DK, DeclContext *DC, SourceLocation L,
Modified: cfe/trunk/include/clang/AST/DeclTemplate.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/DeclTemplate.h?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/DeclTemplate.h (original)
+++ cfe/trunk/include/clang/AST/DeclTemplate.h Thu Feb 5 17:33:38 2009
@@ -201,30 +201,28 @@
/// @code
/// template<typename T> class vector;
/// @endcode
-class TemplateTypeParmDecl
- : public TypeDecl, protected TemplateParmPosition {
- /// Typename - Whether this template type parameter was declaration
- /// with the 'typename' keyword. If false, it was declared with the
+class TemplateTypeParmDecl : public TypeDecl {
+ /// \brief Whether this template type parameter was declaration with
+ /// the 'typename' keyword. If false, it was declared with the
/// 'class' keyword.
bool Typename : 1;
- TemplateTypeParmDecl(DeclContext *DC, SourceLocation L, unsigned D,
- unsigned P, IdentifierInfo *Id, bool Typename)
- : TypeDecl(TemplateTypeParm, DC, L, Id), TemplateParmPosition(D, P),
- Typename(Typename) { }
+ TemplateTypeParmDecl(DeclContext *DC, SourceLocation L, IdentifierInfo *Id,
+ bool Typename, QualType Type)
+ : TypeDecl(TemplateTypeParm, DC, L, Id), Typename(Typename) {
+ TypeForDecl = Type.getTypePtr();
+ }
+
public:
static TemplateTypeParmDecl *Create(ASTContext &C, DeclContext *DC,
SourceLocation L, unsigned D, unsigned P,
IdentifierInfo *Id, bool Typename);
- /// wasDeclarationWithTypename - Whether this template type
- /// parameter was declared with the 'typename' keyword. If not, it
- /// was declared with the 'class' keyword.
+ /// \brief Whether this template type parameter was declared with
+ /// the 'typename' keyword. If not, it was declared with the 'class'
+ /// keyword.
bool wasDeclaredWithTypename() const { return Typename; }
- using TemplateParmPosition::getDepth;
- using TemplateParmPosition::getPosition;
-
// Implement isa/cast/dyncast/etc.
static bool classof(const Decl *D) {
return D->getKind() == TemplateTypeParm;
@@ -232,10 +230,10 @@
static bool classof(const TemplateTypeParmDecl *D) { return true; }
protected:
- /// EmitImpl - Serialize this TemplateTypeParmDecl. Called by Decl::Emit.
+ /// Serialize this TemplateTypeParmDecl. Called by Decl::Emit.
virtual void EmitImpl(llvm::Serializer& S) const;
- /// CreateImpl - Deserialize a TemplateTypeParmDecl. Called by Decl::Create.
+ /// Deserialize a TemplateTypeParmDecl. Called by Decl::Create.
static TemplateTypeParmDecl* CreateImpl(llvm::Deserializer& D, ASTContext& C);
friend Decl* Decl::Create(llvm::Deserializer& D, ASTContext& C);
Modified: cfe/trunk/include/clang/AST/Type.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Type.h?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/trunk/include/clang/AST/Type.h Thu Feb 5 17:33:38 2009
@@ -1188,7 +1188,7 @@
TypedefDecl *getDecl() const { return Decl; }
/// LookThroughTypedefs - Return the ultimate type this typedef corresponds to
- /// potentially looking through *all* consequtive typedefs. This returns the
+ /// potentially looking through *all* consecutive typedefs. This returns the
/// sum of the type qualifiers, so if you have:
/// typedef const int A;
/// typedef volatile A B;
@@ -1350,20 +1350,40 @@
static bool classof(const EnumType *) { return true; }
};
-class TemplateTypeParmType : public Type {
- TemplateTypeParmDecl *Decl;
+class TemplateTypeParmType : public Type, public llvm::FoldingSetNode {
+ unsigned Depth : 16;
+ unsigned Index : 16;
+ IdentifierInfo *Name;
+
+ TemplateTypeParmType(unsigned D, unsigned I, IdentifierInfo *N,
+ QualType Canon)
+ : Type(TemplateTypeParm, Canon, /*Dependent=*/true),
+ Depth(D), Index(I), Name(N) { }
+
+ TemplateTypeParmType(unsigned D, unsigned I)
+ : Type(TemplateTypeParm, QualType(this, 0), /*Dependent=*/true),
+ Depth(D), Index(I), Name(0) { }
-protected:
- TemplateTypeParmType(TemplateTypeParmDecl *D)
- : Type(TemplateTypeParm, QualType(this, 0), /*Dependent=*/true), Decl(D) { }
-
- friend class ASTContext; // ASTContext creates these
+ friend class ASTContext; // ASTContext creates these
public:
- TemplateTypeParmDecl *getDecl() const { return Decl; }
-
+ unsigned getDepth() const { return Depth; }
+ unsigned getIndex() const { return Index; }
+ IdentifierInfo *getName() const { return Name; }
+
virtual void getAsStringInternal(std::string &InnerString) const;
+ void Profile(llvm::FoldingSetNodeID &ID) {
+ Profile(ID, Depth, Index, Name);
+ }
+
+ static void Profile(llvm::FoldingSetNodeID &ID, unsigned Depth,
+ unsigned Index, IdentifierInfo *Name) {
+ ID.AddInteger(Depth);
+ ID.AddInteger(Index);
+ ID.AddPointer(Name);
+ }
+
static bool classof(const Type *T) {
return T->getTypeClass() == TemplateTypeParm;
}
@@ -1374,7 +1394,7 @@
static Type* CreateImpl(ASTContext& Context, llvm::Deserializer& D);
friend class Type;
};
-
+
/// ObjCInterfaceType - Interfaces are the core concept in Objective-C for
/// object oriented design. They basically correspond to C++ classes. There
/// are two kinds of interface types, normal interfaces like "NSString" and
Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Thu Feb 5 17:33:38 2009
@@ -1144,9 +1144,9 @@
if (TypedefDecl *Typedef = dyn_cast<TypedefDecl>(Decl))
return getTypedefType(Typedef);
- else if (TemplateTypeParmDecl *TP = dyn_cast<TemplateTypeParmDecl>(Decl))
- return getTemplateTypeParmType(TP);
- else if (ObjCInterfaceDecl *ObjCInterface = dyn_cast<ObjCInterfaceDecl>(Decl))
+ else if (isa<TemplateTypeParmDecl>(Decl)) {
+ assert(false && "Template type parameter types are always available.");
+ } else if (ObjCInterfaceDecl *ObjCInterface = dyn_cast<ObjCInterfaceDecl>(Decl))
return getObjCInterfaceType(ObjCInterface);
if (CXXRecordDecl *CXXRecord = dyn_cast<CXXRecordDecl>(Decl)) {
@@ -1185,16 +1185,6 @@
return QualType(Decl->TypeForDecl, 0);
}
-/// getTemplateTypeParmType - Return the unique reference to the type
-/// for the specified template type parameter declaration.
-QualType ASTContext::getTemplateTypeParmType(TemplateTypeParmDecl *Decl) {
- if (!Decl->TypeForDecl) {
- Decl->TypeForDecl = new (*this,8) TemplateTypeParmType(Decl);
- Types.push_back(Decl->TypeForDecl);
- }
- return QualType(Decl->TypeForDecl, 0);
-}
-
/// getObjCInterfaceType - Return the unique reference to the type for the
/// specified ObjC interface decl.
QualType ASTContext::getObjCInterfaceType(ObjCInterfaceDecl *Decl) {
@@ -1205,6 +1195,31 @@
return QualType(Decl->TypeForDecl, 0);
}
+/// \brief Retrieve the template type parameter type for a template
+/// parameter with the given depth, index, and (optionally) name.
+QualType ASTContext::getTemplateTypeParmType(unsigned Depth, unsigned Index,
+ IdentifierInfo *Name) {
+ llvm::FoldingSetNodeID ID;
+ TemplateTypeParmType::Profile(ID, Depth, Index, Name);
+ void *InsertPos = 0;
+ TemplateTypeParmType *TypeParm
+ = TemplateTypeParmTypes.FindNodeOrInsertPos(ID, InsertPos);
+
+ if (TypeParm)
+ return QualType(TypeParm, 0);
+
+ if (Name)
+ TypeParm = new (*this, 8) TemplateTypeParmType(Depth, Index, Name,
+ getTemplateTypeParmType(Depth, Index));
+ else
+ TypeParm = new (*this, 8) TemplateTypeParmType(Depth, Index);
+
+ Types.push_back(TypeParm);
+ TemplateTypeParmTypes.InsertNode(TypeParm, InsertPos);
+
+ return QualType(TypeParm, 0);
+}
+
/// CmpProtocolNames - Comparison predicate for sorting protocols
/// alphabetically.
static bool CmpProtocolNames(const ObjCProtocolDecl *LHS,
Modified: cfe/trunk/lib/AST/DeclSerialization.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclSerialization.cpp?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/lib/AST/DeclSerialization.cpp (original)
+++ cfe/trunk/lib/AST/DeclSerialization.cpp Thu Feb 5 17:33:38 2009
@@ -598,21 +598,17 @@
//===----------------------------------------------------------------------===//
void TemplateTypeParmDecl::EmitImpl(Serializer& S) const {
- S.EmitInt(Depth);
- S.EmitInt(Position);
S.EmitBool(Typename);
- NamedDecl::EmitInRec(S);
+ TypeDecl::EmitInRec(S);
}
TemplateTypeParmDecl *
TemplateTypeParmDecl::CreateImpl(Deserializer& D, ASTContext& C) {
- unsigned Depth = D.ReadInt();
- unsigned Position = D.ReadInt();
bool Typename = D.ReadBool();
TemplateTypeParmDecl *decl
- = new (C) TemplateTypeParmDecl(0, SourceLocation(), Depth, Position,
- 0, Typename);
- decl->NamedDecl::ReadInRec(D, C);
+ = new (C) TemplateTypeParmDecl(0, SourceLocation(), 0, Typename,
+ QualType());
+ decl->TypeDecl::ReadInRec(D, C);
return decl;
}
Modified: cfe/trunk/lib/AST/DeclTemplate.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/DeclTemplate.cpp?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/lib/AST/DeclTemplate.cpp (original)
+++ cfe/trunk/lib/AST/DeclTemplate.cpp Thu Feb 5 17:33:38 2009
@@ -78,7 +78,8 @@
TemplateTypeParmDecl::Create(ASTContext &C, DeclContext *DC,
SourceLocation L, unsigned D, unsigned P,
IdentifierInfo *Id, bool Typename) {
- return new (C) TemplateTypeParmDecl(DC, L, D, P, Id, Typename);
+ QualType Type = C.getTemplateTypeParmType(D, P, Id);
+ return new (C) TemplateTypeParmDecl(DC, L, Id, Typename, Type);
}
//===----------------------------------------------------------------------===//
Modified: cfe/trunk/lib/AST/Type.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Type.cpp?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/lib/AST/Type.cpp (original)
+++ cfe/trunk/lib/AST/Type.cpp Thu Feb 5 17:33:38 2009
@@ -1138,7 +1138,12 @@
void TemplateTypeParmType::getAsStringInternal(std::string &InnerString) const {
if (!InnerString.empty()) // Prefix the basic type, e.g. 'parmname X'.
InnerString = ' ' + InnerString;
- InnerString = getDecl()->getIdentifier()->getName() + InnerString;
+
+ if (!Name)
+ InnerString = "type-parameter-" + llvm::utostr_32(Depth) + '-' +
+ llvm::utostr_32(Index) + InnerString;
+ else
+ InnerString = Name->getName() + InnerString;
}
void ObjCInterfaceType::getAsStringInternal(std::string &InnerString) const {
Modified: cfe/trunk/lib/AST/TypeSerialization.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/TypeSerialization.cpp?rev=63899&r1=63898&r2=63899&view=diff
==============================================================================
--- cfe/trunk/lib/AST/TypeSerialization.cpp (original)
+++ cfe/trunk/lib/AST/TypeSerialization.cpp Thu Feb 5 17:33:38 2009
@@ -127,7 +127,7 @@
break;
case Type::TemplateTypeParm:
- D.RegisterPtr(PtrID,TemplateTypeParmType::CreateImpl(Context, D));
+ D.RegisterPtr(PtrID, TemplateTypeParmType::CreateImpl(Context, D));
break;
case Type::VariableArray:
@@ -364,20 +364,18 @@
//===----------------------------------------------------------------------===//
void TemplateTypeParmType::EmitImpl(Serializer& S) const {
- S.EmitPtr(getDecl());
+ S.EmitInt(Depth);
+ S.EmitInt(Index);
+ S.EmitPtr(Name);
}
Type* TemplateTypeParmType::CreateImpl(ASTContext& Context, Deserializer& D) {
- std::vector<Type*>& Types =
- const_cast<std::vector<Type*>&>(Context.getTypes());
-
- TemplateTypeParmType* T = new TemplateTypeParmType(NULL);
- Types.push_back(T);
-
- D.ReadPtr(T->Decl); // May be backpatched.
- return T;
+ unsigned Depth = D.ReadInt();
+ unsigned Index = D.ReadInt();
+ IdentifierInfo *Name = D.ReadPtr<IdentifierInfo>();
+ return Context.getTemplateTypeParmType(Depth, Index, Name).getTypePtr();
}
-
+
//===----------------------------------------------------------------------===//
// VariableArrayType
//===----------------------------------------------------------------------===//
More information about the cfe-commits
mailing list