aboutsummaryrefslogtreecommitdiff
path: root/lib/Sema/SemaLookup.cpp
diff options
context:
space:
mode:
authorEli Bendersky <eliben@chromium.org>2013-07-15 16:08:08 -0700
committerEli Bendersky <eliben@chromium.org>2013-07-15 16:08:08 -0700
commite789858899a7b36caf11b371a97411a1582a482b (patch)
treee8c28b178b32010f73b477b3c65b5ff74437530c /lib/Sema/SemaLookup.cpp
parent99a5501f5ae5b75017dfc386d4abf648234e85df (diff)
parent20c7d45a4da9f58ad805ad1d37f92fe7dc232ec8 (diff)
Merge commit '20c7d45a4da9f58ad805ad1d37f92fe7dc232ec8'
Conflicts: lib/CodeGen/ItaniumCXXABI.cpp
Diffstat (limited to 'lib/Sema/SemaLookup.cpp')
-rw-r--r--lib/Sema/SemaLookup.cpp98
1 files changed, 87 insertions, 11 deletions
diff --git a/lib/Sema/SemaLookup.cpp b/lib/Sema/SemaLookup.cpp
index eae6269ca6..9ab3b2d08e 100644
--- a/lib/Sema/SemaLookup.cpp
+++ b/lib/Sema/SemaLookup.cpp
@@ -287,10 +287,10 @@ void LookupResult::configure() {
IDNS = getIDNS(LookupKind, SemaRef.getLangOpts().CPlusPlus,
isForRedeclaration());
- // If we're looking for one of the allocation or deallocation
- // operators, make sure that the implicitly-declared new and delete
- // operators can be found.
if (!isForRedeclaration()) {
+ // If we're looking for one of the allocation or deallocation
+ // operators, make sure that the implicitly-declared new and delete
+ // operators can be found.
switch (NameInfo.getName().getCXXOverloadedOperator()) {
case OO_New:
case OO_Delete:
@@ -302,6 +302,15 @@ void LookupResult::configure() {
default:
break;
}
+
+ // Compiler builtins are always visible, regardless of where they end
+ // up being declared.
+ if (IdentifierInfo *Id = NameInfo.getName().getAsIdentifierInfo()) {
+ if (unsigned BuiltinID = Id->getBuiltinID()) {
+ if (!SemaRef.Context.BuiltinInfo.isPredefinedLibFunction(BuiltinID))
+ AllowHidden = true;
+ }
+ }
}
}
@@ -722,7 +731,7 @@ static bool LookupDirect(Sema &S, LookupResult &R, const DeclContext *DC) {
EPI.NumExceptions = 0;
QualType ExpectedType
= R.getSema().Context.getFunctionType(R.getLookupName().getCXXNameType(),
- ArrayRef<QualType>(), EPI);
+ None, EPI);
// Perform template argument deduction against the type that we would
// expect the function to have.
@@ -875,6 +884,8 @@ bool Sema::CppLookupName(LookupResult &R, Scope *S) {
// }
// }
//
+ UnqualUsingDirectiveSet UDirs;
+ bool VisitedUsingDirectives = false;
DeclContext *OutsideOfTemplateParamDC = 0;
for (; S && !isNamespaceOrTranslationUnitScope(S); S = S->getParent()) {
DeclContext *Ctx = static_cast<DeclContext*>(S->getEntity());
@@ -945,6 +956,40 @@ bool Sema::CppLookupName(LookupResult &R, Scope *S) {
continue;
}
+ // If this is a file context, we need to perform unqualified name
+ // lookup considering using directives.
+ if (Ctx->isFileContext()) {
+ // If we haven't handled using directives yet, do so now.
+ if (!VisitedUsingDirectives) {
+ // Add using directives from this context up to the top level.
+ for (DeclContext *UCtx = Ctx; UCtx; UCtx = UCtx->getParent()) {
+ if (UCtx->isTransparentContext())
+ continue;
+
+ UDirs.visit(UCtx, UCtx);
+ }
+
+ // Find the innermost file scope, so we can add using directives
+ // from local scopes.
+ Scope *InnermostFileScope = S;
+ while (InnermostFileScope &&
+ !isNamespaceOrTranslationUnitScope(InnermostFileScope))
+ InnermostFileScope = InnermostFileScope->getParent();
+ UDirs.visitScopeChain(Initial, InnermostFileScope);
+
+ UDirs.done();
+
+ VisitedUsingDirectives = true;
+ }
+
+ if (CppNamespaceLookup(*this, R, Context, Ctx, UDirs)) {
+ R.resolveKind();
+ return true;
+ }
+
+ continue;
+ }
+
// Perform qualified name lookup into this context.
// FIXME: In some cases, we know that every name that could be found by
// this qualified name lookup will also be on the identifier chain. For
@@ -970,16 +1015,15 @@ bool Sema::CppLookupName(LookupResult &R, Scope *S) {
//
// FIXME: Cache this sorted list in Scope structure, and DeclContext, so we
// don't build it for each lookup!
-
- UnqualUsingDirectiveSet UDirs;
- UDirs.visitScopeChain(Initial, S);
- UDirs.done();
-
+ if (!VisitedUsingDirectives) {
+ UDirs.visitScopeChain(Initial, S);
+ UDirs.done();
+ }
+
// Lookup namespace scope, and global scope.
// Unqualified name lookup in C++ requires looking into scopes
// that aren't strictly lexical, and therefore we walk through the
// context as well as walking through the scopes.
-
for (; S; S = S->getParent()) {
// Check whether the IdResolver has anything in this scope.
bool Found = false;
@@ -2043,6 +2087,10 @@ addAssociatedClassesAndNamespaces(AssociatedLookup &Result, QualType Ty) {
case Type::Complex:
break;
+ // Non-deduced auto types only get here for error cases.
+ case Type::Auto:
+ break;
+
// If T is an Objective-C object or interface type, or a pointer to an
// object or interface type, the associated namespace is the global
// namespace.
@@ -2538,6 +2586,12 @@ Sema::LookupLiteralOperator(Scope *S, LookupResult &R,
bool IsRaw = false;
bool IsExactMatch = false;
+ // If the declaration we found is invalid, skip it.
+ if (D->isInvalidDecl()) {
+ F.erase();
+ continue;
+ }
+
if (FunctionDecl *FD = dyn_cast<FunctionDecl>(D)) {
if (FD->getNumParams() == 1 &&
FD->getParamDecl(0)->getType()->getAs<PointerType>())
@@ -3382,7 +3436,7 @@ class NamespaceSpecifierSet {
}
DeclContextList NamespaceSpecifierSet::BuildContextChain(DeclContext *Start) {
- assert(Start && "Bulding a context chain from a null context");
+ assert(Start && "Building a context chain from a null context");
DeclContextList Chain;
for (DeclContext *DC = Start->getPrimaryContext(); DC != NULL;
DC = DC->getLookupParent()) {
@@ -3734,6 +3788,10 @@ TypoCorrection Sema::CorrectTypo(const DeclarationNameInfo &TypoName,
if (!ActiveTemplateInstantiations.empty())
return TypoCorrection();
+ // Don't try to correct 'super'.
+ if (S && S->isInObjcMethodScope() && Typo == getSuperIdentifier())
+ return TypoCorrection();
+
NamespaceSpecifierSet Namespaces(Context, CurContext, SS);
TypoCorrectionConsumer Consumer(*this, Typo);
@@ -4114,3 +4172,21 @@ std::string TypoCorrection::getAsString(const LangOptions &LO) const {
return CorrectionName.getAsString();
}
+
+bool CorrectionCandidateCallback::ValidateCandidate(const TypoCorrection &candidate) {
+ if (!candidate.isResolved())
+ return true;
+
+ if (candidate.isKeyword())
+ return WantTypeSpecifiers || WantExpressionKeywords || WantCXXNamedCasts ||
+ WantRemainingKeywords || WantObjCSuper;
+
+ for (TypoCorrection::const_decl_iterator CDecl = candidate.begin(),
+ CDeclEnd = candidate.end();
+ CDecl != CDeclEnd; ++CDecl) {
+ if (!isa<TypeDecl>(*CDecl))
+ return true;
+ }
+
+ return WantTypeSpecifiers;
+}