Rip out the last remaining implicit use of OverloadedFunctionDecl in Sema:

LookupResult::getAsSingleDecl() is no more.  Shift Sema::LookupSingleName to
return null on overloaded results.

llvm-svn: 90309
This commit is contained in:
John McCall 2009-12-02 08:25:40 +00:00
parent a510597ef9
commit 67c0087074
9 changed files with 19 additions and 76 deletions

View File

@ -26,13 +26,6 @@ namespace clang {
/// a single declaration, a set of overloaded functions, or an
/// ambiguity. Use the getKind() method to determine which of these
/// results occurred for a given lookup.
///
/// Any non-ambiguous lookup can be converted into a single
/// (possibly NULL) @c NamedDecl* via the getAsSingleDecl() method.
/// This permits the common-case usage in C and Objective-C where
/// name lookup will always return a single declaration. Use of
/// this is largely deprecated; callers should handle the possibility
/// of multiple declarations.
class LookupResult {
public:
enum LookupResultKind {
@ -282,13 +275,6 @@ public:
}
}
/// \brief Fetch this as an unambiguous single declaration
/// (possibly an overloaded one).
///
/// This is deprecated; users should be written to handle
/// ambiguous and overloaded lookups.
NamedDecl *getAsSingleDecl(ASTContext &Context) const;
template <class DeclClass>
DeclClass *getAsSingle() const {
if (getResultKind() != Found) return 0;

View File

@ -1160,7 +1160,7 @@ public:
}
/// \brief Look up a name, looking for a single declaration. Return
/// null if no unambiguous results were found.
/// null if the results were absent, ambiguous, or overloaded.
///
/// It is preferable to use the elaborated form and explicitly handle
/// ambiguity and overloaded.

View File

@ -183,20 +183,19 @@ void Sema::ActOnPragmaUnused(const Token *Identifiers, unsigned NumIdentifiers,
LookupResult Lookup(*this, Name, Tok.getLocation(), LookupOrdinaryName);
LookupParsedName(Lookup, curScope, NULL, true);
NamedDecl *ND = Lookup.getAsSingleDecl(Context);
if (!ND) {
if (Lookup.empty()) {
Diag(PragmaLoc, diag::warn_pragma_unused_undeclared_var)
<< Name << SourceRange(Tok.getLocation());
continue;
}
if (!isa<VarDecl>(ND) || !cast<VarDecl>(ND)->hasLocalStorage()) {
VarDecl *VD = Lookup.getAsSingle<VarDecl>();
if (!VD || !VD->hasLocalStorage()) {
Diag(PragmaLoc, diag::warn_pragma_unused_expected_localvar)
<< Name << SourceRange(Tok.getLocation());
continue;
}
ND->addAttr(::new (Context) UnusedAttr());
VD->addAttr(::new (Context) UnusedAttr());
}
}

View File

@ -313,7 +313,10 @@ NamedDecl *Sema::FindFirstQualifierInScope(Scope *S, NestedNameSpecifier *NNS) {
LookupName(Found, S);
assert(!Found.isAmbiguous() && "Cannot handle ambiguities here yet");
NamedDecl *Result = Found.getAsSingleDecl(Context);
if (!Found.isSingleResult())
return 0;
NamedDecl *Result = Found.getFoundDecl();
if (isAcceptableNestedNameSpecifier(Result))
return Result;
@ -414,7 +417,7 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
}
// FIXME: Deal with ambiguities cleanly.
NamedDecl *SD = Found.getAsSingleDecl(Context);
NamedDecl *SD = Found.getAsSingle<NamedDecl>();
if (isAcceptableNestedNameSpecifier(SD)) {
if (!ObjectType.isNull() && !ObjectTypeSearchedInScope) {
// C++ [basic.lookup.classref]p4:
@ -429,7 +432,7 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
if (S) {
LookupResult FoundOuter(*this, &II, IdLoc, LookupNestedNameSpecifierName);
LookupName(FoundOuter, S);
OuterDecl = FoundOuter.getAsSingleDecl(Context);
OuterDecl = FoundOuter.getAsSingle<NamedDecl>();
} else
OuterDecl = ScopeLookupResult;
@ -469,14 +472,13 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S,
// If we didn't find anything during our lookup, try again with
// ordinary name lookup, which can help us produce better error
// messages.
if (!SD) {
if (Found.empty()) {
Found.clear(LookupOrdinaryName);
LookupName(Found, S);
SD = Found.getAsSingleDecl(Context);
}
unsigned DiagID;
if (SD)
if (!Found.empty())
DiagID = diag::err_expected_class_or_namespace;
else if (SS.isSet()) {
Diag(IdLoc, diag::err_no_member) << &II << LookupCtx << SS.getRange();

View File

@ -229,7 +229,7 @@ DeclSpec::TST Sema::isTagName(IdentifierInfo &II, Scope *S) {
LookupName(R, S, false);
R.suppressDiagnostics();
if (R.getResultKind() == LookupResult::Found)
if (const TagDecl *TD = dyn_cast<TagDecl>(R.getAsSingleDecl(Context))) {
if (const TagDecl *TD = R.getAsSingle<TagDecl>()) {
switch (TD->getTagKind()) {
case TagDecl::TK_struct: return DeclSpec::TST_struct;
case TagDecl::TK_union: return DeclSpec::TST_union;
@ -4734,10 +4734,7 @@ CreateNewDecl:
LookupResult Lookup(*this, Name, NameLoc, LookupOrdinaryName,
ForRedeclaration);
LookupName(Lookup, S);
TypedefDecl *PrevTypedef = 0;
if (NamedDecl *Prev = Lookup.getAsSingleDecl(Context))
PrevTypedef = dyn_cast<TypedefDecl>(Prev);
TypedefDecl *PrevTypedef = Lookup.getAsSingle<TypedefDecl>();
NamedDecl *PrevTypedefNamed = PrevTypedef;
if (PrevTypedef && isDeclInScope(PrevTypedefNamed, SearchDC, S) &&
Context.getCanonicalType(Context.getTypeDeclType(PrevTypedef)) !=

View File

@ -6370,8 +6370,7 @@ Sema::OwningExprResult Sema::ActOnBuiltinOffsetOf(Scope *S,
LookupResult R(*this, OC.U.IdentInfo, OC.LocStart, LookupMemberName);
LookupQualifiedName(R, RD);
FieldDecl *MemberDecl
= dyn_cast_or_null<FieldDecl>(R.getAsSingleDecl(Context));
FieldDecl *MemberDecl = R.getAsSingle<FieldDecl>();
// FIXME: Leaks Res
if (!MemberDecl)
return ExprError(Diag(BuiltinLoc, diag::err_no_member)

View File

@ -37,8 +37,7 @@ Sema::ActOnCXXTypeid(SourceLocation OpLoc, SourceLocation LParenLoc,
IdentifierInfo *TypeInfoII = &PP.getIdentifierTable().get("type_info");
LookupResult R(*this, TypeInfoII, SourceLocation(), LookupTagName);
LookupQualifiedName(R, StdNamespace);
Decl *TypeInfoDecl = R.getAsSingleDecl(Context);
RecordDecl *TypeInfoRecordDecl = dyn_cast_or_null<RecordDecl>(TypeInfoDecl);
RecordDecl *TypeInfoRecordDecl = R.getAsSingle<RecordDecl>();
if (!TypeInfoRecordDecl)
return ExprError(Diag(OpLoc, diag::err_need_header_before_typeid));

View File

@ -337,44 +337,6 @@ void LookupResult::resolveKind() {
ResultKind = LookupResult::Found;
}
/// @brief Converts the result of name lookup into a single (possible
/// NULL) pointer to a declaration.
///
/// The resulting declaration will either be the declaration we found
/// (if only a single declaration was found), an
/// OverloadedFunctionDecl (if an overloaded function was found), or
/// NULL (if no declaration was found). This conversion must not be
/// used anywhere where name lookup could result in an ambiguity.
///
/// The OverloadedFunctionDecl conversion is meant as a stop-gap
/// solution, since it causes the OverloadedFunctionDecl to be
/// leaked. FIXME: Eventually, there will be a better way to iterate
/// over the set of overloaded functions returned by name lookup.
NamedDecl *LookupResult::getAsSingleDecl(ASTContext &C) const {
size_t size = Decls.size();
if (size == 0) return 0;
if (size == 1) return (*begin())->getUnderlyingDecl();
if (isAmbiguous()) return 0;
iterator I = begin(), E = end();
OverloadedFunctionDecl *Ovl
= OverloadedFunctionDecl::Create(C, (*I)->getDeclContext(),
(*I)->getDeclName());
for (; I != E; ++I) {
NamedDecl *ND = (*I)->getUnderlyingDecl();
assert(ND->isFunctionOrFunctionTemplate());
if (isa<FunctionDecl>(ND))
Ovl->addOverload(cast<FunctionDecl>(ND));
else
Ovl->addOverload(cast<FunctionTemplateDecl>(ND));
// FIXME: UnresolvedUsingDecls.
}
return Ovl;
}
void LookupResult::addDeclsFromBasePaths(const CXXBasePaths &P) {
CXXBasePaths::paths_iterator I, E;
DeclContext::lookup_iterator DI, DE;
@ -1610,7 +1572,7 @@ NamedDecl *Sema::LookupSingleName(Scope *S, DeclarationName Name,
RedeclarationKind Redecl) {
LookupResult R(*this, Name, SourceLocation(), NameKind, Redecl);
LookupName(R, S);
return R.getAsSingleDecl(Context);
return R.getAsSingle<NamedDecl>();
}
/// \brief Find the protocol with the given name, if any.

View File

@ -4397,8 +4397,7 @@ Sema::DeclResult Sema::ActOnExplicitInstantiation(Scope *S,
if (Previous.isAmbiguous())
return true;
VarDecl *Prev = dyn_cast_or_null<VarDecl>(
Previous.getAsSingleDecl(Context));
VarDecl *Prev = Previous.getAsSingle<VarDecl>();
if (!Prev || !Prev->isStaticDataMember()) {
// We expect to see a data data member here.
Diag(D.getIdentifierLoc(), diag::err_explicit_instantiation_not_known)