aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/Sema/Sema.h179
-rw-r--r--lib/Sema/SemaAttr.cpp6
-rw-r--r--lib/Sema/SemaCXXScopeSpec.cpp28
-rw-r--r--lib/Sema/SemaDecl.cpp80
-rw-r--r--lib/Sema/SemaDeclCXX.cpp37
-rw-r--r--lib/Sema/SemaExpr.cpp23
-rw-r--r--lib/Sema/SemaExprCXX.cpp16
-rw-r--r--lib/Sema/SemaLookup.cpp108
-rw-r--r--lib/Sema/SemaOverload.cpp18
-rw-r--r--lib/Sema/SemaTemplate.cpp40
-rw-r--r--lib/Sema/SemaTemplateInstantiateDecl.cpp13
11 files changed, 325 insertions, 223 deletions
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h
index 011747a1dc..e6772dbe68 100644
--- a/lib/Sema/Sema.h
+++ b/lib/Sema/Sema.h
@@ -1092,7 +1092,7 @@ public:
/// of multiple declarations.
class LookupResult {
public:
- enum LookupKind {
+ enum LookupResultKind {
/// @brief No entity found met the criteria.
NotFound = 0,
@@ -1173,24 +1173,86 @@ public:
AmbiguousTagHiding
};
+ enum RedeclarationKind {
+ NotForRedeclaration,
+ ForRedeclaration
+ };
+
+ /// A little identifier for flagging temporary lookup results.
+ enum TemporaryToken {
+ Temporary
+ };
+
typedef llvm::SmallVector<NamedDecl*, 4> DeclsTy;
typedef DeclsTy::const_iterator iterator;
- LookupResult()
- : Kind(NotFound),
- Paths(0)
+ LookupResult(Sema &SemaRef, DeclarationName Name, SourceLocation NameLoc,
+ LookupNameKind LookupKind,
+ RedeclarationKind Redecl = NotForRedeclaration)
+ : ResultKind(NotFound),
+ Paths(0),
+ SemaRef(SemaRef),
+ Name(Name),
+ NameLoc(NameLoc),
+ LookupKind(LookupKind),
+ IDNS(0),
+ Redecl(Redecl != NotForRedeclaration),
+ Diagnose(Redecl == NotForRedeclaration)
{}
+
+ /// Creates a temporary lookup result, initializing its core data
+ /// using the information from another result. Diagnostics are always
+ /// disabled.
+ LookupResult(TemporaryToken _, const LookupResult &Other)
+ : ResultKind(NotFound),
+ Paths(0),
+ SemaRef(Other.SemaRef),
+ Name(Other.Name),
+ NameLoc(Other.NameLoc),
+ LookupKind(Other.LookupKind),
+ IDNS(Other.IDNS),
+ Redecl(Other.Redecl),
+ Diagnose(false)
+ {}
+
~LookupResult() {
+ if (Diagnose) diagnose();
if (Paths) deletePaths(Paths);
}
+ /// Gets the name to look up.
+ DeclarationName getLookupName() const {
+ return Name;
+ }
+
+ /// Gets the kind of lookup to perform.
+ LookupNameKind getLookupKind() const {
+ return LookupKind;
+ }
+
+ /// True if this lookup is just looking for an existing declaration.
+ bool isForRedeclaration() const {
+ return Redecl;
+ }
+
+ /// The identifier namespace of this lookup. This information is
+ /// private to the lookup routines.
+ unsigned getIdentifierNamespace() const {
+ assert(IDNS);
+ return IDNS;
+ }
+
+ void setIdentifierNamespace(unsigned NS) {
+ IDNS = NS;
+ }
+
bool isAmbiguous() const {
- return getKind() == Ambiguous;
+ return getResultKind() == Ambiguous;
}
- LookupKind getKind() const {
+ LookupResultKind getResultKind() const {
sanity();
- return Kind;
+ return ResultKind;
}
AmbiguityKind getAmbiguityKind() const {
@@ -1226,14 +1288,14 @@ public:
}
} else
Decls.push_back(D->getUnderlyingDecl());
- Kind = Found;
+ ResultKind = Found;
}
/// \brief Add all the declarations from another set of lookup
/// results.
void addAllDecls(const LookupResult &Other) {
Decls.append(Other.begin(), Other.end());
- Kind = Found;
+ ResultKind = Found;
}
/// \brief Hides a set of declarations.
@@ -1267,13 +1329,14 @@ public:
/// This is intended for users who have examined the result kind
/// and are certain that there is only one result.
NamedDecl *getFoundDecl() const {
- assert(getKind() == Found && "getFoundDecl called on non-unique result");
+ assert(getResultKind() == Found
+ && "getFoundDecl called on non-unique result");
return *Decls.begin();
}
/// \brief Asks if the result is a single tag decl.
bool isSingleTagDecl() const {
- return getKind() == Found && isa<TagDecl>(getFoundDecl());
+ return getResultKind() == Found && isa<TagDecl>(getFoundDecl());
}
/// \brief Make these results show that the name was found in
@@ -1297,17 +1360,53 @@ public:
/// \brief Clears out any current state.
void clear() {
- Kind = NotFound;
+ ResultKind = NotFound;
Decls.clear();
if (Paths) deletePaths(Paths);
Paths = NULL;
}
+ /// \brief Clears out any current state and re-initializes for a
+ /// different kind of lookup.
+ void clear(LookupNameKind Kind) {
+ clear();
+ LookupKind = Kind;
+ }
+
void print(llvm::raw_ostream &);
+ /// Suppress the diagnostics that would normally fire because of this
+ /// lookup. This happens during (e.g.) redeclaration lookups.
+ void suppressDiagnostics() {
+ Diagnose = false;
+ }
+
+ /// Sets a 'context' source range.
+ void setContextRange(SourceRange SR) {
+ NameContextRange = SR;
+ }
+
+ /// Gets the source range of the context of this name; for C++
+ /// qualified lookups, this is the source range of the scope
+ /// specifier.
+ SourceRange getContextRange() const {
+ return NameContextRange;
+ }
+
+ /// Gets the location of the identifier. This isn't always defined:
+ /// sometimes we're doing lookups on synthesized names.
+ SourceLocation getNameLoc() const {
+ return NameLoc;
+ }
+
private:
+ void diagnose() {
+ if (isAmbiguous())
+ SemaRef.DiagnoseAmbiguousLookup(*this);
+ }
+
void setAmbiguous(AmbiguityKind AK) {
- Kind = Ambiguous;
+ ResultKind = Ambiguous;
Ambiguity = AK;
}
@@ -1315,29 +1414,41 @@ public:
// Sanity checks.
void sanity() const {
- assert(Kind != NotFound || Decls.size() == 0);
- assert(Kind != Found || Decls.size() == 1);
- assert(Kind == NotFound || Kind == Found ||
- (Kind == Ambiguous && Ambiguity == AmbiguousBaseSubobjects)
+ assert(ResultKind != NotFound || Decls.size() == 0);
+ assert(ResultKind != Found || Decls.size() == 1);
+ assert(ResultKind == NotFound || ResultKind == Found ||
+ (ResultKind == Ambiguous && Ambiguity == AmbiguousBaseSubobjects)
|| Decls.size() > 1);
- assert((Paths != NULL) == (Kind == Ambiguous &&
+ assert((Paths != NULL) == (ResultKind == Ambiguous &&
(Ambiguity == AmbiguousBaseSubobjectTypes ||
Ambiguity == AmbiguousBaseSubobjects)));
}
static void deletePaths(CXXBasePaths *);
- LookupKind Kind;
+ // Results.
+ LookupResultKind ResultKind;
AmbiguityKind Ambiguity; // ill-defined unless ambiguous
DeclsTy Decls;
CXXBasePaths *Paths;
+
+ // Parameters.
+ Sema &SemaRef;
+ DeclarationName Name;
+ SourceLocation NameLoc;
+ SourceRange NameContextRange;
+ LookupNameKind LookupKind;
+ unsigned IDNS; // ill-defined until set by lookup
+ bool Redecl;
+
+ bool Diagnose;
};
private:
typedef llvm::SmallVector<LookupResult, 3> LookupResultsVecTy;
- bool CppLookupName(LookupResult &R, Scope *S, DeclarationName Name,
- LookupNameKind NameKind, bool RedeclarationOnly);
+ bool CppLookupName(LookupResult &R, Scope *S);
+
public:
/// Determines whether D is a suitable lookup result according to the
/// lookup criteria.
@@ -1376,27 +1487,17 @@ public:
/// ambiguity and overloaded.
NamedDecl *LookupSingleName(Scope *S, DeclarationName Name,
LookupNameKind NameKind,
- bool RedeclarationOnly = false) {
- LookupResult R;
- LookupName(R, S, Name, NameKind, RedeclarationOnly);
+ LookupResult::RedeclarationKind Redecl
+ = LookupResult::NotForRedeclaration) {
+ LookupResult R(*this, Name, SourceLocation(), NameKind, Redecl);
+ LookupName(R, S);
return R.getAsSingleDecl(Context);
}
bool LookupName(LookupResult &R, Scope *S,
- DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false,
- bool AllowBuiltinCreation = false,
- SourceLocation Loc = SourceLocation());
- bool LookupQualifiedName(LookupResult &R, DeclContext *LookupCtx,
- DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false);
+ bool AllowBuiltinCreation = false);
+ bool LookupQualifiedName(LookupResult &R, DeclContext *LookupCtx);
bool LookupParsedName(LookupResult &R, Scope *S, const CXXScopeSpec *SS,
- DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false,
bool AllowBuiltinCreation = false,
- SourceLocation Loc = SourceLocation(),
bool EnteringContext = false);
ObjCProtocolDecl *LookupProtocol(IdentifierInfo *II);
@@ -1414,9 +1515,7 @@ public:
AssociatedNamespaceSet &AssociatedNamespaces,
AssociatedClassSet &AssociatedClasses);
- bool DiagnoseAmbiguousLookup(LookupResult &Result, DeclarationName Name,
- SourceLocation NameLoc,
- SourceRange LookupRange = SourceRange());
+ bool DiagnoseAmbiguousLookup(LookupResult &Result);
//@}
ObjCInterfaceDecl *getObjCInterfaceDecl(IdentifierInfo *Id);
diff --git a/lib/Sema/SemaAttr.cpp b/lib/Sema/SemaAttr.cpp
index 0a5335a2be..e2eb87f25e 100644
--- a/lib/Sema/SemaAttr.cpp
+++ b/lib/Sema/SemaAttr.cpp
@@ -179,10 +179,8 @@ void Sema::ActOnPragmaUnused(const Token *Identifiers, unsigned NumIdentifiers,
for (unsigned i = 0; i < NumIdentifiers; ++i) {
const Token &Tok = Identifiers[i];
IdentifierInfo *Name = Tok.getIdentifierInfo();
- LookupResult Lookup;
- LookupParsedName(Lookup, curScope, NULL, Name,LookupOrdinaryName,
- false, true, Tok.getLocation());
- // FIXME: Handle Lookup.isAmbiguous?
+ LookupResult Lookup(*this, Name, Tok.getLocation(), LookupOrdinaryName);
+ LookupParsedName(Lookup, curScope, NULL, true);
NamedDecl *ND = Lookup.getAsSingleDecl(Context);
diff --git a/lib/Sema/SemaCXXScopeSpec.cpp b/lib/Sema/SemaCXXScopeSpec.cpp
index ce3fb5f83c..b196dcec6f 100644
--- a/lib/Sema/SemaCXXScopeSpec.cpp
+++ b/lib/Sema/SemaCXXScopeSpec.cpp
@@ -307,8 +307,9 @@ NamedDecl *Sema::FindFirstQualifierInScope(Scope *S, NestedNameSpecifier *NNS) {
if (NNS->getKind() != NestedNameSpecifier::Identifier)
return 0;
- LookupResult Found;
- LookupName(Found, S, NNS->getAsIdentifier(), LookupNestedNameSpecifierName);
+ LookupResult Found(*this, NNS->getAsIdentifier(), SourceLocation(),
+ LookupNestedNameSpecifierName);
+ LookupName(Found, S);
assert(!Found.isAmbiguous() && "Cannot handle ambiguities here yet");
NamedDecl *Result = Found.getAsSingleDecl(Context);
@@ -336,6 +337,8 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
NestedNameSpecifier *Prefix
= static_cast<NestedNameSpecifier *>(SS.getScopeRep());
+ LookupResult Found(*this, &II, IdLoc, LookupNestedNameSpecifierName);
+
// Determine where to perform name lookup
DeclContext *LookupCtx = 0;
bool isDependent = false;
@@ -350,9 +353,10 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
// so long into the context associated with the prior nested-name-specifier.
LookupCtx = computeDeclContext(SS, EnteringContext);
isDependent = isDependentScopeSpecifier(SS);
+ Found.setContextRange(SS.getRange());
}
- LookupResult Found;
+
bool ObjectTypeSearchedInScope = false;
if (LookupCtx) {
// Perform "qualified" name lookup into the declaration context we
@@ -364,10 +368,9 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(SS))
return 0;
- LookupQualifiedName(Found, LookupCtx, &II, LookupNestedNameSpecifierName,
- false);
+ LookupQualifiedName(Found, LookupCtx);
- if (!ObjectType.isNull() && Found.getKind() == LookupResult::NotFound) {
+ if (!ObjectType.isNull() && Found.empty()) {
// C++ [basic.lookup.classref]p4:
// If the id-expression in a class member access is a qualified-id of
// the form
@@ -389,7 +392,7 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
// reconstruct the result from when name lookup was performed at template
// definition time.
if (S)
- LookupName(Found, S, &II, LookupNestedNameSpecifierName);
+ LookupName(Found, S);
else if (ScopeLookupResult)
Found.addDecl(ScopeLookupResult);
@@ -406,7 +409,7 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
return NestedNameSpecifier::Create(Context, Prefix, &II);
} else {
// Perform unqualified name lookup in the current scope.
- LookupName(Found, S, &II, LookupNestedNameSpecifierName);
+ LookupName(Found, S);
}
// FIXME: Deal with ambiguities cleanly.
@@ -423,9 +426,8 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
// scope, reconstruct the result from the template instantiation itself.
NamedDecl *OuterDecl;
if (S) {
- LookupResult FoundOuter;
- LookupName(FoundOuter, S, &II, LookupNestedNameSpecifierName);
- // FIXME: Handle ambiguities!
+ LookupResult FoundOuter(*this, &II, IdLoc, LookupNestedNameSpecifierName);
+ LookupName(FoundOuter, S);
OuterDecl = FoundOuter.getAsSingleDecl(Context);
} else
OuterDecl = ScopeLookupResult;
@@ -467,8 +469,8 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
// ordinary name lookup, which can help us produce better error
// messages.
if (!SD) {
- Found.clear();
- LookupName(Found, S, &II, LookupOrdinaryName);
+ Found.clear(LookupOrdinaryName);
+ LookupName(Found, S);
SD = Found.getAsSingleDecl(Context);
}
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index 502a0f1ab2..ecea71d7ed 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -87,11 +87,11 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
II, SS->getRange()).getAsOpaquePtr();
}
- LookupResult Result;
- LookupParsedName(Result, S, SS, &II, LookupOrdinaryName, false, false);
+ LookupResult Result(*this, &II, NameLoc, LookupOrdinaryName);
+ LookupParsedName(Result, S, SS, false);
NamedDecl *IIDecl = 0;
- switch (Result.getKind()) {
+ switch (Result.getResultKind()) {
case LookupResult::NotFound:
case LookupResult::FoundOverloaded:
return 0;
@@ -102,8 +102,10 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
// diagnose the error then. If we don't do this, then the error
// about hiding the type will be immediately followed by an error
// that only makes sense if the identifier was treated like a type.
- if (Result.getAmbiguityKind() == LookupResult::AmbiguousTagHiding)
+ if (Result.getAmbiguityKind() == LookupResult::AmbiguousTagHiding) {
+ Result.suppressDiagnostics();
return 0;
+ }
// Look to see if we have a type anywhere in the list of results.
for (LookupResult::iterator Res = Result.begin(), ResEnd = Result.end();
@@ -123,6 +125,7 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
// perform this lookup again (e.g., as an object name), which
// will produce the ambiguity, or will complain that it expected
// a type name.
+ Result.suppressDiagnostics();
return 0;
}
@@ -130,7 +133,6 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
// ambiguity and then return that type. This might be the right
// answer, or it might not be, but it suppresses any attempt to
// perform the name lookup again.
- DiagnoseAmbiguousLookup(Result, DeclarationName(&II), NameLoc);
break;
case LookupResult::Found:
@@ -143,7 +145,7 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
QualType T;
if (TypeDecl *TD = dyn_cast<TypeDecl>(IIDecl)) {
DiagnoseUseOfDecl(IIDecl, NameLoc);
-
+
// C++ [temp.local]p2:
// Within the scope of a class template specialization or
// partial specialization, when the injected-class-name is
@@ -163,10 +165,12 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
T = getQualifiedNameType(*SS, T);
} else if (ObjCInterfaceDecl *IDecl = dyn_cast<ObjCInterfaceDecl>(IIDecl)) {
- DiagnoseUseOfDecl(IIDecl, NameLoc);
T = Context.getObjCInterfaceType(IDecl);
- } else
+ } else {
+ // If it's not plausibly a type, suppress diagnostics.
+ Result.suppressDiagnostics();
return 0;
+ }
return T.getAsOpaquePtr();
}
@@ -178,9 +182,10 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc,
/// where the user forgot to specify the tag.
DeclSpec::TST Sema::isTagName(IdentifierInfo &II, Scope *S) {
// Do a tag name lookup in this scope.
- LookupResult R;
- LookupName(R, S, &II, LookupTagName, false, false);
- if (R.getKind() == LookupResult::Found)
+ LookupResult R(*this, &II, SourceLocation(), LookupTagName);
+ LookupName(R, S, false);
+ R.suppressDiagnostics();
+ if (R.getResultKind() == LookupResult::Found)
if (const TagDecl *TD = dyn_cast<TagDecl>(R.getAsSingleDecl(Context))) {
switch (TD->getTagKind()) {
case TagDecl::TK_struct: return DeclSpec::TST_struct;
@@ -1415,9 +1420,9 @@ bool Sema::InjectAnonymousStructOrUnionMembers(Scope *S, DeclContext *Owner,
FEnd = AnonRecord->field_end();
F != FEnd; ++F) {
if ((*F)->getDeclName()) {
- LookupResult R;
- LookupQualifiedName(R, Owner, (*F)->getDeclName(),
- LookupOrdinaryName, true);
+ LookupResult R(*this, (*F)->getDeclName(), SourceLocation(),
+ LookupOrdinaryName, LookupResult::ForRedeclaration);
+ LookupQualifiedName(R, Owner);
NamedDecl *PrevDecl = R.getAsSingleDecl(Context);
if (PrevDecl && !isa<TagDecl>(PrevDecl)) {
// C++ [class.union]p2:
@@ -1784,10 +1789,10 @@ Sema::HandleDeclarator(Scope *S, Declarator &D,
NameKind = LookupRedeclarationWithLinkage;
DC = CurContext;
- LookupResult R;
- LookupName(R, S, Name, NameKind, true,
- NameKind == LookupRedeclarationWithLinkage,
- D.getIdentifierLoc());
+ LookupResult R(*this, Name, D.getIdentifierLoc(), NameKind,
+ LookupResult::ForRedeclaration);
+
+ LookupName(R, S, NameKind == LookupRedeclarationWithLinkage);
PrevDecl = R.getAsSingleDecl(Context);
} else { // Something like "int foo::x;"
DC = computeDeclContext(D.getCXXScopeSpec(), true);
@@ -1808,8 +1813,9 @@ Sema::HandleDeclarator(Scope *S, Declarator &D,
RequireCompleteDeclContext(D.getCXXScopeSpec()))
return DeclPtrTy();
- LookupResult Res;
- LookupQualifiedName(Res, DC, Name, LookupOrdinaryName, true);
+ LookupResult Res(*this, Name, D.getIdentifierLoc(), LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
+ LookupQualifiedName(Res, DC);
PrevDecl = Res.getAsSingleDecl(Context);
// C++ 7.3.1.2p2:
@@ -2923,8 +2929,9 @@ Sema::ActOnFunctionDeclarator(Scope* S, Declarator& D, DeclContext* DC,
<< Name << DC << D.getCXXScopeSpec().getRange();
NewFD->setInvalidDecl();
- LookupResult Prev;
- LookupQualifiedName(Prev, DC, Name, LookupOrdinaryName, true);
+ LookupResult Prev(*this, Name, D.getIdentifierLoc(), LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
+ LookupQualifiedName(Prev, DC);
assert(!Prev.isAmbiguous() &&
"Cannot have an ambiguity in previous-declaration lookup");
for (LookupResult::iterator Func = Prev.begin(), FuncEnd = Prev.end();
@@ -4302,7 +4309,8 @@ Sema::DeclPtrTy Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK,
bool isStdBadAlloc = false;
bool Invalid = false;
- bool RedeclarationOnly = (TUK != TUK_Reference);
+ LookupResult::RedeclarationKind Redecl =
+ (LookupResult::RedeclarationKind) (TUK != TUK_Reference);
if (Name && SS.isNotEmpty()) {
// We have a nested-name tag ('struct foo::bar').
@@ -4329,15 +4337,13 @@ Sema::DeclPtrTy Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK,
DC = computeDeclContext(SS, true);
SearchDC = DC;
// Look-up name inside 'foo::'.
- LookupResult R;
- LookupQualifiedName(R, DC, Name, LookupTagName, RedeclarationOnly);
+ LookupResult R(*this, Name, NameLoc, LookupTagName, Redecl);
+ LookupQualifiedName(R, DC);
- if (R.isAmbiguous()) {
- DiagnoseAmbiguousLookup(R, Name, NameLoc, SS.getRange());
+ if (R.isAmbiguous())
return DeclPtrTy();
- }
- if (R.getKind() == LookupResult::Found)
+ if (R.getResultKind() == LookupResult::Found)
PrevDecl = dyn_cast<TagDecl>(R.getFoundDecl());
// A tag 'foo::bar' must already exist.
@@ -4353,10 +4359,9 @@ Sema::DeclPtrTy Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK,
// FIXME: We're looking into outer scopes here, even when we
// shouldn't be. Doing so can result in ambiguities that we
// shouldn't be diagnosing.
- LookupResult R;
- LookupName(R, S, Name, LookupTagName, RedeclarationOnly);
+ LookupResult R(*this, Name, NameLoc, LookupTagName, Redecl);
+ LookupName(R, S);
if (R.isAmbiguous()) {
- DiagnoseAmbiguousLookup(R, Name, NameLoc);
// FIXME: This is not best way to recover from case like:
//
// struct S s;
@@ -4618,8 +4623,9 @@ CreateNewDecl:
// shall not be declared with the same name as a typedef-name
// that is declared in that scope and refers to a type other
// than the class or enumeration itself.
- LookupResult Lookup;
- LookupName(Lookup, S, Name, LookupOrdinaryName, true);
+ LookupResult Lookup(*this, Name, NameLoc, LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
+ LookupName(Lookup, S);
TypedefDecl *PrevTypedef = 0;
if (NamedDecl *Prev = Lookup.getAsSingleDecl(Context))
PrevTypedef = dyn_cast<TypedefDecl>(Prev);
@@ -4838,7 +4844,8 @@ FieldDecl *Sema::HandleField(Scope *S, RecordDecl *Record,
if (D.getDeclSpec().isThreadSpecified())
Diag(D.getDeclSpec().getThreadSpecLoc(), diag::err_invalid_thread);
- NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName, true);
+ NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName,
+ LookupResult::ForRedeclaration);
if (PrevDecl && PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
@@ -5223,7 +5230,8 @@ Sema::DeclPtrTy Sema::ActOnIvar(Scope *S,
DInfo, ac, (Expr *)BitfieldWidth);
if (II) {
- NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName, true);
+ NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName,
+ LookupResult::ForRedeclaration);
if (PrevDecl && isDeclInScope(PrevDecl, EnclosingContext, S)
&& !isa<TagDecl>(PrevDecl)) {
Diag(Loc, diag::err_duplicate_member) << II;
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index e956ffec49..18e62291e5 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -2652,7 +2652,8 @@ Sema::DeclPtrTy Sema::ActOnStartNamespaceDef(Scope *NamespcScope,
// in that declarative region, it is treated as an original-namespace-name.
NamedDecl *PrevDecl
- = LookupSingleName(DeclRegionScope, II, LookupOrdinaryName, true);
+ = LookupSingleName(DeclRegionScope, II, LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
if (NamespaceDecl *OrigNS = dyn_cast_or_null<NamespaceDecl>(PrevDecl)) {
// This is an extended namespace definition.
@@ -2760,12 +2761,11 @@ Sema::DeclPtrTy Sema::ActOnUsingDirective(Scope *S,
UsingDirectiveDecl *UDir = 0;
// Lookup namespace name.
- LookupResult R;
- LookupParsedName(R, S, &SS, NamespcName, LookupNamespaceName, false);
- if (R.isAmbiguous()) {
- DiagnoseAmbiguousLookup(R, NamespcName, IdentLoc);
+ LookupResult R(*this, NamespcName, IdentLoc, LookupNamespaceName);
+ LookupParsedName(R, S, &SS);
+ if (R.isAmbiguous())
return DeclPtrTy();
- }
+
if (!R.empty()) {
NamedDecl *NS = R.getFoundDecl();
// FIXME: Namespace aliases!
@@ -2913,8 +2913,8 @@ NamedDecl *Sema::BuildUsingDeclaration(SourceLocation UsingLoc,
}
// Lookup target name.
- LookupResult R;
- LookupQualifiedName(R, LookupContext, Name, LookupOrdinaryName);
+ LookupResult R(*this, Name, IdentLoc, LookupOrdinaryName);
+ LookupQualifiedName(R, LookupContext);
if (R.empty()) {
Diag(IdentLoc, diag::err_no_member)
@@ -2959,12 +2959,13 @@ Sema::DeclPtrTy Sema::ActOnNamespaceAliasDef(Scope *S,
IdentifierInfo *Ident) {
// Lookup the namespace name.
- LookupResult R;
- LookupParsedName(R, S, &SS, Ident, LookupNamespaceName, false);
+ LookupResult R(*this, Ident, IdentLoc, LookupNamespaceName);
+ LookupParsedName(R, S, &SS);
// Check if we have a previous declaration with the same name.
if (NamedDecl *PrevDecl
- = LookupSingleName(S, Alias, LookupOrdinaryName, true)) {
+ = LookupSingleName(S, Alias, LookupOrdinaryName,
+ LookupResult::ForRedeclaration)) {
if (NamespaceAliasDecl *AD = dyn_cast<NamespaceAliasDecl>(PrevDecl)) {
// We already have an alias with the same name that points to the same
// namespace, so don't create a new one.
@@ -2980,10 +2981,8 @@ Sema::DeclPtrTy Sema::ActOnNamespaceAliasDef(Scope *S,
return DeclPtrTy();
}
- if (R.isAmbiguous()) {
- DiagnoseAmbiguousLookup(R, Ident, IdentLoc);
+ if (R.isAmbiguous())
return DeclPtrTy();
- }
if (R.empty()) {
Diag(NamespaceLoc, diag::err_expected_namespace_name) << SS.getRange();
@@ -4613,8 +4612,9 @@ Sema::ActOnFriendFunctionDecl(Scope *S,
// FIXME: handle dependent contexts
if (!DC) return DeclPtrTy();
- LookupResult R;
- LookupQualifiedName(R, DC, Name, LookupOrdinaryName, true);
+ LookupResult R(*this, Name, Loc, LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
+ LookupQualifiedName(R, DC);
PrevDecl = R.getAsSingleDecl(Context);
// If searching in that context implicitly found a declaration in
@@ -4648,8 +4648,9 @@ Sema::ActOnFriendFunctionDecl(Scope *S,
while (DC->isRecord())
DC = DC->getParent();
- LookupResult R;
- LookupQualifiedName(R, DC, Name, LookupOrdinaryName, true);
+ LookupResult R(*this, Name, Loc, LookupOrdinaryName,
+ LookupResult::ForRedeclaration);
+ LookupQualifiedName(R, DC);
PrevDecl = R.getAsSingleDecl(Context);
// TODO: decide what we think about using declarations.
diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp
index a74d50365e..535632e6db 100644
--- a/lib/Sema/SemaExpr.cpp
+++ b/lib/Sema/SemaExpr.cpp
@@ -681,15 +681,11 @@ Sema::ActOnDeclarationNameExpr(Scope *S, SourceLocation Loc,
isAddressOfOperand));
}
- LookupResult Lookup;
- LookupParsedName(Lookup, S, SS, Name, LookupOrdinaryName, false, true, Loc);
+ LookupResult Lookup(*this, Name, Loc, LookupOrdinaryName);
+ LookupParsedName(Lookup, S, SS, true);
- if (Lookup.isAmbiguous()) {
- DiagnoseAmbiguousLookup(Lookup, Name, Loc,
- SS && SS->isSet() ? SS->getRange()
- : SourceRange());
+ if (Lookup.isAmbiguous())
return ExprError();
- }
NamedDecl *D = Lookup.getAsSingleDecl(Context);
@@ -2075,17 +2071,14 @@ Sema::BuildMemberReferenceExpr(Scope *S, ExprArg Base, SourceLocation OpLoc,
}
// The record definition is complete, now make sure the member is valid.
- LookupResult Result;
- LookupQualifiedName(Result, DC, MemberName, LookupMemberName, false);
+ LookupResult Result(*this, MemberName, MemberLoc, LookupMemberName);
+ LookupQualifiedName(Result, DC);
if (Result.empty())
return ExprError(Diag(MemberLoc, diag::err_no_member)
<< MemberName << DC << BaseExpr->getSourceRange());
- if (Result.isAmbiguous()) {
- DiagnoseAmbiguousLookup(Result, MemberName, MemberLoc,
- BaseExpr->getSourceRange());
+ if (Result.isAmbiguous())
return ExprError();
- }
NamedDecl *MemberDecl = Result.getAsSingleDecl(Context);
@@ -5887,8 +5880,8 @@ Sema::OwningExprResult Sema::ActOnBuiltinOffsetOf(Scope *S,
}
}
- LookupResult R;
- LookupQualifiedName(R, RD, OC.U.IdentInfo, LookupMemberName);
+ LookupResult R(*this, OC.U.IdentInfo, OC.LocStart, LookupMemberName);
+ LookupQualifiedName(R, RD);
FieldDecl *MemberDecl
= dyn_cast_or_null<FieldDecl>(R.getAsSingleDecl(Context));
diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp
index 3fcacfc9f3..fdce0e6c2d 100644
--- a/lib/Sema/SemaExprCXX.cpp
+++ b/lib/Sema/SemaExprCXX.cpp
@@ -34,8 +34,8 @@ Sema::ActOnCXXTypeid(SourceLocation OpLoc, SourceLocation LParenLoc,
TyOrExpr = GetTypeFromParser(TyOrExpr).getAsOpaquePtr();
IdentifierInfo *TypeInfoII = &PP.getIdentifierTable().get("type_info");
- LookupResult R;
- LookupQualifiedName(R, StdNamespace, TypeInfoII, LookupTagName);
+ LookupResult R(*this, TypeInfoII, SourceLocation(), LookupTagName);
+ LookupQualifiedName(R, StdNamespace);
Decl *TypeInfoDecl = R.getAsSingleDecl(Context);
RecordDecl *TypeInfoRecordDecl = dyn_cast_or_null<RecordDecl>(TypeInfoDecl);
if (!TypeInfoRecordDecl)
@@ -567,8 +567,8 @@ bool Sema::FindAllocationOverload(SourceLocation StartLoc, SourceRange Range,
DeclarationName Name, Expr** Args,
unsigned NumArgs, DeclContext *Ctx,
bool AllowMissing, FunctionDecl *&Operator) {
- LookupResult R;
- LookupQualifiedName(R, Ctx, Name, LookupOrdinaryName);
+ LookupResult R(*this, Name, StartLoc, LookupOrdinaryName);
+ LookupQualifiedName(R, Ctx);
if (R.empty()) {
if (AllowMissing)
return false;
@@ -756,14 +756,12 @@ void Sema::DeclareGlobalAllocationFunction(DeclarationName Name,
bool Sema::FindDeallocationFunction(SourceLocation StartLoc, CXXRecordDecl *RD,
DeclarationName Name,
FunctionDecl* &Operator) {
- LookupResult Found;
+ LookupResult Found(*this, Name, StartLoc, LookupOrdinaryName);
// Try to find operator delete/operator delete[] in class scope.
- LookupQualifiedName(Found, RD, Name, LookupOrdinaryName);
+ LookupQualifiedName(Found, RD);
- if (Found.isAmbiguous()) {
- DiagnoseAmbiguousLookup(Found, Name, StartLoc);
+ if (Found.isAmbiguous())
return true;
- }
for (LookupResult::iterator F = Found.begin(), FEnd = Found.end();
F != FEnd; ++F) {
diff --git a/lib/Sema/SemaLookup.cpp b/lib/Sema/SemaLookup.cpp
index d45a1a8b92..1c7dce0def 100644
--- a/lib/Sema/SemaLookup.cpp
+++ b/lib/Sema/SemaLookup.cpp
@@ -248,7 +248,7 @@ void Sema::LookupResult::resolveKind() {
if (N <= 1) return;
// Don't do any extra resolution if we've already resolved as ambiguous.
- if (Kind == Ambiguous) return;
+ if (ResultKind == Ambiguous) return;
llvm::SmallPtrSet<NamedDecl*, 16> Unique;
@@ -308,9 +308,9 @@ void Sema::LookupResult::resolveKind() {
if (Ambiguous)
setAmbiguous(LookupResult::AmbiguousReference);
else if (N > 1)
- Kind = LookupResult::FoundOverloaded;
+ ResultKind = LookupResult::FoundOverloaded;
else
- Kind = LookupResult::Found;
+ ResultKind = LookupResult::Found;
}
/// @brief Converts the result of name lookup into a single (possible
@@ -391,15 +391,13 @@ void Sema::LookupResult::print(llvm::raw_ostream &Out) {
// Adds all qualifying matches for a name within a decl context to the
// given lookup result. Returns true if any matches were found.
static bool LookupDirect(Sema::LookupResult &R,
- const DeclContext *DC,
- DeclarationName Name,
- Sema::LookupNameKind NameKind,
- unsigned IDNS) {
+ const DeclContext *DC) {
bool Found = false;
DeclContext::lookup_const_iterator I, E;
- for (llvm::tie(I, E) = DC->lookup(Name); I != E; ++I)
- if (Sema::isAcceptableLookupResult(*I, NameKind, IDNS))
+ for (llvm::tie(I, E) = DC->lookup(R.getLookupName()); I != E; ++I)
+ if (Sema::isAcceptableLookupResult(*I, R.getLookupKind(),
+ R.getIdentifierNamespace()))
R.addDecl(*I), Found = true;
return Found;
@@ -408,13 +406,12 @@ static bool LookupDirect(Sema::LookupResult &R,
// Performs C++ unqualified lookup into the given file context.
static bool
CppNamespaceLookup(Sema::LookupResult &R, ASTContext &Context, DeclContext *NS,
- DeclarationName Name, Sema::LookupNameKind NameKind,
- unsigned IDNS, UnqualUsingDirectiveSet &UDirs) {
+ UnqualUsingDirectiveSet &UDirs) {
assert(NS && NS->isFileContext() && "CppNamespaceLookup() requires namespace!");
// Perform direct name lookup into the LookupCtx.
- bool Found = LookupDirect(R, NS, Name, NameKind, IDNS);
+ bool Found = LookupDirect(R, NS);
// Perform direct name lookup into the namespaces nominated by the
// using directives whose common ancestor is this namespace.
@@ -422,7 +419,7 @@ CppNamespaceLookup(Sema::LookupResult &R, ASTContext &Context, DeclContext *NS,
llvm::tie(UI, UEnd) = UDirs.getNamespacesFor(NS);
for (; UI != UEnd; ++UI)
- if (LookupDirect(R, UI->getNominatedNamespace(), Name, NameKind, IDNS))
+ if (LookupDirect(R, UI->getNominatedNamespace()))
Found = true;
R.resolveKind();
@@ -445,20 +442,23 @@ static DeclContext *findOuterContext(Scope *S) {
return 0;
}
-bool
-Sema::CppLookupName(LookupResult &R, Scope *S, DeclarationName Name,
- LookupNameKind NameKind, bool RedeclarationOnly) {
+bool Sema::CppLookupName(LookupResult &R, Scope *S) {
assert(getLangOptions().CPlusPlus &&
"Can perform only C++ lookup");
+ LookupNameKind NameKind = R.getLookupKind();
unsigned