diff options
author | Douglas Gregor <dgregor@apple.com> | 2011-07-01 01:22:09 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2011-07-01 01:22:09 +0000 |
commit | 678d76c02671e0584d81eee03702f54b2a02633a (patch) | |
tree | e24b7139f60bb9c95ed2bbb25c317032df148c4f /clang/lib/AST/ASTContext.cpp | |
parent | f2bcad972d5c0605199ecc8423a7d5120e48911a (diff) | |
download | bcm5719-llvm-678d76c02671e0584d81eee03702f54b2a02633a.tar.gz bcm5719-llvm-678d76c02671e0584d81eee03702f54b2a02633a.zip |
Introduce the notion of instantiation dependence into Clang's AST. A
type/expression/template argument/etc. is instantiation-dependent if
it somehow involves a template parameter, even if it doesn't meet the
requirements for the more common kinds of dependence (dependent type,
type-dependent expression, value-dependent expression).
When we see an instantiation-dependent type, we know we always need to
perform substitution into that instantiation-dependent type. This
keeps us from short-circuiting evaluation in places where we
shouldn't, and lets us properly implement C++0x [temp.type]p2.
In theory, this would also allow us to properly mangle
instantiation-dependent-but-not-dependent decltype types per the
Itanium C++ ABI, but we aren't quite there because we still mangle
based on the canonical type in cases like, e.g.,
template<unsigned> struct A { };
template<typename T>
void f(A<sizeof(sizeof(decltype(T() + T())))>) { }
template void f<int>(A<sizeof(sizeof(int))>);
and therefore get the wrong answer.
llvm-svn: 134225
Diffstat (limited to 'clang/lib/AST/ASTContext.cpp')
-rw-r--r-- | clang/lib/AST/ASTContext.cpp | 7 |
1 files changed, 6 insertions, 1 deletions
diff --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp index ec064fc2f4f..4c42393365b 100644 --- a/clang/lib/AST/ASTContext.cpp +++ b/clang/lib/AST/ASTContext.cpp @@ -2802,7 +2802,12 @@ static QualType getDecltypeForExpr(const Expr *e, const ASTContext &Context) { /// on canonical type's (which are always unique). QualType ASTContext::getDecltypeType(Expr *e) const { DecltypeType *dt; - if (e->isTypeDependent()) { + + // C++0x [temp.type]p2: + // If an expression e involves a template parameter, decltype(e) denotes a + // unique dependent type. Two such decltype-specifiers refer to the same + // type only if their expressions are equivalent (14.5.6.1). + if (e->isInstantiationDependent()) { llvm::FoldingSetNodeID ID; DependentDecltypeType::Profile(ID, *this, e); |