aboutsummaryrefslogtreecommitdiff
path: root/lib/Sema/SemaLookup.cpp
diff options
context:
space:
mode:
authorDouglas Gregor <dgregor@apple.com>2009-05-11 19:58:34 +0000
committerDouglas Gregor <dgregor@apple.com>2009-05-11 19:58:34 +0000
commit42af25f865a82022a04bedeb483ac251c4412e29 (patch)
tree579ef3cff4425baa0298aab2b3495d56ace030ba /lib/Sema/SemaLookup.cpp
parent8c8b0ad9601d6ccf3d7b2a3f77a896ef4fb4e6e9 (diff)
Implement the notions of the "current instantiation" and "unknown
specialization" within a C++ template, and permit name lookup into the current instantiation. For example, given: template<typename T, typename U> struct X { typedef T type; X* x1; // current instantiation X<T, U> *x2; // current instantiation X<U, T> *x3; // not current instantiation ::X<type, U> *x4; // current instantiation X<typename X<type, U>::type, U>: *x5; // current instantiation }; git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@71471 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaLookup.cpp')
-rw-r--r--lib/Sema/SemaLookup.cpp35
1 files changed, 29 insertions, 6 deletions
diff --git a/lib/Sema/SemaLookup.cpp b/lib/Sema/SemaLookup.cpp
index b1643bb50b..64acbe04c1 100644
--- a/lib/Sema/SemaLookup.cpp
+++ b/lib/Sema/SemaLookup.cpp
@@ -17,6 +17,7 @@
#include "clang/AST/Decl.h"
#include "clang/AST/DeclCXX.h"
#include "clang/AST/DeclObjC.h"
+#include "clang/AST/DeclTemplate.h"
#include "clang/AST/Expr.h"
#include "clang/Parse/DeclSpec.h"
#include "clang/Basic/LangOptions.h"
@@ -1117,14 +1118,37 @@ Sema::LookupParsedName(Scope *S, const CXXScopeSpec *SS,
DeclarationName Name, LookupNameKind NameKind,
bool RedeclarationOnly, bool AllowBuiltinCreation,
SourceLocation Loc) {
- if (SS) {
- if (SS->isInvalid() || RequireCompleteDeclContext(*SS))
+ if (SS && (SS->isSet() || SS->isInvalid())) {
+ // If the scope specifier is invalid, don't even look for
+ // anything.
+ if (SS->isInvalid())
return LookupResult::CreateLookupResult(Context, 0);
- if (SS->isSet()) {
- return LookupQualifiedName(computeDeclContext(*SS),
- Name, NameKind, RedeclarationOnly);
+ assert(!isUnknownSpecialization(*SS) && "Can't lookup dependent types");
+
+ if (isDependentScopeSpecifier(*SS)) {
+ // Determine whether we are looking into the current
+ // instantiation.
+ NestedNameSpecifier *NNS
+ = static_cast<NestedNameSpecifier *>(SS->getScopeRep());
+ CXXRecordDecl *Current = getCurrentInstantiationOf(NNS);
+ assert(Current && "Bad dependent scope specifier");
+
+ // We nested name specifier refers to the current instantiation,
+ // so now we will look for a member of the current instantiation
+ // (C++0x [temp.dep.type]).
+ unsigned IDNS = getIdentifierNamespacesFromLookupNameKind(NameKind, true);
+ DeclContext::lookup_iterator I, E;
+ for (llvm::tie(I, E) = Current->lookup(Context, Name); I != E; ++I)
+ if (isAcceptableLookupResult(*I, NameKind, IDNS))
+ return LookupResult::CreateLookupResult(Context, I, E);
}
+
+ if (RequireCompleteDeclContext(*SS))
+ return LookupResult::CreateLookupResult(Context, 0);
+
+ return LookupQualifiedName(computeDeclContext(*SS),
+ Name, NameKind, RedeclarationOnly);
}
return LookupName(S, Name, NameKind, RedeclarationOnly,
@@ -1601,4 +1625,3 @@ void Sema::ArgumentDependentLookup(DeclarationName Name,
}
}
}
-