[cfe-commits] r77647 - in /cfe/trunk: include/clang/AST/ASTContext.h include/clang/AST/Type.h lib/AST/ASTContext.cpp lib/AST/Type.cpp test/SemaTemplate/canonical-expr-type.cpp
Douglas Gregor
dgregor at apple.com
Thu Jul 30 17:23:36 PDT 2009
Author: dgregor
Date: Thu Jul 30 19:23:35 2009
New Revision: 77647
URL: http://llvm.org/viewvc/llvm-project?rev=77647&view=rev
Log:
Build canonical types for dependently-sized array types.
Modified:
cfe/trunk/include/clang/AST/ASTContext.h
cfe/trunk/include/clang/AST/Type.h
cfe/trunk/lib/AST/ASTContext.cpp
cfe/trunk/lib/AST/Type.cpp
cfe/trunk/test/SemaTemplate/canonical-expr-type.cpp
Modified: cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=77647&r1=77646&r2=77647&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Thu Jul 30 19:23:35 2009
@@ -70,7 +70,7 @@
llvm::FoldingSet<ConstantArrayType> ConstantArrayTypes;
llvm::FoldingSet<IncompleteArrayType> IncompleteArrayTypes;
std::vector<VariableArrayType*> VariableArrayTypes;
- std::vector<DependentSizedArrayType*> DependentSizedArrayTypes;
+ llvm::FoldingSet<DependentSizedArrayType> DependentSizedArrayTypes;
std::vector<DependentSizedExtVectorType*> DependentSizedExtVectorTypes;
llvm::FoldingSet<VectorType> VectorTypes;
llvm::FoldingSet<FunctionNoProtoType> FunctionNoProtoTypes;
Modified: cfe/trunk/include/clang/AST/Type.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Type.h?rev=77647&r1=77646&r2=77647&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/trunk/include/clang/AST/Type.h Thu Jul 30 19:23:35 2009
@@ -1180,17 +1180,19 @@
/// until template instantiation occurs, at which point this will
/// become either a ConstantArrayType or a VariableArrayType.
class DependentSizedArrayType : public ArrayType {
+ ASTContext &Context;
+
/// SizeExpr - An assignment expression that will instantiate to the
/// size of the array.
Stmt *SizeExpr;
/// Brackets - The left and right array brackets.
SourceRange Brackets;
- DependentSizedArrayType(QualType et, QualType can, Expr *e,
- ArraySizeModifier sm, unsigned tq,
+ DependentSizedArrayType(ASTContext &Context, QualType et, QualType can,
+ Expr *e, ArraySizeModifier sm, unsigned tq,
SourceRange brackets)
: ArrayType(DependentSizedArray, et, can, sm, tq),
- SizeExpr((Stmt*) e), Brackets(brackets) {}
+ Context(Context), SizeExpr((Stmt*) e), Brackets(brackets) {}
friend class ASTContext; // ASTContext creates these.
virtual void Destroy(ASTContext& C);
@@ -1214,9 +1216,15 @@
friend class StmtIteratorBase;
+
void Profile(llvm::FoldingSetNodeID &ID) {
- assert(0 && "Cannnot unique DependentSizedArrayTypes.");
+ Profile(ID, Context, getElementType(),
+ getSizeModifier(), getIndexTypeQualifier(), getSizeExpr());
}
+
+ static void Profile(llvm::FoldingSetNodeID &ID, ASTContext &Context,
+ QualType ET, ArraySizeModifier SizeMod,
+ unsigned TypeQuals, Expr *E);
};
/// DependentSizedExtVectorType - This type represent an extended vector type
Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=77647&r1=77646&r2=77647&view=diff
==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Thu Jul 30 19:23:35 2009
@@ -1371,8 +1371,7 @@
/// getDependentSizedArrayType - Returns a non-unique reference to
/// the type for a dependently-sized array of the specified element
-/// type. FIXME: We will need these to be uniqued, or at least
-/// comparable, at some point.
+/// type.
QualType ASTContext::getDependentSizedArrayType(QualType EltTy,
Expr *NumElts,
ArrayType::ArraySizeModifier ASM,
@@ -1381,15 +1380,38 @@
assert((NumElts->isTypeDependent() || NumElts->isValueDependent()) &&
"Size must be type- or value-dependent!");
- // Since we don't unique expressions, it isn't possible to unique
- // dependently-sized array types.
-
- DependentSizedArrayType *New =
- new (*this,8) DependentSizedArrayType(EltTy, QualType(),
- NumElts, ASM, EltTypeQuals,
- Brackets);
+ llvm::FoldingSetNodeID ID;
+ DependentSizedArrayType::Profile(ID, *this, getCanonicalType(EltTy), ASM,
+ EltTypeQuals, NumElts);
- DependentSizedArrayTypes.push_back(New);
+ void *InsertPos = 0;
+ DependentSizedArrayType *Canon
+ = DependentSizedArrayTypes.FindNodeOrInsertPos(ID, InsertPos);
+ DependentSizedArrayType *New;
+ if (Canon) {
+ // We already have a canonical version of this array type; use it as
+ // the canonical type for a newly-built type.
+ New = new (*this,8) DependentSizedArrayType(*this, EltTy,
+ QualType(Canon, 0),
+ NumElts, ASM, EltTypeQuals,
+ Brackets);
+ } else {
+ QualType CanonEltTy = getCanonicalType(EltTy);
+ if (CanonEltTy == EltTy) {
+ New = new (*this,8) DependentSizedArrayType(*this, EltTy, QualType(),
+ NumElts, ASM, EltTypeQuals,
+ Brackets);
+ DependentSizedArrayTypes.InsertNode(New, InsertPos);
+ } else {
+ QualType Canon = getDependentSizedArrayType(CanonEltTy, NumElts,
+ ASM, EltTypeQuals,
+ SourceRange());
+ New = new (*this,8) DependentSizedArrayType(*this, EltTy, Canon,
+ NumElts, ASM, EltTypeQuals,
+ Brackets);
+ }
+ }
+
Types.push_back(New);
return QualType(New, 0);
}
Modified: cfe/trunk/lib/AST/Type.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Type.cpp?rev=77647&r1=77646&r2=77647&view=diff
==============================================================================
--- cfe/trunk/lib/AST/Type.cpp (original)
+++ cfe/trunk/lib/AST/Type.cpp Thu Jul 30 19:23:35 2009
@@ -64,6 +64,18 @@
C.Deallocate(this);
}
+void DependentSizedArrayType::Profile(llvm::FoldingSetNodeID &ID,
+ ASTContext &Context,
+ QualType ET,
+ ArraySizeModifier SizeMod,
+ unsigned TypeQuals,
+ Expr *E) {
+ ID.AddPointer(ET.getAsOpaquePtr());
+ ID.AddInteger(SizeMod);
+ ID.AddInteger(TypeQuals);
+ E->Profile(ID, Context, true);
+}
+
void DependentSizedExtVectorType::Destroy(ASTContext& C) {
// FIXME: Deallocate size expression, once we're cloning properly.
// if (SizeExpr)
Modified: cfe/trunk/test/SemaTemplate/canonical-expr-type.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaTemplate/canonical-expr-type.cpp?rev=77647&r1=77646&r2=77647&view=diff
==============================================================================
--- cfe/trunk/test/SemaTemplate/canonical-expr-type.cpp (original)
+++ cfe/trunk/test/SemaTemplate/canonical-expr-type.cpp Thu Jul 30 19:23:35 2009
@@ -13,4 +13,14 @@
void f0(T x, __typeof__((f)(N)) y) { }
template<typename U, U M>
-void f0(U u, __typeof__(f(M))) { } // expected-error{{redefinition}}
\ No newline at end of file
+void f0(U u, __typeof__(f(M))) { } // expected-error{{redefinition}}
+
+// Test dependently-sized array canonicalization
+template<typename T, int N, int M>
+void f1(T (&array)[N + M]) { } // expected-note{{previous}}
+
+template<typename T, int N, int M>
+void f1(T (&array)[M + N]) { }
+
+template<typename T, int M, int N>
+void f1(T (&array)[M + N]) { } // expected-error{{redefinition}}
More information about the cfe-commits
mailing list