[cfe-commits] r83674 - in /cfe/trunk: lib/AST/Decl.cpp lib/Sema/Sema.h lib/Sema/SemaAttr.cpp lib/Sema/SemaCXXScopeSpec.cpp lib/Sema/SemaDecl.cpp lib/Sema/SemaDeclAttr.cpp lib/Sema/SemaDeclCXX.cpp lib/Sema/SemaDeclObjC.cpp lib/Sema/SemaExpr.cpp lib/Sema/SemaExprCXX.cpp lib/Sema/SemaExprObjC.cpp lib/Sema/SemaLookup.cpp lib/Sema/SemaOverload.cpp lib/Sema/SemaTemplate.cpp lib/Sema/SemaTemplateInstantiateDecl.cpp test/SemaCXX/class-names.cpp
John McCall
rjmccall at apple.com
Fri Oct 9 14:13:30 PDT 2009
Author: rjmccall
Date: Fri Oct 9 16:13:30 2009
New Revision: 83674
URL: http://llvm.org/viewvc/llvm-project?rev=83674&view=rev
Log:
Refactor the LookupResult API to simplify most common operations. Require users to
pass a LookupResult reference to lookup routines. Call out uses which assume a single
result.
Modified:
cfe/trunk/lib/AST/Decl.cpp
cfe/trunk/lib/Sema/Sema.h
cfe/trunk/lib/Sema/SemaAttr.cpp
cfe/trunk/lib/Sema/SemaCXXScopeSpec.cpp
cfe/trunk/lib/Sema/SemaDecl.cpp
cfe/trunk/lib/Sema/SemaDeclAttr.cpp
cfe/trunk/lib/Sema/SemaDeclCXX.cpp
cfe/trunk/lib/Sema/SemaDeclObjC.cpp
cfe/trunk/lib/Sema/SemaExpr.cpp
cfe/trunk/lib/Sema/SemaExprCXX.cpp
cfe/trunk/lib/Sema/SemaExprObjC.cpp
cfe/trunk/lib/Sema/SemaLookup.cpp
cfe/trunk/lib/Sema/SemaOverload.cpp
cfe/trunk/lib/Sema/SemaTemplate.cpp
cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp
cfe/trunk/test/SemaCXX/class-names.cpp
Modified: cfe/trunk/lib/AST/Decl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Decl.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/AST/Decl.cpp (original)
+++ cfe/trunk/lib/AST/Decl.cpp Fri Oct 9 16:13:30 2009
@@ -299,6 +299,9 @@
if (isa<ObjCMethodDecl>(this))
return false;
+ if (isa<ObjCInterfaceDecl>(this) && isa<ObjCCompatibleAliasDecl>(OldD))
+ return true;
+
// For non-function declarations, if the declarations are of the
// same kind then this must be a redeclaration, or semantic analysis
// would not have given us the new declaration.
Modified: cfe/trunk/lib/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.h?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/Sema.h (original)
+++ cfe/trunk/lib/Sema/Sema.h Fri Oct 9 16:13:30 2009
@@ -1045,63 +1045,13 @@
/// results occurred for a given lookup.
///
/// Any non-ambiguous lookup can be converted into a single
- /// (possibly NULL) @c NamedDecl* via a conversion function or the
- /// getAsDecl() method. This conversion permits the common-case
- /// usage in C and Objective-C where name lookup will always return
- /// a single declaration.
- struct LookupResult {
- /// The kind of entity that is actually stored within the
- /// LookupResult object.
- enum {
- /// First is a single declaration (a NamedDecl*), which may be NULL.
- SingleDecl,
-
- /// First is a single declaration (an OverloadedFunctionDecl*).
- OverloadedDeclSingleDecl,
-
- /// [First, Last) is an iterator range represented as opaque
- /// pointers used to reconstruct IdentifierResolver::iterators.
- OverloadedDeclFromIdResolver,
-
- /// [First, Last) is an iterator range represented as opaque
- /// pointers used to reconstruct DeclContext::lookup_iterators.
- OverloadedDeclFromDeclContext,
-
- /// First is a pointer to a CXXBasePaths structure, which is owned
- /// by the LookupResult. Last is non-zero to indicate that the
- /// ambiguity is caused by two names found in base class
- /// subobjects of different types.
- AmbiguousLookupStoresBasePaths,
-
- /// [First, Last) is an iterator range represented as opaque
- /// pointers used to reconstruct new'ed Decl*[] array containing
- /// found ambiguous decls. LookupResult is owner of this array.
- AmbiguousLookupStoresDecls
- } StoredKind;
-
- /// The first lookup result, whose contents depend on the kind of
- /// lookup result. This may be a NamedDecl* (if StoredKind ==
- /// SingleDecl), OverloadedFunctionDecl* (if StoredKind ==
- /// OverloadedDeclSingleDecl), the opaque pointer from an
- /// IdentifierResolver::iterator (if StoredKind ==
- /// OverloadedDeclFromIdResolver), a DeclContext::lookup_iterator
- /// (if StoredKind == OverloadedDeclFromDeclContext), or a
- /// CXXBasePaths pointer (if StoredKind == AmbiguousLookupStoresBasePaths).
- mutable uintptr_t First;
-
- /// The last lookup result, whose contents depend on the kind of
- /// lookup result. This may be unused (if StoredKind ==
- /// SingleDecl), it may have the same type as First (for
- /// overloaded function declarations), or is may be used as a
- /// Boolean value (if StoredKind == AmbiguousLookupStoresBasePaths).
- mutable uintptr_t Last;
-
- /// Context - The context in which we will build any
- /// OverloadedFunctionDecl nodes needed by the conversion to
- /// Decl*.
- ASTContext *Context;
-
- /// @brief The kind of entity found by name lookup.
+ /// (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 LookupKind {
/// @brief No entity found met the criteria.
NotFound = 0,
@@ -1156,122 +1106,119 @@
/// }
/// }
/// @endcode
- AmbiguousReference
+ AmbiguousReference,
+
+ FirstAmbiguous = AmbiguousBaseSubobjectTypes
};
- static LookupResult CreateLookupResult(ASTContext &Context, NamedDecl *D);
+ typedef llvm::SmallVector<NamedDecl*, 4> DeclsTy;
+ typedef DeclsTy::const_iterator iterator;
- static LookupResult CreateLookupResult(ASTContext &Context,
- IdentifierResolver::iterator F,
- IdentifierResolver::iterator L);
-
- static LookupResult CreateLookupResult(ASTContext &Context,
- DeclContext::lookup_iterator F,
- DeclContext::lookup_iterator L);
-
- static LookupResult CreateLookupResult(ASTContext &Context,
- CXXBasePaths *Paths,
- bool DifferentSubobjectTypes) {
- LookupResult Result;
- Result.StoredKind = AmbiguousLookupStoresBasePaths;
- Result.First = reinterpret_cast<uintptr_t>(Paths);
- Result.Last = DifferentSubobjectTypes? 1 : 0;
- Result.Context = &Context;
- return Result;
+ LookupResult()
+ : Kind(NotFound),
+ Paths(0)
+ {}
+ ~LookupResult() {
+ if (Paths) deletePaths(Paths);
}
- template <typename Iterator>
- static LookupResult CreateLookupResult(ASTContext &Context,
- Iterator B, std::size_t Len) {
- NamedDecl ** Array = new NamedDecl*[Len];
- for (std::size_t Idx = 0; Idx < Len; ++Idx, ++B)
- Array[Idx] = *B;
- LookupResult Result;
- Result.StoredKind = AmbiguousLookupStoresDecls;
- Result.First = reinterpret_cast<uintptr_t>(Array);
- Result.Last = reinterpret_cast<uintptr_t>(Array + Len);
- Result.Context = &Context;
- return Result;
+ bool isAmbiguous() const {
+ return getKind() >= FirstAmbiguous;
+ }
+
+ LookupKind getKind() const {
+ sanity();
+ return Kind;
}
- LookupKind getKind() const;
+ iterator begin() const { return Decls.begin(); }
+ iterator end() const { return Decls.end(); }
- /// @brief Determine whether name look found something.
- operator bool() const { return getKind() != NotFound; }
+ /// \brief Return true if no decls were found
+ bool empty() const { return Decls.empty(); }
- /// @brief Determines whether the lookup resulted in an ambiguity.
- bool isAmbiguous() const {
- return StoredKind == AmbiguousLookupStoresBasePaths ||
- StoredKind == AmbiguousLookupStoresDecls;
+ /// \brief Return the base paths structure that's associated with
+ /// these results, or null if none is.
+ CXXBasePaths *getBasePaths() const {
+ return Paths;
}
- /// @brief Allows conversion of a lookup result into a
- /// declaration, with the same behavior as getAsDecl.
- operator NamedDecl*() const { return getAsDecl(); }
+ /// \brief Add a declaration to these results.
+ void addDecl(NamedDecl *D) {
+ Decls.push_back(D->getUnderlyingDecl());
+ Kind = Found;
+ }
- NamedDecl* getAsDecl() const;
+ /// \brief Resolves the kind of the lookup, possibly hiding decls.
+ ///
+ /// This should be called in any environment where lookup might
+ /// generate multiple lookup results.
+ void resolveKind();
- CXXBasePaths *getBasePaths() const;
+ /// \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;
- /// \brief Iterate over the results of name lookup.
+ /// \brief Fetch the unique decl found by this lookup. Asserts
+ /// that one was found.
///
- /// The @c iterator class provides iteration over the results of a
- /// non-ambiguous name lookup.
- class iterator {
- /// The LookupResult structure we're iterating through.
- LookupResult *Result;
-
- /// The current position of this iterator within the sequence of
- /// results. This value will have the same representation as the
- /// @c First field in the LookupResult structure.
- mutable uintptr_t Current;
-
- public:
- typedef NamedDecl * value_type;
- typedef NamedDecl * reference;
- typedef NamedDecl * pointer;
- typedef std::ptrdiff_t difference_type;
- typedef std::forward_iterator_tag iterator_category;
-
- iterator() : Result(0), Current(0) { }
-
- iterator(LookupResult *Res, uintptr_t Cur) : Result(Res), Current(Cur) { }
-
- reference operator*() const;
-
- pointer operator->() const { return **this; }
-
- iterator &operator++();
-
- iterator operator++(int) {
- iterator tmp(*this);
- ++(*this);
- return tmp;
- }
+ /// 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");
+ return *Decls.begin();
+ }
- friend inline bool operator==(iterator const& x, iterator const& y) {
- return x.Current == y.Current;
- }
+ /// \brief Make these results show that the name was found in
+ /// base classes of different types.
+ ///
+ /// The given paths object is copied and invalidated.
+ void setAmbiguousBaseSubobjectTypes(CXXBasePaths &P);
- friend inline bool operator!=(iterator const& x, iterator const& y) {
- return x.Current != y.Current;
- }
- };
- friend class iterator;
+ /// \brief Make these results show that the name was found in
+ /// distinct base classes of the same type.
+ ///
+ /// The given paths object is copied and invalidated.
+ void setAmbiguousBaseSubobjects(CXXBasePaths &P);
+
+ /// \brief Clears out any current state.
+ void clear() {
+ Kind = NotFound;
+ Decls.clear();
+ if (Paths) deletePaths(Paths);
+ Paths = NULL;
+ }
- iterator begin();
- iterator end();
+ void print(llvm::raw_ostream &);
- /// \brief Free the memory associated with this lookup.
- void Destroy();
+ private:
+ void addDeclsFromBasePaths(const CXXBasePaths &P);
+
+ // Sanity checks.
+ void sanity() const {
+ assert(Kind != NotFound || Decls.size() == 0);
+ assert(Kind != Found || Decls.size() == 1);
+ assert(Kind == NotFound || Kind == Found ||
+ Kind == AmbiguousBaseSubobjects || Decls.size() > 1);
+ assert((Paths != NULL) == (Kind == AmbiguousBaseSubobjectTypes ||
+ Kind == AmbiguousBaseSubobjects));
+ }
+
+ static void deletePaths(CXXBasePaths *);
+
+ LookupKind Kind;
+ DeclsTy Decls;
+ CXXBasePaths *Paths;
};
private:
typedef llvm::SmallVector<LookupResult, 3> LookupResultsVecTy;
- std::pair<bool, LookupResult> CppLookupName(Scope *S, DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly);
+ bool CppLookupName(LookupResult &R, Scope *S, DeclarationName Name,
+ LookupNameKind NameKind, bool RedeclarationOnly);
public:
/// Determines whether D is a suitable lookup result according to the
/// lookup criteria.
@@ -1303,24 +1250,38 @@
return false;
}
- LookupResult LookupName(Scope *S, DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false,
- bool AllowBuiltinCreation = false,
- SourceLocation Loc = SourceLocation());
- LookupResult LookupQualifiedName(DeclContext *LookupCtx, DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false);
+ /// \brief Look up a name, looking for a single declaration. Return
+ /// null if no unambiguous results were found.
+ ///
+ /// It is preferable to use the elaborated form and explicitly handle
+ /// ambiguity and overloaded.
+ NamedDecl *LookupSingleName(Scope *S, DeclarationName Name,
+ LookupNameKind NameKind,
+ bool RedeclarationOnly = false) {
+ LookupResult R;
+ LookupName(R, S, Name, NameKind, RedeclarationOnly);
+ 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);
Decl *LookupQualifiedNameWithType(DeclContext *LookupCtx,
DeclarationName Name,
QualType T);
- LookupResult LookupParsedName(Scope *S, const CXXScopeSpec *SS,
- DeclarationName Name,
- LookupNameKind NameKind,
- bool RedeclarationOnly = false,
- bool AllowBuiltinCreation = false,
- SourceLocation Loc = SourceLocation(),
- bool EnteringContext = false);
+ 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);
ObjCCategoryImplDecl *LookupObjCCategoryImpl(IdentifierInfo *II);
Modified: cfe/trunk/lib/Sema/SemaAttr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaAttr.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaAttr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaAttr.cpp Fri Oct 9 16:13:30 2009
@@ -179,13 +179,12 @@
for (unsigned i = 0; i < NumIdentifiers; ++i) {
const Token &Tok = Identifiers[i];
IdentifierInfo *Name = Tok.getIdentifierInfo();
- const LookupResult &Lookup = LookupParsedName(curScope, NULL, Name,
- LookupOrdinaryName,
- false, true,
- Tok.getLocation());
+ LookupResult Lookup;
+ LookupParsedName(Lookup, curScope, NULL, Name,LookupOrdinaryName,
+ false, true, Tok.getLocation());
// FIXME: Handle Lookup.isAmbiguous?
- NamedDecl *ND = Lookup.getAsDecl();
+ NamedDecl *ND = Lookup.getAsSingleDecl(Context);
if (!ND) {
Diag(PragmaLoc, diag::warn_pragma_unused_undeclared_var)
Modified: cfe/trunk/lib/Sema/SemaCXXScopeSpec.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaCXXScopeSpec.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaCXXScopeSpec.cpp (original)
+++ cfe/trunk/lib/Sema/SemaCXXScopeSpec.cpp Fri Oct 9 16:13:30 2009
@@ -302,11 +302,11 @@
if (NNS->getKind() != NestedNameSpecifier::Identifier)
return 0;
- LookupResult Found
- = LookupName(S, NNS->getAsIdentifier(), LookupNestedNameSpecifierName);
+ LookupResult Found;
+ LookupName(Found, S, NNS->getAsIdentifier(), LookupNestedNameSpecifierName);
assert(!Found.isAmbiguous() && "Cannot handle ambiguities here yet");
- NamedDecl *Result = Found;
+ NamedDecl *Result = Found.getAsSingleDecl(Context);
if (isAcceptableNestedNameSpecifier(Result))
return Result;
@@ -359,8 +359,8 @@
if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(SS))
return 0;
- Found = LookupQualifiedName(LookupCtx, &II, LookupNestedNameSpecifierName,
- false);
+ LookupQualifiedName(Found, LookupCtx, &II, LookupNestedNameSpecifierName,
+ false);
if (!ObjectType.isNull() && Found.getKind() == LookupResult::NotFound) {
// C++ [basic.lookup.classref]p4:
@@ -384,9 +384,9 @@
// reconstruct the result from when name lookup was performed at template
// definition time.
if (S)
- Found = LookupName(S, &II, LookupNestedNameSpecifierName);
- else
- Found = LookupResult::CreateLookupResult(Context, ScopeLookupResult);
+ LookupName(Found, S, &II, LookupNestedNameSpecifierName);
+ else if (ScopeLookupResult)
+ Found.addDecl(ScopeLookupResult);
ObjectTypeSearchedInScope = true;
}
@@ -401,11 +401,11 @@
return NestedNameSpecifier::Create(Context, Prefix, &II);
} else {
// Perform unqualified name lookup in the current scope.
- Found = LookupName(S, &II, LookupNestedNameSpecifierName);
+ LookupName(Found, S, &II, LookupNestedNameSpecifierName);
}
// FIXME: Deal with ambiguities cleanly.
- NamedDecl *SD = Found;
+ NamedDecl *SD = Found.getAsSingleDecl(Context);
if (isAcceptableNestedNameSpecifier(SD)) {
if (!ObjectType.isNull() && !ObjectTypeSearchedInScope) {
// C++ [basic.lookup.classref]p4:
@@ -416,15 +416,15 @@
// into the current scope (the scope of the postfix-expression) to
// see if we can find the same name there. As above, if there is no
// scope, reconstruct the result from the template instantiation itself.
- LookupResult FoundOuter;
- if (S)
- FoundOuter = LookupName(S, &II, LookupNestedNameSpecifierName);
- else
- FoundOuter = LookupResult::CreateLookupResult(Context,
- ScopeLookupResult);
+ NamedDecl *OuterDecl;
+ if (S) {
+ LookupResult FoundOuter;
+ LookupName(FoundOuter, S, &II, LookupNestedNameSpecifierName);
+ // FIXME: Handle ambiguities!
+ OuterDecl = FoundOuter.getAsSingleDecl(Context);
+ } else
+ OuterDecl = ScopeLookupResult;
- // FIXME: Handle ambiguities in FoundOuter!
- NamedDecl *OuterDecl = FoundOuter;
if (isAcceptableNestedNameSpecifier(OuterDecl) &&
OuterDecl->getCanonicalDecl() != SD->getCanonicalDecl() &&
(!isa<TypeDecl>(OuterDecl) || !isa<TypeDecl>(SD) ||
@@ -461,8 +461,11 @@
// 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)
- SD = LookupName(S, &II, LookupOrdinaryName);
+ if (!SD) {
+ Found.clear();
+ LookupName(Found, S, &II, LookupOrdinaryName);
+ SD = Found.getAsSingleDecl(Context);
+ }
unsigned DiagID;
if (SD)
Modified: cfe/trunk/lib/Sema/SemaDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDecl.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDecl.cpp Fri Oct 9 16:13:30 2009
@@ -85,8 +85,8 @@
II, SS->getRange()).getAsOpaquePtr();
}
- LookupResult Result
- = LookupParsedName(S, SS, &II, LookupOrdinaryName, false, false);
+ LookupResult Result;
+ LookupParsedName(Result, S, SS, &II, LookupOrdinaryName, false, false);
NamedDecl *IIDecl = 0;
switch (Result.getKind()) {
@@ -115,7 +115,6 @@
// 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.Destroy();
return 0;
}
@@ -128,7 +127,7 @@
}
case LookupResult::Found:
- IIDecl = Result.getAsDecl();
+ IIDecl = Result.getFoundDecl();
break;
}
@@ -179,9 +178,10 @@
/// 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(S, &II, LookupTagName, false, false);
+ LookupResult R;
+ LookupName(R, S, &II, LookupTagName, false, false);
if (R.getKind() == LookupResult::Found)
- if (const TagDecl *TD = dyn_cast<TagDecl>(R.getAsDecl())) {
+ if (const TagDecl *TD = dyn_cast<TagDecl>(R.getAsSingleDecl(Context))) {
switch (TD->getTagKind()) {
case TagDecl::TK_struct: return DeclSpec::TST_struct;
case TagDecl::TK_union: return DeclSpec::TST_union;
@@ -303,84 +303,20 @@
(isa<VarDecl>(D) && cast<VarDecl>(D)->isOutOfLine()))
return;
- S->AddDecl(DeclPtrTy::make(D));
-
- // C++ [basic.scope]p4:
- // -- exactly one declaration shall declare a class name or
- // enumeration name that is not a typedef name and the other
- // declarations shall all refer to the same object or
- // enumerator, or all refer to functions and function templates;
- // in this case the class name or enumeration name is hidden.
- if (TagDecl *TD = dyn_cast<TagDecl>(D)) {
- // We are pushing the name of a tag (enum or class).
- if (CurContext->getLookupContext()
- == TD->getDeclContext()->getLookupContext()) {
- // We're pushing the tag into the current context, which might
- // require some reshuffling in the identifier resolver.
- IdentifierResolver::iterator
- I = IdResolver.begin(TD->getDeclName()),
- IEnd = IdResolver.end();
- NamedDecl *ID = *I;
- if (I != IEnd && isDeclInScope(ID, CurContext, S)) {
- NamedDecl *PrevDecl = *I;
- for (; I != IEnd && isDeclInScope(ID, CurContext, S);
- PrevDecl = *I, ++I) {
- if (TD->declarationReplaces(*I)) {
- // This is a redeclaration. Remove it from the chain and
- // break out, so that we'll add in the shadowed
- // declaration.
- S->RemoveDecl(DeclPtrTy::make(*I));
- if (PrevDecl == *I) {
- IdResolver.RemoveDecl(*I);
- IdResolver.AddDecl(TD);
- return;
- } else {
- IdResolver.RemoveDecl(*I);
- break;
- }
- }
- }
-
- // There is already a declaration with the same name in the same
- // scope, which is not a tag declaration. It must be found
- // before we find the new declaration, so insert the new
- // declaration at the end of the chain.
- IdResolver.AddShadowedDecl(TD, PrevDecl);
+ // If this replaces anything in the current scope,
+ IdentifierResolver::iterator I = IdResolver.begin(D->getDeclName()),
+ IEnd = IdResolver.end();
+ for (; I != IEnd; ++I) {
+ if (S->isDeclScope(DeclPtrTy::make(*I)) && D->declarationReplaces(*I)) {
+ S->RemoveDecl(DeclPtrTy::make(*I));
+ IdResolver.RemoveDecl(*I);
- return;
- }
- }
- } else if ((isa<FunctionDecl>(D) &&
- AllowOverloadingOfFunction(D, Context)) ||
- isa<FunctionTemplateDecl>(D)) {
- // We are pushing the name of a function or function template,
- // which might be an overloaded name.
- IdentifierResolver::iterator Redecl
- = std::find_if(IdResolver.begin(D->getDeclName()),
- IdResolver.end(),
- std::bind1st(std::mem_fun(&NamedDecl::declarationReplaces),
- D));
- if (Redecl != IdResolver.end() &&
- S->isDeclScope(DeclPtrTy::make(*Redecl))) {
- // There is already a declaration of a function on our
- // IdResolver chain. Replace it with this declaration.
- S->RemoveDecl(DeclPtrTy::make(*Redecl));
- IdResolver.RemoveDecl(*Redecl);
- }
- } else if (isa<ObjCInterfaceDecl>(D)) {
- // We're pushing an Objective-C interface into the current
- // context. If there is already an alias declaration, remove it first.
- for (IdentifierResolver::iterator
- I = IdResolver.begin(D->getDeclName()), IEnd = IdResolver.end();
- I != IEnd; ++I) {
- if (isa<ObjCCompatibleAliasDecl>(*I)) {
- S->RemoveDecl(DeclPtrTy::make(*I));
- IdResolver.RemoveDecl(*I);
- break;
- }
+ // Should only need to replace one decl.
+ break;
}
}
+ S->AddDecl(DeclPtrTy::make(D));
IdResolver.AddDecl(D);
}
@@ -450,7 +386,7 @@
ObjCInterfaceDecl *Sema::getObjCInterfaceDecl(IdentifierInfo *Id) {
// The third "scope" argument is 0 since we aren't enabling lazy built-in
// creation from this context.
- NamedDecl *IDecl = LookupName(TUScope, Id, LookupOrdinaryName);
+ NamedDecl *IDecl = LookupSingleName(TUScope, Id, LookupOrdinaryName);
return dyn_cast_or_null<ObjCInterfaceDecl>(IDecl);
}
@@ -492,7 +428,7 @@
return;
IdentifierInfo *VaIdent = &Context.Idents.get("__builtin_va_list");
- NamedDecl *VaDecl = LookupName(TUScope, VaIdent, LookupOrdinaryName);
+ NamedDecl *VaDecl = LookupSingleName(TUScope, VaIdent, LookupOrdinaryName);
TypedefDecl *VaTypedef = cast<TypedefDecl>(VaDecl);
Context.setBuiltinVaListType(Context.getTypedefType(VaTypedef));
}
@@ -1414,8 +1350,10 @@
FEnd = AnonRecord->field_end();
F != FEnd; ++F) {
if ((*F)->getDeclName()) {
- NamedDecl *PrevDecl = LookupQualifiedName(Owner, (*F)->getDeclName(),
- LookupOrdinaryName, true);
+ LookupResult R;
+ LookupQualifiedName(R, Owner, (*F)->getDeclName(),
+ LookupOrdinaryName, true);
+ NamedDecl *PrevDecl = R.getAsSingleDecl(Context);
if (PrevDecl && !isa<TagDecl>(PrevDecl)) {
// C++ [class.union]p2:
// The names of the members of an anonymous union shall be
@@ -1771,9 +1709,11 @@
NameKind = LookupRedeclarationWithLinkage;
DC = CurContext;
- PrevDecl = LookupName(S, Name, NameKind, true,
- NameKind == LookupRedeclarationWithLinkage,
- D.getIdentifierLoc());
+ LookupResult R;
+ LookupName(R, S, Name, NameKind, true,
+ NameKind == LookupRedeclarationWithLinkage,
+ D.getIdentifierLoc());
+ PrevDecl = R.getAsSingleDecl(Context);
} else { // Something like "int foo::x;"
DC = computeDeclContext(D.getCXXScopeSpec(), true);
@@ -1789,7 +1729,9 @@
return DeclPtrTy();
}
- PrevDecl = LookupQualifiedName(DC, Name, LookupOrdinaryName, true);
+ LookupResult Res;
+ LookupQualifiedName(Res, DC, Name, LookupOrdinaryName, true);
+ PrevDecl = Res.getAsSingleDecl(Context);
// C++ 7.3.1.2p2:
// Members (including explicit specializations of templates) of a named
@@ -2885,8 +2827,8 @@
<< cast<NamedDecl>(DC) << D.getCXXScopeSpec().getRange();
NewFD->setInvalidDecl();
- LookupResult Prev = LookupQualifiedName(DC, Name, LookupOrdinaryName,
- true);
+ LookupResult Prev;
+ LookupQualifiedName(Prev, DC, Name, LookupOrdinaryName, true);
assert(!Prev.isAmbiguous() &&
"Cannot have an ambiguity in previous-declaration lookup");
for (LookupResult::iterator Func = Prev.begin(), FuncEnd = Prev.end();
@@ -3603,7 +3545,7 @@
// among each other. Here they can only shadow globals, which is ok.
IdentifierInfo *II = D.getIdentifier();
if (II) {
- if (NamedDecl *PrevDecl = LookupName(S, II, LookupOrdinaryName)) {
+ if (NamedDecl *PrevDecl = LookupSingleName(S, II, LookupOrdinaryName)) {
if (PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
DiagnoseTemplateParameterShadow(D.getIdentifierLoc(), PrevDecl);
@@ -4212,9 +4154,9 @@
DC = computeDeclContext(SS, true);
SearchDC = DC;
// Look-up name inside 'foo::'.
- PrevDecl
- = dyn_cast_or_null<TagDecl>(
- LookupQualifiedName(DC, Name, LookupTagName, true).getAsDecl());
+ LookupResult R;
+ LookupQualifiedName(R, DC, Name, LookupTagName, true);
+ PrevDecl = dyn_cast_or_null<TagDecl>(R.getAsSingleDecl(Context));
// A tag 'foo::bar' must already exist.
if (PrevDecl == 0) {
@@ -4229,7 +4171,8 @@
// 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(S, Name, LookupTagName,
+ LookupResult R;
+ LookupName(R, S, Name, LookupTagName,
/*RedeclarationOnly=*/(TUK != TUK_Reference));
if (R.isAmbiguous()) {
DiagnoseAmbiguousLookup(R, Name, NameLoc);
@@ -4242,7 +4185,7 @@
PrevDecl = 0;
Invalid = true;
} else
- PrevDecl = R;
+ PrevDecl = R.getAsSingleDecl(Context);
if (!getLangOptions().CPlusPlus && TUK != TUK_Reference) {
// FIXME: This makes sure that we ignore the contexts associated
@@ -4489,10 +4432,11 @@
// 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(S, Name, LookupOrdinaryName, true);
+ LookupResult Lookup;
+ LookupName(Lookup, S, Name, LookupOrdinaryName, true);
TypedefDecl *PrevTypedef = 0;
- if (Lookup.getKind() == LookupResult::Found)
- PrevTypedef = dyn_cast<TypedefDecl>(Lookup.getAsDecl());
+ if (NamedDecl *Prev = Lookup.getAsSingleDecl(Context))
+ PrevTypedef = dyn_cast<TypedefDecl>(Prev);
NamedDecl *PrevTypedefNamed = PrevTypedef;
if (PrevTypedef && isDeclInScope(PrevTypedefNamed, SearchDC, S) &&
@@ -4708,7 +4652,7 @@
if (D.getDeclSpec().isThreadSpecified())
Diag(D.getDeclSpec().getThreadSpecLoc(), diag::err_invalid_thread);
- NamedDecl *PrevDecl = LookupName(S, II, LookupMemberName, true);
+ NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName, true);
if (PrevDecl && PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
@@ -5089,7 +5033,7 @@
DInfo, ac, (Expr *)BitfieldWidth);
if (II) {
- NamedDecl *PrevDecl = LookupName(S, II, LookupMemberName, true);
+ NamedDecl *PrevDecl = LookupSingleName(S, II, LookupMemberName, true);
if (PrevDecl && isDeclInScope(PrevDecl, EnclosingContext, S)
&& !isa<TagDecl>(PrevDecl)) {
Diag(Loc, diag::err_duplicate_member) << II;
@@ -5342,7 +5286,7 @@
// Verify that there isn't already something declared with this name in this
// scope.
- NamedDecl *PrevDecl = LookupName(S, Id, LookupOrdinaryName);
+ NamedDecl *PrevDecl = LookupSingleName(S, Id, LookupOrdinaryName);
if (PrevDecl && PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
DiagnoseTemplateParameterShadow(IdLoc, PrevDecl);
@@ -5585,7 +5529,7 @@
void Sema::ActOnPragmaWeakID(IdentifierInfo* Name,
SourceLocation PragmaLoc,
SourceLocation NameLoc) {
- Decl *PrevDecl = LookupName(TUScope, Name, LookupOrdinaryName);
+ Decl *PrevDecl = LookupSingleName(TUScope, Name, LookupOrdinaryName);
if (PrevDecl) {
PrevDecl->addAttr(::new (Context) WeakAttr());
@@ -5601,7 +5545,7 @@
SourceLocation PragmaLoc,
SourceLocation NameLoc,
SourceLocation AliasNameLoc) {
- Decl *PrevDecl = LookupName(TUScope, AliasName, LookupOrdinaryName);
+ Decl *PrevDecl = LookupSingleName(TUScope, AliasName, LookupOrdinaryName);
WeakInfo W = WeakInfo(Name, NameLoc);
if (PrevDecl) {
Modified: cfe/trunk/lib/Sema/SemaDeclAttr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclAttr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclAttr.cpp Fri Oct 9 16:13:30 2009
@@ -1104,8 +1104,9 @@
}
// Look up the function
- NamedDecl *CleanupDecl = S.LookupName(S.TUScope, Attr.getParameterName(),
- Sema::LookupOrdinaryName);
+ NamedDecl *CleanupDecl
+ = S.LookupSingleName(S.TUScope, Attr.getParameterName(),
+ Sema::LookupOrdinaryName);
if (!CleanupDecl) {
S.Diag(Attr.getLoc(), diag::err_attribute_cleanup_arg_not_found) <<
Attr.getParameterName();
Modified: cfe/trunk/lib/Sema/SemaDeclCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclCXX.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclCXX.cpp Fri Oct 9 16:13:30 2009
@@ -2490,8 +2490,8 @@
// original-namespace-definition is the name of the namespace. Subsequently
// in that declarative region, it is treated as an original-namespace-name.
- NamedDecl *PrevDecl = LookupName(DeclRegionScope, II, LookupOrdinaryName,
- true);
+ NamedDecl *PrevDecl
+ = LookupSingleName(DeclRegionScope, II, LookupOrdinaryName, true);
if (NamespaceDecl *OrigNS = dyn_cast_or_null<NamespaceDecl>(PrevDecl)) {
// This is an extended namespace definition.
@@ -2599,13 +2599,14 @@
UsingDirectiveDecl *UDir = 0;
// Lookup namespace name.
- LookupResult R = LookupParsedName(S, &SS, NamespcName,
- LookupNamespaceName, false);
+ LookupResult R;
+ LookupParsedName(R, S, &SS, NamespcName, LookupNamespaceName, false);
if (R.isAmbiguous()) {
DiagnoseAmbiguousLookup(R, NamespcName, IdentLoc);
return DeclPtrTy();
}
- if (NamedDecl *NS = R) {
+ if (!R.empty()) {
+ NamedDecl *NS = R.getFoundDecl();
assert(isa<NamespaceDecl>(NS) && "expected namespace decl");
// C++ [namespace.udir]p1:
// A using-directive specifies that the names in the nominated
@@ -2746,15 +2747,16 @@
// Lookup target name.
- LookupResult R = LookupQualifiedName(LookupContext,
- Name, LookupOrdinaryName);
+ LookupResult R;
+ LookupQualifiedName(R, LookupContext, Name, LookupOrdinaryName);
- if (!R) {
+ if (R.empty()) {
DiagnoseMissingMember(IdentLoc, Name, NNS, SS.getRange());
return 0;
}
- NamedDecl *ND = R.getAsDecl();
+ // FIXME: handle ambiguity?
+ NamedDecl *ND = R.getAsSingleDecl(Context);
if (IsTypeName && !isa<TypeDecl>(ND)) {
Diag(IdentLoc, diag::err_using_typename_non_type);
@@ -2790,14 +2792,17 @@
IdentifierInfo *Ident) {
// Lookup the namespace name.
- LookupResult R = LookupParsedName(S, &SS, Ident, LookupNamespaceName, false);
+ LookupResult R;
+ LookupParsedName(R, S, &SS, Ident, LookupNamespaceName, false);
// Check if we have a previous declaration with the same name.
- if (NamedDecl *PrevDecl = LookupName(S, Alias, LookupOrdinaryName, true)) {
+ if (NamedDecl *PrevDecl
+ = LookupSingleName(S, Alias, LookupOrdinaryName, true)) {
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.
- if (!R.isAmbiguous() && AD->getNamespace() == getNamespaceDecl(R))
+ if (!R.isAmbiguous() && !R.empty() &&
+ AD->getNamespace() == getNamespaceDecl(R.getFoundDecl()))
return DeclPtrTy();
}
@@ -2813,7 +2818,7 @@
return DeclPtrTy();
}
- if (!R) {
+ if (R.empty()) {
Diag(NamespaceLoc, diag::err_expected_namespace_name) << SS.getRange();
return DeclPtrTy();
}
@@ -2822,7 +2827,7 @@
NamespaceAliasDecl::Create(Context, CurContext, NamespaceLoc, AliasLoc,
Alias, SS.getRange(),
(NestedNameSpecifier *)SS.getScopeRep(),
- IdentLoc, R);
+ IdentLoc, R.getFoundDecl());
CurContext->addDecl(AliasDecl);
return DeclPtrTy::make(AliasDecl);
@@ -4151,7 +4156,7 @@
bool Invalid = D.isInvalidType();
IdentifierInfo *II = D.getIdentifier();
- if (NamedDecl *PrevDecl = LookupName(S, II, LookupOrdinaryName)) {
+ if (NamedDecl *PrevDecl = LookupSingleName(S, II, LookupOrdinaryName)) {
// The scope should be freshly made just for us. There is just no way
// it contains any previous declaration.
assert(!S->isDeclScope(DeclPtrTy::make(PrevDecl)));
@@ -4398,7 +4403,9 @@
// FIXME: handle dependent contexts
if (!DC) return DeclPtrTy();
- PrevDecl = LookupQualifiedName(DC, Name, LookupOrdinaryName, true);
+ LookupResult R;
+ LookupQualifiedName(R, DC, Name, LookupOrdinaryName, true);
+ PrevDecl = R.getAsSingleDecl(Context);
// If searching in that context implicitly found a declaration in
// a different context, treat it like it wasn't found at all.
@@ -4431,7 +4438,9 @@
while (DC->isRecord())
DC = DC->getParent();
- PrevDecl = LookupQualifiedName(DC, Name, LookupOrdinaryName, true);
+ LookupResult R;
+ LookupQualifiedName(R, DC, Name, LookupOrdinaryName, true);
+ PrevDecl = R.getAsSingleDecl(Context);
// TODO: decide what we think about using declarations.
if (PrevDecl)
Modified: cfe/trunk/lib/Sema/SemaDeclObjC.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclObjC.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclObjC.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclObjC.cpp Fri Oct 9 16:13:30 2009
@@ -84,7 +84,7 @@
assert(ClassName && "Missing class identifier");
// Check for another declaration kind with the same name.
- NamedDecl *PrevDecl = LookupName(TUScope, ClassName, LookupOrdinaryName);
+ NamedDecl *PrevDecl = LookupSingleName(TUScope, ClassName, LookupOrdinaryName);
if (PrevDecl && PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
DiagnoseTemplateParameterShadow(ClassLoc, PrevDecl);
@@ -124,7 +124,7 @@
if (SuperName) {
// Check if a different kind of symbol declared in this scope.
- PrevDecl = LookupName(TUScope, SuperName, LookupOrdinaryName);
+ PrevDecl = LookupSingleName(TUScope, SuperName, LookupOrdinaryName);
if (PrevDecl == IDecl) {
Diag(SuperLoc, diag::err_recursive_superclass)
<< SuperName << ClassName << SourceRange(AtInterfaceLoc, ClassLoc);
@@ -195,7 +195,7 @@
IdentifierInfo *ClassName,
SourceLocation ClassLocation) {
// Look for previous declaration of alias name
- NamedDecl *ADecl = LookupName(TUScope, AliasName, LookupOrdinaryName);
+ NamedDecl *ADecl = LookupSingleName(TUScope, AliasName, LookupOrdinaryName);
if (ADecl) {
if (isa<ObjCCompatibleAliasDecl>(ADecl))
Diag(AliasLocation, diag::warn_previous_alias_decl);
@@ -205,13 +205,13 @@
return DeclPtrTy();
}
// Check for class declaration
- NamedDecl *CDeclU = LookupName(TUScope, ClassName, LookupOrdinaryName);
+ NamedDecl *CDeclU = LookupSingleName(TUScope, ClassName, LookupOrdinaryName);
if (const TypedefDecl *TDecl = dyn_cast_or_null<TypedefDecl>(CDeclU)) {
QualType T = TDecl->getUnderlyingType();
if (T->isObjCInterfaceType()) {
if (NamedDecl *IDecl = T->getAs<ObjCInterfaceType>()->getDecl()) {
ClassName = IDecl->getIdentifier();
- CDeclU = LookupName(TUScope, ClassName, LookupOrdinaryName);
+ CDeclU = LookupSingleName(TUScope, ClassName, LookupOrdinaryName);
}
}
}
@@ -654,7 +654,8 @@
SourceLocation SuperClassLoc) {
ObjCInterfaceDecl* IDecl = 0;
// Check for another declaration kind with the same name.
- NamedDecl *PrevDecl = LookupName(TUScope, ClassName, LookupOrdinaryName);
+ NamedDecl *PrevDecl
+ = LookupSingleName(TUScope, ClassName, LookupOrdinaryName);
if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
Diag(ClassLoc, diag::err_redefinition_different_kind) << ClassName;
Diag(PrevDecl->getLocation(), diag::note_previous_definition);
@@ -671,7 +672,7 @@
ObjCInterfaceDecl* SDecl = 0;
if (SuperClassname) {
// Check if a different kind of symbol declared in this scope.
- PrevDecl = LookupName(TUScope, SuperClassname, LookupOrdinaryName);
+ PrevDecl = LookupSingleName(TUScope, SuperClassname, LookupOrdinaryName);
if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) {
Diag(SuperClassLoc, diag::err_redefinition_different_kind)
<< SuperClassname;
@@ -1121,7 +1122,8 @@
for (unsigned i = 0; i != NumElts; ++i) {
// Check for another declaration kind with the same name.
- NamedDecl *PrevDecl = LookupName(TUScope, IdentList[i], LookupOrdinaryName);
+ NamedDecl *PrevDecl
+ = LookupSingleName(TUScope, IdentList[i], LookupOrdinaryName);
if (PrevDecl && PrevDecl->isTemplateParameter()) {
// Maybe we will complain about the shadowed template parameter.
DiagnoseTemplateParameterShadow(AtClassLoc, PrevDecl);
Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Fri Oct 9 16:13:30 2009
@@ -695,8 +695,8 @@
isAddressOfOperand));
}
- LookupResult Lookup = LookupParsedName(S, SS, Name, LookupOrdinaryName,
- false, true, Loc);
+ LookupResult Lookup;
+ LookupParsedName(Lookup, S, SS, Name, LookupOrdinaryName, false, true, Loc);
if (Lookup.isAmbiguous()) {
DiagnoseAmbiguousLookup(Lookup, Name, Loc,
@@ -705,7 +705,7 @@
return ExprError();
}
- NamedDecl *D = Lookup.getAsDecl();
+ NamedDecl *D = Lookup.getAsSingleDecl(Context);
// If this reference is in an Objective-C method, then ivar lookup happens as
// well.
@@ -2181,10 +2181,10 @@
}
// The record definition is complete, now make sure the member is valid.
- LookupResult Result
- = LookupQualifiedName(DC, MemberName, LookupMemberName, false);
+ LookupResult Result;
+ LookupQualifiedName(Result, DC, MemberName, LookupMemberName, false);
- if (!Result)
+ if (Result.empty())
return ExprError(Diag(MemberLoc, diag::err_typecheck_no_member_deprecated)
<< MemberName << BaseExpr->getSourceRange());
if (Result.isAmbiguous()) {
@@ -2193,13 +2193,14 @@
return ExprError();
}
+ NamedDecl *MemberDecl = Result.getAsSingleDecl(Context);
+
if (SS && SS->isSet()) {
+ TypeDecl* TyD = cast<TypeDecl>(MemberDecl->getDeclContext());
QualType BaseTypeCanon
= Context.getCanonicalType(BaseType).getUnqualifiedType();
QualType MemberTypeCanon
- = Context.getCanonicalType(
- Context.getTypeDeclType(
- dyn_cast<TypeDecl>(Result.getAsDecl()->getDeclContext())));
+ = Context.getCanonicalType(Context.getTypeDeclType(TyD));
if (BaseTypeCanon != MemberTypeCanon &&
!IsDerivedFrom(BaseTypeCanon, MemberTypeCanon))
@@ -2208,8 +2209,6 @@
<< MemberTypeCanon << BaseTypeCanon);
}
- NamedDecl *MemberDecl = Result;
-
// If the decl being referenced had an error, return an error for this
// sub-expr without emitting another error, in order to avoid cascading
// error cases.
@@ -5685,10 +5684,11 @@
}
}
+ LookupResult R;
+ LookupQualifiedName(R, RD, OC.U.IdentInfo, LookupMemberName);
+
FieldDecl *MemberDecl
- = dyn_cast_or_null<FieldDecl>(LookupQualifiedName(RD, OC.U.IdentInfo,
- LookupMemberName)
- .getAsDecl());
+ = dyn_cast_or_null<FieldDecl>(R.getAsSingleDecl(Context));
// FIXME: Leaks Res
if (!MemberDecl)
return ExprError(Diag(BuiltinLoc, diag::err_typecheck_no_member_deprecated)
Modified: cfe/trunk/lib/Sema/SemaExprCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprCXX.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExprCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExprCXX.cpp Fri Oct 9 16:13:30 2009
@@ -69,8 +69,9 @@
TyOrExpr = GetTypeFromParser(TyOrExpr).getAsOpaquePtr();
IdentifierInfo *TypeInfoII = &PP.getIdentifierTable().get("type_info");
- Decl *TypeInfoDecl = LookupQualifiedName(StdNamespace, TypeInfoII,
- LookupTagName);
+ LookupResult R;
+ LookupQualifiedName(R, StdNamespace, TypeInfoII, LookupTagName);
+ Decl *TypeInfoDecl = R.getAsSingleDecl(Context);
RecordDecl *TypeInfoRecordDecl = dyn_cast_or_null<RecordDecl>(TypeInfoDecl);
if (!TypeInfoRecordDecl)
return ExprError(Diag(OpLoc, diag::err_need_header_before_typeid));
@@ -589,14 +590,17 @@
DeclarationName Name, Expr** Args,
unsigned NumArgs, DeclContext *Ctx,
bool AllowMissing, FunctionDecl *&Operator) {
- LookupResult R = LookupQualifiedName(Ctx, Name, LookupOrdinaryName);
- if (!R) {
+ LookupResult R;
+ LookupQualifiedName(R, Ctx, Name, LookupOrdinaryName);
+ if (R.empty()) {
if (AllowMissing)
return false;
return Diag(StartLoc, diag::err_ovl_no_viable_function_in_call)
<< Name << Range;
}
+ // FIXME: handle ambiguity
+
OverloadCandidateSet Candidates;
for (LookupResult::iterator Alloc = R.begin(), AllocEnd = R.end();
Alloc != AllocEnd; ++Alloc) {
@@ -868,8 +872,8 @@
= cast<CXXRecordDecl>(Pointee->getAs<RecordType>()->getDecl());
// Try to find operator delete/operator delete[] in class scope.
- LookupResult Found = LookupQualifiedName(Record, DeleteName,
- LookupOrdinaryName);
+ LookupResult Found;
+ LookupQualifiedName(Found, Record, DeleteName, LookupOrdinaryName);
// FIXME: Diagnose ambiguity properly
assert(!Found.isAmbiguous() && "Ambiguous delete/delete[] not handled");
for (LookupResult::iterator F = Found.begin(), FEnd = Found.end();
Modified: cfe/trunk/lib/Sema/SemaExprObjC.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExprObjC.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExprObjC.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExprObjC.cpp Fri Oct 9 16:13:30 2009
@@ -77,7 +77,7 @@
Ty = Context.getObjCObjectPointerType(Ty);
} else {
IdentifierInfo *NSIdent = &Context.Idents.get("NSString");
- NamedDecl *IF = LookupName(TUScope, NSIdent, LookupOrdinaryName);
+ NamedDecl *IF = LookupSingleName(TUScope, NSIdent, LookupOrdinaryName);
if (ObjCInterfaceDecl *StrIF = dyn_cast_or_null<ObjCInterfaceDecl>(IF)) {
Context.setObjCConstantStringInterface(StrIF);
Ty = Context.getObjCConstantStringInterface();
@@ -387,7 +387,8 @@
} else {
// 'super' has been used outside a method context. If a variable named
// 'super' has been declared, redirect. If not, produce a diagnostic.
- NamedDecl *SuperDecl = LookupName(S, receiverName, LookupOrdinaryName);
+ NamedDecl *SuperDecl
+ = LookupSingleName(S, receiverName, LookupOrdinaryName);
ValueDecl *VD = dyn_cast_or_null<ValueDecl>(SuperDecl);
if (VD) {
ExprResult ReceiverExpr = new (Context) DeclRefExpr(VD, VD->getType(),
@@ -412,7 +413,8 @@
//
// If necessary, the following lookup could move to getObjCInterfaceDecl().
if (!ClassDecl) {
- NamedDecl *IDecl = LookupName(TUScope, receiverName, LookupOrdinaryName);
+ NamedDecl *IDecl
+ = LookupSingleName(TUScope, receiverName, LookupOrdinaryName);
if (TypedefDecl *OCTD = dyn_cast_or_null<TypedefDecl>(IDecl)) {
const ObjCInterfaceType *OCIT;
OCIT = OCTD->getUnderlyingType()->getAs<ObjCInterfaceType>();
Modified: cfe/trunk/lib/Sema/SemaLookup.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaLookup.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaLookup.cpp (original)
+++ cfe/trunk/lib/Sema/SemaLookup.cpp Fri Oct 9 16:13:30 2009
@@ -35,7 +35,6 @@
typedef llvm::SmallVector<UsingDirectiveDecl*, 4> UsingDirectivesTy;
typedef llvm::DenseSet<NamespaceDecl*> NamespaceSet;
-typedef llvm::SmallVector<Sema::LookupResult, 3> LookupResultsTy;
/// UsingDirAncestorCompare - Implements strict weak ordering of
/// UsingDirectives. It orders them by address of its common ancestor.
@@ -107,178 +106,6 @@
}
}
-/// MaybeConstructOverloadSet - Name lookup has determined that the
-/// elements in [I, IEnd) have the name that we are looking for, and
-/// *I is a match for the namespace. This routine returns an
-/// appropriate Decl for name lookup, which may either be *I or an
-/// OverloadedFunctionDecl that represents the overloaded functions in
-/// [I, IEnd).
-///
-/// The existance of this routine is temporary; users of LookupResult
-/// should be able to handle multiple results, to deal with cases of
-/// ambiguity and overloaded functions without needing to create a
-/// Decl node.
-template<typename DeclIterator>
-static NamedDecl *
-MaybeConstructOverloadSet(ASTContext &Context,
- DeclIterator I, DeclIterator IEnd) {
- assert(I != IEnd && "Iterator range cannot be empty");
- assert(!isa<OverloadedFunctionDecl>(*I) &&
- "Cannot have an overloaded function");
-
- if ((*I)->isFunctionOrFunctionTemplate()) {
- // If we found a function, there might be more functions. If
- // so, collect them into an overload set.
- DeclIterator Last = I;
- OverloadedFunctionDecl *Ovl = 0;
- for (++Last;
- Last != IEnd && (*Last)->isFunctionOrFunctionTemplate();
- ++Last) {
- if (!Ovl) {
- // FIXME: We leak this overload set. Eventually, we want to stop
- // building the declarations for these overload sets, so there will be
- // nothing to leak.
- Ovl = OverloadedFunctionDecl::Create(Context, (*I)->getDeclContext(),
- (*I)->getDeclName());
- NamedDecl *ND = (*I)->getUnderlyingDecl();
- if (isa<FunctionDecl>(ND))
- Ovl->addOverload(cast<FunctionDecl>(ND));
- else
- Ovl->addOverload(cast<FunctionTemplateDecl>(ND));
- }
-
- NamedDecl *ND = (*Last)->getUnderlyingDecl();
- if (isa<FunctionDecl>(ND))
- Ovl->addOverload(cast<FunctionDecl>(ND));
- else
- Ovl->addOverload(cast<FunctionTemplateDecl>(ND));
- }
-
- // If we had more than one function, we built an overload
- // set. Return it.
- if (Ovl)
- return Ovl;
- }
-
- return *I;
-}
-
-/// Merges together multiple LookupResults dealing with duplicated Decl's.
-static Sema::LookupResult
-MergeLookupResults(ASTContext &Context, LookupResultsTy &Results) {
- typedef Sema::LookupResult LResult;
- typedef llvm::SmallPtrSet<NamedDecl*, 4> DeclsSetTy;
-
- // Remove duplicated Decl pointing at same Decl, by storing them in
- // associative collection. This might be case for code like:
- //
- // namespace A { int i; }
- // namespace B { using namespace A; }
- // namespace C { using namespace A; }
- //
- // void foo() {
- // using namespace B;
- // using namespace C;
- // ++i; // finds A::i, from both namespace B and C at global scope
- // }
- //
- // C++ [namespace.qual].p3:
- // The same declaration found more than once is not an ambiguity
- // (because it is still a unique declaration).
- DeclsSetTy FoundDecls;
-
- // Counter of tag names, and functions for resolving ambiguity
- // and name hiding.
- std::size_t TagNames = 0, Functions = 0, OrdinaryNonFunc = 0;
-
- LookupResultsTy::iterator I = Results.begin(), End = Results.end();
-
- // No name lookup results, return early.
- if (I == End) return LResult::CreateLookupResult(Context, 0);
-
- // Keep track of the tag declaration we found. We only use this if
- // we find a single tag declaration.
- TagDecl *TagFound = 0;
-
- for (; I != End; ++I) {
- switch (I->getKind()) {
- case LResult::NotFound:
- assert(false &&
- "Should be always successful name lookup result here.");
- break;
-
- case LResult::AmbiguousReference:
- case LResult::AmbiguousBaseSubobjectTypes:
- case LResult::AmbiguousBaseSubobjects:
- assert(false && "Shouldn't get ambiguous lookup here.");
- break;
-
- case LResult::Found: {
- NamedDecl *ND = I->getAsDecl()->getUnderlyingDecl();
-
- if (TagDecl *TD = dyn_cast<TagDecl>(ND)) {
- TagFound = TD->getCanonicalDecl();
- TagNames += FoundDecls.insert(TagFound)? 1 : 0;
- } else if (ND->isFunctionOrFunctionTemplate())
- Functions += FoundDecls.insert(ND)? 1 : 0;
- else
- FoundDecls.insert(ND);
- break;
- }
-
- case LResult::FoundOverloaded:
- for (LResult::iterator FI = I->begin(), FEnd = I->end(); FI != FEnd; ++FI)
- Functions += FoundDecls.insert(*FI)? 1 : 0;
- break;
- }
- }
- OrdinaryNonFunc = FoundDecls.size() - TagNames - Functions;
- bool Ambiguous = false, NameHidesTags = false;
-
- if (FoundDecls.size() == 1) {
- // 1) Exactly one result.
- } else if (TagNames > 1) {
- // 2) Multiple tag names (even though they may be hidden by an
- // object name).
- Ambiguous = true;
- } else if (FoundDecls.size() - TagNames == 1) {
- // 3) Ordinary name hides (optional) tag.
- NameHidesTags = TagFound;
- } else if (Functions) {
- // C++ [basic.lookup].p1:
- // ... Name lookup may associate more than one declaration with
- // a name if it finds the name to be a function name; the declarations
- // are said to form a set of overloaded functions (13.1).
- // Overload resolution (13.3) takes place after name lookup has succeeded.
- //
- if (!OrdinaryNonFunc) {
- // 4) Functions hide tag names.
- NameHidesTags = TagFound;
- } else {
- // 5) Functions + ordinary names.
- Ambiguous = true;
- }
- } else {
- // 6) Multiple non-tag names
- Ambiguous = true;
- }
-
- if (Ambiguous)
- return LResult::CreateLookupResult(Context,
- FoundDecls.begin(), FoundDecls.size());
- if (NameHidesTags) {
- // There's only one tag, TagFound. Remove it.
- assert(TagFound && FoundDecls.count(TagFound) && "No tag name found?");
- FoundDecls.erase(TagFound);
- }
-
- // Return successful name lookup result.
- return LResult::CreateLookupResult(Context,
- MaybeConstructOverloadSet(Context,
- FoundDecls.begin(),
- FoundDecls.end()));
-}
-
// Retrieve the set of identifier namespaces that correspond to a
// specific kind of name lookup.
inline unsigned
@@ -324,97 +151,78 @@
return IDNS;
}
-Sema::LookupResult
-Sema::LookupResult::CreateLookupResult(ASTContext &Context, NamedDecl *D) {
- if (D)
- D = D->getUnderlyingDecl();
-
- LookupResult Result;
- Result.StoredKind = (D && isa<OverloadedFunctionDecl>(D))?
- OverloadedDeclSingleDecl : SingleDecl;
- Result.First = reinterpret_cast<uintptr_t>(D);
- Result.Last = 0;
- Result.Context = &Context;
- return Result;
-}
-
-/// @brief Moves the name-lookup results from Other to this LookupResult.
-Sema::LookupResult
-Sema::LookupResult::CreateLookupResult(ASTContext &Context,
- IdentifierResolver::iterator F,
- IdentifierResolver::iterator L) {
- LookupResult Result;
- Result.Context = &Context;
-
- if (F != L && (*F)->isFunctionOrFunctionTemplate()) {
- IdentifierResolver::iterator Next = F;
- ++Next;
- if (Next != L && (*Next)->isFunctionOrFunctionTemplate()) {
- Result.StoredKind = OverloadedDeclFromIdResolver;
- Result.First = F.getAsOpaqueValue();
- Result.Last = L.getAsOpaqueValue();
- return Result;
- }
- }
+// Necessary because CXXBasePaths is not complete in Sema.h
+void Sema::LookupResult::deletePaths(CXXBasePaths *Paths) {
+ delete Paths;
+}
- NamedDecl *D = *F;
- if (D)
- D = D->getUnderlyingDecl();
-
- Result.StoredKind = SingleDecl;
- Result.First = reinterpret_cast<uintptr_t>(D);
- Result.Last = 0;
- return Result;
-}
-
-Sema::LookupResult
-Sema::LookupResult::CreateLookupResult(ASTContext &Context,
- DeclContext::lookup_iterator F,
- DeclContext::lookup_iterator L) {
- LookupResult Result;
- Result.Context = &Context;
-
- if (F != L && (*F)->isFunctionOrFunctionTemplate()) {
- DeclContext::lookup_iterator Next = F;
- ++Next;
- if (Next != L && (*Next)->isFunctionOrFunctionTemplate()) {
- Result.StoredKind = OverloadedDeclFromDeclContext;
- Result.First = reinterpret_cast<uintptr_t>(F);
- Result.Last = reinterpret_cast<uintptr_t>(L);
- return Result;
- }
- }
+void Sema::LookupResult::resolveKind() {
+ unsigned N = Decls.size();
- NamedDecl *D = *F;
- if (D)
- D = D->getUnderlyingDecl();
+ // Fast case: no possible ambiguity.
+ if (N <= 1) return;
- Result.StoredKind = SingleDecl;
- Result.First = reinterpret_cast<uintptr_t>(D);
- Result.Last = 0;
- return Result;
-}
+ llvm::SmallPtrSet<NamedDecl*, 16> Unique;
+
+ bool Ambiguous = false;
+ bool HasTag = false, HasFunction = false, HasNonFunction = false;
-/// @brief Determine the result of name lookup.
-Sema::LookupResult::LookupKind Sema::LookupResult::getKind() const {
- switch (StoredKind) {
- case SingleDecl:
- return (reinterpret_cast<Decl *>(First) != 0)? Found : NotFound;
+ unsigned UniqueTagIndex = 0;
+
+ unsigned I = 0;
+ while (I < N) {
+ NamedDecl *D = Decls[I];
+ assert(D == D->getUnderlyingDecl());
+
+ NamedDecl *CanonD = cast<NamedDecl>(D->getCanonicalDecl());
+ if (!Unique.insert(CanonD)) {
+ // If it's not unique, pull something off the back (and
+ // continue at this index).
+ Decls[I] = Decls[--N];
+ } else if (isa<UnresolvedUsingDecl>(D)) {
+ // FIXME: proper support for UnresolvedUsingDecls.
+ Decls[I] = Decls[--N];
+ } else {
+ // Otherwise, do some decl type analysis and then continue.
+ if (isa<TagDecl>(D)) {
+ if (HasTag)
+ Ambiguous = true;
+ UniqueTagIndex = I;
+ HasTag = true;
+ } else if (D->isFunctionOrFunctionTemplate()) {
+ HasFunction = true;
+ } else {
+ if (HasNonFunction)
+ Ambiguous = true;
+ HasNonFunction = true;
+ }
+ I++;
+ }
+ }
- case OverloadedDeclSingleDecl:
- case OverloadedDeclFromIdResolver:
- case OverloadedDeclFromDeclContext:
- return FoundOverloaded;
+ // C++ [basic.scope.hiding]p2:
+ // A class name or enumeration name can be hidden by the name of
+ // an object, function, or enumerator declared in the same
+ // scope. If a class or enumeration name and an object, function,
+ // or enumerator are declared in the same scope (in any order)
+ // with the same name, the class or enumeration name is hidden
+ // wherever the object, function, or enumerator name is visible.
+ // But it's still an error if there are distinct tag types found,
+ // even if they're not visible. (ref?)
+ if (HasTag && !Ambiguous && (HasFunction || HasNonFunction))
+ Decls[UniqueTagIndex] = Decls[--N];
- case AmbiguousLookupStoresBasePaths:
- return Last? AmbiguousBaseSubobjectTypes : AmbiguousBaseSubobjects;
+ Decls.set_size(N);
- case AmbiguousLookupStoresDecls:
- return AmbiguousReference;
- }
+ if (HasFunction && HasNonFunction)
+ Ambiguous = true;
- // We can't ever get here.
- return NotFound;
+ if (Ambiguous)
+ Kind = AmbiguousReference;
+ else if (N > 1)
+ Kind = FoundOverloaded;
+ else
+ Kind = Found;
}
/// @brief Converts the result of name lookup into a single (possible
@@ -430,191 +238,93 @@
/// 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 *Sema::LookupResult::getAsDecl() const {
- switch (StoredKind) {
- case SingleDecl:
- return reinterpret_cast<NamedDecl *>(First);
-
- case OverloadedDeclFromIdResolver:
- return MaybeConstructOverloadSet(*Context,
- IdentifierResolver::iterator::getFromOpaqueValue(First),
- IdentifierResolver::iterator::getFromOpaqueValue(Last));
-
- case OverloadedDeclFromDeclContext:
- return MaybeConstructOverloadSet(*Context,
- reinterpret_cast<DeclContext::lookup_iterator>(First),
- reinterpret_cast<DeclContext::lookup_iterator>(Last));
-
- case OverloadedDeclSingleDecl:
- return reinterpret_cast<OverloadedFunctionDecl*>(First);
-
- case AmbiguousLookupStoresDecls:
- case AmbiguousLookupStoresBasePaths:
- assert(false &&
- "Name lookup returned an ambiguity that could not be handled");
- break;
+NamedDecl *Sema::LookupResult::getAsSingleDecl(ASTContext &C) const {
+ size_t size = Decls.size();
+ if (size == 0) return 0;
+ if (size == 1) return *begin();
+
+ 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;
+ assert(ND->getUnderlyingDecl() == ND
+ && "decls in lookup result should have redirections stripped");
+ assert(ND->isFunctionOrFunctionTemplate());
+ if (isa<FunctionDecl>(ND))
+ Ovl->addOverload(cast<FunctionDecl>(ND));
+ else
+ Ovl->addOverload(cast<FunctionTemplateDecl>(ND));
+ // FIXME: UnresolvedUsingDecls.
}
-
- return 0;
+
+ return Ovl;
}
-/// @brief Retrieves the BasePaths structure describing an ambiguous
-/// name lookup, or null.
-CXXBasePaths *Sema::LookupResult::getBasePaths() const {
- if (StoredKind == AmbiguousLookupStoresBasePaths)
- return reinterpret_cast<CXXBasePaths *>(First);
- return 0;
+void Sema::LookupResult::addDeclsFromBasePaths(const CXXBasePaths &P) {
+ CXXBasePaths::paths_iterator I, E;
+ DeclContext::lookup_iterator DI, DE;
+ for (I = P.begin(), E = P.end(); I != E; ++I)
+ for (llvm::tie(DI,DE) = I->Decls; DI != DE; ++DI)
+ addDecl(*DI);
}
-Sema::LookupResult::iterator::reference
-Sema::LookupResult::iterator::operator*() const {
- switch (Result->StoredKind) {
- case SingleDecl:
- return reinterpret_cast<NamedDecl*>(Current);
-
- case OverloadedDeclSingleDecl:
- return *reinterpret_cast<NamedDecl**>(Current);
-
- case OverloadedDeclFromIdResolver:
- return *IdentifierResolver::iterator::getFromOpaqueValue(Current);
-
- case AmbiguousLookupStoresBasePaths:
- if (Result->Last)
- return *reinterpret_cast<NamedDecl**>(Current);
-
- // Fall through to handle the DeclContext::lookup_iterator we're
- // storing.
-
- case OverloadedDeclFromDeclContext:
- case AmbiguousLookupStoresDecls:
- return *reinterpret_cast<DeclContext::lookup_iterator>(Current);
- }
-
- return 0;
+void Sema::LookupResult::setAmbiguousBaseSubobjects(CXXBasePaths &P) {
+ Paths = new CXXBasePaths;
+ Paths->swap(P);
+ addDeclsFromBasePaths(*Paths);
+ resolveKind();
+ Kind = AmbiguousBaseSubobjects;
}
-Sema::LookupResult::iterator& Sema::LookupResult::iterator::operator++() {
- switch (Result->StoredKind) {
- case SingleDecl:
- Current = reinterpret_cast<uintptr_t>((NamedDecl*)0);
- break;
-
- case OverloadedDeclSingleDecl: {
- NamedDecl ** I = reinterpret_cast<NamedDecl**>(Current);
- ++I;
- Current = reinterpret_cast<uintptr_t>(I);
- break;
- }
-
- case OverloadedDeclFromIdResolver: {
- IdentifierResolver::iterator I
- = IdentifierResolver::iterator::getFromOpaqueValue(Current);
- ++I;
- Current = I.getAsOpaqueValue();
- break;
- }
-
- case AmbiguousLookupStoresBasePaths:
- if (Result->Last) {
- NamedDecl ** I = reinterpret_cast<NamedDecl**>(Current);
- ++I;
- Current = reinterpret_cast<uintptr_t>(I);
- break;
- }
- // Fall through to handle the DeclContext::lookup_iterator we're
- // storing.
-
- case OverloadedDeclFromDeclContext:
- case AmbiguousLookupStoresDecls: {
- DeclContext::lookup_iterator I
- = reinterpret_cast<DeclContext::lookup_iterator>(Current);
- ++I;
- Current = reinterpret_cast<uintptr_t>(I);
- break;
- }
- }
-
- return *this;
+void Sema::LookupResult::setAmbiguousBaseSubobjectTypes(CXXBasePaths &P) {
+ Paths = new CXXBasePaths;
+ Paths->swap(P);
+ addDeclsFromBasePaths(*Paths);
+ resolveKind();
+ Kind = AmbiguousBaseSubobjectTypes;
}
-Sema::LookupResult::iterator Sema::LookupResult::begin() {
- switch (StoredKind) {
- case SingleDecl:
- case OverloadedDeclFromIdResolver:
- case OverloadedDeclFromDeclContext:
- case AmbiguousLookupStoresDecls:
- return iterator(this, First);
-
- case OverloadedDeclSingleDecl: {
- OverloadedFunctionDecl * Ovl =
- reinterpret_cast<OverloadedFunctionDecl*>(First);
- return iterator(this,
- reinterpret_cast<uintptr_t>(&(*Ovl->function_begin())));
- }
-
- case AmbiguousLookupStoresBasePaths:
- if (Last)
- return iterator(this,
- reinterpret_cast<uintptr_t>(getBasePaths()->found_decls_begin()));
- else
- return iterator(this,
- reinterpret_cast<uintptr_t>(getBasePaths()->front().Decls.first));
+void Sema::LookupResult::print(llvm::raw_ostream &Out) {
+ Out << Decls.size() << " result(s)";
+ if (isAmbiguous()) Out << ", ambiguous";
+ if (Paths) Out << ", base paths present";
+
+ for (iterator I = begin(), E = end(); I != E; ++I) {
+ Out << "\n";
+ (*I)->print(Out, 2);
}
-
- // Required to suppress GCC warning.
- return iterator();
}
-Sema::LookupResult::iterator Sema::LookupResult::end() {
- switch (StoredKind) {
- case SingleDecl:
- case OverloadedDeclFromIdResolver:
- case OverloadedDeclFromDeclContext:
- case AmbiguousLookupStoresDecls:
- return iterator(this, Last);
-
- case OverloadedDeclSingleDecl: {
- OverloadedFunctionDecl * Ovl =
- reinterpret_cast<OverloadedFunctionDecl*>(First);
- return iterator(this,
- reinterpret_cast<uintptr_t>(&(*Ovl->function_end())));
- }
-
- case AmbiguousLookupStoresBasePaths:
- if (Last)
- return iterator(this,
- reinterpret_cast<uintptr_t>(getBasePaths()->found_decls_end()));
- else
- return iterator(this, reinterpret_cast<uintptr_t>(
- getBasePaths()->front().Decls.second));
- }
+// 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, DeclContext *DC,
+ DeclarationName Name,
+ Sema::LookupNameKind NameKind,
+ unsigned IDNS) {
+ bool Found = false;
- // Required to suppress GCC warning.
- return iterator();
-}
+ DeclContext::lookup_iterator I, E;
+ for (llvm::tie(I, E) = DC->lookup(Name); I != E; ++I)
+ if (Sema::isAcceptableLookupResult(*I, NameKind, IDNS))
+ R.addDecl(*I), Found = true;
-void Sema::LookupResult::Destroy() {
- if (CXXBasePaths *Paths = getBasePaths())
- delete Paths;
- else if (getKind() == AmbiguousReference)
- delete[] reinterpret_cast<NamedDecl **>(First);
+ return Found;
}
-static void
-CppNamespaceLookup(ASTContext &Context, DeclContext *NS,
+static bool
+CppNamespaceLookup(Sema::LookupResult &R, ASTContext &Context, DeclContext *NS,
DeclarationName Name, Sema::LookupNameKind NameKind,
- unsigned IDNS, LookupResultsTy &Results,
- UsingDirectivesTy *UDirs = 0) {
+ unsigned IDNS, UsingDirectivesTy *UDirs = 0) {
assert(NS && NS->isFileContext() && "CppNamespaceLookup() requires namespace!");
// Perform qualified name lookup into the LookupCtx.
- DeclContext::lookup_iterator I, E;
- for (llvm::tie(I, E) = NS->lookup(Name); I != E; ++I)
- if (Sema::isAcceptableLookupResult(*I, NameKind, IDNS)) {
- Results.push_back(Sema::LookupResult::CreateLookupResult(Context, I, E));
- break;
- }
+ bool Found = LookupDirect(R, NS, Name, NameKind, IDNS);
if (UDirs) {
// For each UsingDirectiveDecl, which common ancestor is equal
@@ -625,9 +335,13 @@
UsingDirAncestorCompare());
for (; UI != UEnd; ++UI)
- CppNamespaceLookup(Context, (*UI)->getNominatedNamespace(),
- Name, NameKind, IDNS, Results);
+ if (LookupDirect(R, (*UI)->getNominatedNamespace(), Name, NameKind, IDNS))
+ Found = true;
}
+
+ R.resolveKind();
+
+ return Found;
}
static bool isNamespaceOrTranslationUnitScope(Scope *S) {
@@ -645,8 +359,8 @@
return 0;
}
-std::pair<bool, Sema::LookupResult>
-Sema::CppLookupName(Scope *S, DeclarationName Name,
+bool
+Sema::CppLookupName(LookupResult &R, Scope *S, DeclarationName Name,
LookupNameKind NameKind, bool RedeclarationOnly) {
assert(getLangOptions().CPlusPlus &&
"Can perform only C++ lookup");
@@ -684,25 +398,19 @@
//
for (; S && !isNamespaceOrTranslationUnitScope(S); S = S->getParent()) {
// Check whether the IdResolver has anything in this scope.
+ bool Found = false;
for (; I != IEnd && S->isDeclScope(DeclPtrTy::make(*I)); ++I) {
if (isAcceptableLookupResult(*I, NameKind, IDNS)) {
- // We found something. Look for anything else in our scope
- // with this same name and in an acceptable identifier
- // namespace, so that we can construct an overload set if we
- // need to.
- IdentifierResolver::iterator LastI = I;
- for (++LastI; LastI != IEnd; ++LastI) {
- if (!S->isDeclScope(DeclPtrTy::make(*LastI)))
- break;
- }
- LookupResult Result =
- LookupResult::CreateLookupResult(Context, I, LastI);
- return std::make_pair(true, Result);
+ Found = true;
+ R.addDecl(*I);
}
}
+ if (Found) {
+ R.resolveKind();
+ return true;
+ }
+
if (DeclContext *Ctx = static_cast<DeclContext*>(S->getEntity())) {
- LookupResult R;
-
DeclContext *OuterCtx = findOuterContext(S);
for (; Ctx && Ctx->getPrimaryContext() != OuterCtx;
Ctx = Ctx->getLookupParent()) {
@@ -715,9 +423,8 @@
// example, inside a class without any base classes, we never need to
// perform qualified lookup because all of the members are on top of the
// identifier chain.
- R = LookupQualifiedName(Ctx, Name, NameKind, RedeclarationOnly);
- if (R)
- return std::make_pair(true, R);
+ if (LookupQualifiedName(R, Ctx, Name, NameKind, RedeclarationOnly))
+ return true;
}
}
}
@@ -740,8 +447,6 @@
// that aren't strictly lexical, and therefore we walk through the
// context as well as walking through the scopes.
- LookupResultsTy LookupResults;
- bool LookedInCtx = false;
for (; S; S = S->getParent()) {
DeclContext *Ctx = static_cast<DeclContext *>(S->getEntity());
if (Ctx->isTransparentContext())
@@ -751,45 +456,32 @@
"We should have been looking only at file context here already.");
// Check whether the IdResolver has anything in this scope.
+ bool Found = false;
for (; I != IEnd && S->isDeclScope(DeclPtrTy::make(*I)); ++I) {
if (isAcceptableLookupResult(*I, NameKind, IDNS)) {
// We found something. Look for anything else in our scope
// with this same name and in an acceptable identifier
// namespace, so that we can construct an overload set if we
// need to.
- IdentifierResolver::iterator LastI = I;
- for (++LastI; LastI != IEnd; ++LastI) {
- if (!S->isDeclScope(DeclPtrTy::make(*LastI)))
- break;
- }
-
- // We store name lookup result, and continue trying to look into
- // associated context, and maybe namespaces nominated by
- // using-directives.
- LookupResults.push_back(
- LookupResult::CreateLookupResult(Context, I, LastI));
- break;
+ Found = true;
+ R.addDecl(*I);
}
}
- LookedInCtx = true;
// Look into context considering using-directives.
- CppNamespaceLookup(Context, Ctx, Name, NameKind, IDNS,
- LookupResults, &UDirs);
+ if (CppNamespaceLookup(R, Context, Ctx, Name, NameKind, IDNS, &UDirs))
+ Found = true;
- LookupResult Result;
- if ((Result = MergeLookupResults(Context, LookupResults)) ||
- (RedeclarationOnly && !Ctx->isTransparentContext()))
- return std::make_pair(true, Result);
- }
-
- if (!(LookedInCtx || LookupResults.empty())) {
- // We didn't Performed lookup in Scope entity, so we return
- // result form IdentifierResolver.
- assert((LookupResults.size() == 1) && "Wrong size!");
- return std::make_pair(true, LookupResults.front());
+ if (Found) {
+ R.resolveKind();
+ return true;
+ }
+
+ if (RedeclarationOnly && !Ctx->isTransparentContext())
+ return false;
}
- return std::make_pair(false, LookupResult());
+
+ return !R.empty();
}
/// @brief Perform unqualified name lookup starting from a given
@@ -823,11 +515,10 @@
/// @returns The result of name lookup, which includes zero or more
/// declarations and possibly additional information used to diagnose
/// ambiguities.
-Sema::LookupResult
-Sema::LookupName(Scope *S, DeclarationName Name, LookupNameKind NameKind,
- bool RedeclarationOnly, bool AllowBuiltinCreation,
- SourceLocation Loc) {
- if (!Name) return LookupResult::CreateLookupResult(Context, 0);
+bool Sema::LookupName(LookupResult &R, Scope *S, DeclarationName Name,
+ LookupNameKind NameKind, bool RedeclarationOnly,
+ bool AllowBuiltinCreation, SourceLocation Loc) {
+ if (!Name) return false;
if (!getLangOptions().CPlusPlus) {
// Unqualified name lookup in C/Objective-C is purely lexical, so
@@ -897,6 +588,8 @@
continue;
}
+ R.addDecl(*I);
+
if ((*I)->getAttr<OverloadableAttr>()) {
// If this declaration has the "overloadable" attribute, we
// might have a set of overloaded functions.
@@ -912,20 +605,18 @@
for (++LastI; LastI != IEnd; ++LastI) {
if (!S->isDeclScope(DeclPtrTy::make(*LastI)))
break;
+ R.addDecl(*LastI);
}
-
- return LookupResult::CreateLookupResult(Context, I, LastI);
}
- // We have a single lookup result.
- return LookupResult::CreateLookupResult(Context, *I);
+ R.resolveKind();
+
+ return true;
}
} else {
// Perform C++ unqualified name lookup.
- std::pair<bool, LookupResult> MaybeResult =
- CppLookupName(S, Name, NameKind, RedeclarationOnly);
- if (MaybeResult.first)
- return MaybeResult.second;
+ if (CppLookupName(R, S, Name, NameKind, RedeclarationOnly))
+ return true;
}
// If we didn't find a use of this identifier, and if the identifier
@@ -941,15 +632,16 @@
// 'malloc'. Instead, we'll just error.
if (getLangOptions().CPlusPlus &&
Context.BuiltinInfo.isPredefinedLibFunction(BuiltinID))
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
- return LookupResult::CreateLookupResult(Context,
- LazilyCreateBuiltin((IdentifierInfo *)II, BuiltinID,
- S, RedeclarationOnly, Loc));
+ NamedDecl *D = LazilyCreateBuiltin((IdentifierInfo *)II, BuiltinID,
+ S, RedeclarationOnly, Loc);
+ if (D) R.addDecl(D);
+ return (D != NULL);
}
}
}
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
}
/// @brief Perform qualified name lookup into a given context.
@@ -982,13 +674,13 @@
/// @returns The result of name lookup, which includes zero or more
/// declarations and possibly additional information used to diagnose
/// ambiguities.
-Sema::LookupResult
-Sema::LookupQualifiedName(DeclContext *LookupCtx, DeclarationName Name,
- LookupNameKind NameKind, bool RedeclarationOnly) {
+bool Sema::LookupQualifiedName(LookupResult &R, DeclContext *LookupCtx,
+ DeclarationName Name, LookupNameKind NameKind,
+ bool RedeclarationOnly) {
assert(LookupCtx && "Sema::LookupQualifiedName requires a lookup context");
if (!Name)
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
// If we're performing qualified name lookup (e.g., lookup into a
// struct), find fields as part of ordinary name lookup.
@@ -1007,15 +699,15 @@
"Declaration context must already be complete!");
// Perform qualified name lookup into the LookupCtx.
- DeclContext::lookup_iterator I, E;
- for (llvm::tie(I, E) = LookupCtx->lookup(Name); I != E; ++I)
- if (isAcceptableLookupResult(*I, NameKind, IDNS))
- return LookupResult::CreateLookupResult(Context, I, E);
+ if (LookupDirect(R, LookupCtx, Name, NameKind, IDNS)) {
+ R.resolveKind();
+ return true;
+ }
// If this isn't a C++ class, we aren't allowed to look into base
// classes, we're done.
if (RedeclarationOnly || !isa<CXXRecordDecl>(LookupCtx))
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
// Perform lookup into our base classes.
CXXRecordDecl *LookupRec = cast<CXXRecordDecl>(LookupCtx);
@@ -1041,7 +733,7 @@
case LookupObjCImplementationName:
case LookupObjCCategoryImplName:
// These lookups will never find a member in a C++ class (or base class).
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
case LookupNestedNameSpecifierName:
BaseCallback = &CXXRecordDecl::FindNestedNameSpecifierMember;
@@ -1049,7 +741,7 @@
}
if (!LookupRec->lookupInBases(BaseCallback, Name.getAsOpaquePtr(), Paths))
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
// C++ [class.member.lookup]p2:
// [...] If the resulting set of declarations are not all from
@@ -1066,16 +758,15 @@
// Determine whether we're looking at a distinct sub-object or not.
if (SubobjectType.isNull()) {
- // This is the first subobject we've looked at. Record it's type.
+ // This is the first subobject we've looked at. Record its type.
SubobjectType = Context.getCanonicalType(PathElement.Base->getType());
SubobjectNumber = PathElement.SubobjectNumber;
} else if (SubobjectType
!= Context.getCanonicalType(PathElement.Base->getType())) {
// We found members of the given name in two subobjects of
// different types. This lookup is ambiguous.
- CXXBasePaths *PathsOnHeap = new CXXBasePaths;
- PathsOnHeap->swap(Paths);
- return LookupResult::CreateLookupResult(Context, PathsOnHeap, true);
+ R.setAmbiguousBaseSubobjectTypes(Paths);
+ return true;
} else if (SubobjectNumber != PathElement.SubobjectNumber) {
// We have a different subobject of the same type.
@@ -1111,21 +802,18 @@
// We have found a nonstatic member name in multiple, distinct
// subobjects. Name lookup is ambiguous.
- CXXBasePaths *PathsOnHeap = new CXXBasePaths;
- PathsOnHeap->swap(Paths);
- return LookupResult::CreateLookupResult(Context, PathsOnHeap, false);
+ R.setAmbiguousBaseSubobjects(Paths);
+ return true;
}
}
// Lookup in a base class succeeded; return these results.
- // If we found a function declaration, return an overload set.
- if ((*Paths.front().Decls.first)->isFunctionOrFunctionTemplate())
- return LookupResult::CreateLookupResult(Context,
- Paths.front().Decls.first, Paths.front().Decls.second);
-
- // We found a non-function declaration; return a single declaration.
- return LookupResult::CreateLookupResult(Context, *Paths.front().Decls.first);
+ DeclContext::lookup_iterator I, E;
+ for (llvm::tie(I,E) = Paths.front().Decls; I != E; ++I)
+ R.addDecl(*I);
+ R.resolveKind();
+ return true;
}
/// @brief Performs name lookup for a name that was parsed in the
@@ -1152,17 +840,16 @@
/// @param EnteringContext Indicates whether we are going to enter the
/// context of the scope-specifier SS (if present).
///
-/// @returns The result of qualified or unqualified name lookup.
-Sema::LookupResult
-Sema::LookupParsedName(Scope *S, const CXXScopeSpec *SS,
- DeclarationName Name, LookupNameKind NameKind,
- bool RedeclarationOnly, bool AllowBuiltinCreation,
- SourceLocation Loc,
- bool EnteringContext) {
+/// @returns True if any decls were found (but possibly ambiguous)
+bool Sema::LookupParsedName(LookupResult &R, Scope *S, const CXXScopeSpec *SS,
+ DeclarationName Name, LookupNameKind NameKind,
+ bool RedeclarationOnly, bool AllowBuiltinCreation,
+ SourceLocation Loc,
+ bool EnteringContext) {
if (SS && SS->isInvalid()) {
// When the scope specifier is invalid, don't even look for
// anything.
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
}
if (SS && SS->isSet()) {
@@ -1170,20 +857,20 @@
// We have resolved the scope specifier to a particular declaration
// contex, and will perform name lookup in that context.
if (!DC->isDependentContext() && RequireCompleteDeclContext(*SS))
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
- return LookupQualifiedName(DC, Name, NameKind, RedeclarationOnly);
+ return LookupQualifiedName(R, DC, Name, NameKind, RedeclarationOnly);
}
// We could not resolve the scope specified to a specific declaration
// context, which means that SS refers to an unknown specialization.
// Name lookup can't find anything in this case.
- return LookupResult::CreateLookupResult(Context, 0);
+ return false;
}
// Perform unqualified name lookup starting in the given scope.
- return LookupName(S, Name, NameKind, RedeclarationOnly, AllowBuiltinCreation,
- Loc);
+ return LookupName(R, S, Name, NameKind, RedeclarationOnly,
+ AllowBuiltinCreation, Loc);
}
@@ -1222,7 +909,6 @@
Diag((*Found)->getLocation(), diag::note_ambiguous_member_found);
- Result.Destroy();
return true;
}
@@ -1240,24 +926,18 @@
Diag(D->getLocation(), diag::note_ambiguous_member_found);
}
- Result.Destroy();
- return true;
- } else if (Result.getKind() == LookupResult::AmbiguousReference) {
- Diag(NameLoc, diag::err_ambiguous_reference) << Name << LookupRange;
-
- NamedDecl **DI = reinterpret_cast<NamedDecl **>(Result.First),
- **DEnd = reinterpret_cast<NamedDecl **>(Result.Last);
-
- for (; DI != DEnd; ++DI)
- Diag((*DI)->getLocation(), diag::note_ambiguous_candidate) << *DI;
-
- Result.Destroy();
return true;
}
- assert(false && "Unhandled form of name lookup ambiguity");
+ assert(Result.getKind() == LookupResult::AmbiguousReference &&
+ "unhandled form of name lookup ambiguity");
+ Diag(NameLoc, diag::err_ambiguous_reference) << Name << LookupRange;
+
+
+ LookupResult::iterator DI = Result.begin(), DE = Result.end();
+ for (; DI != DE; ++DI)
+ Diag((*DI)->getLocation(), diag::note_ambiguous_candidate) << *DI;
- // We can't reach here.
return true;
}
@@ -1661,14 +1341,14 @@
/// \brief Find the protocol with the given name, if any.
ObjCProtocolDecl *Sema::LookupProtocol(IdentifierInfo *II) {
- Decl *D = LookupName(TUScope, II, LookupObjCProtocolName).getAsDecl();
+ Decl *D = LookupSingleName(TUScope, II, LookupObjCProtocolName);
return cast_or_null<ObjCProtocolDecl>(D);
}
/// \brief Find the Objective-C category implementation with the given
/// name, if any.
ObjCCategoryImplDecl *Sema::LookupObjCCategoryImpl(IdentifierInfo *II) {
- Decl *D = LookupName(TUScope, II, LookupObjCCategoryImplName).getAsDecl();
+ Decl *D = LookupSingleName(TUScope, II, LookupObjCCategoryImplName);
return cast_or_null<ObjCCategoryImplDecl>(D);
}
@@ -1678,8 +1358,8 @@
Decl *Sema::LookupQualifiedNameWithType(DeclContext *DC,
DeclarationName Name,
QualType T) {
- LookupResult result =
- LookupQualifiedName(DC, Name, LookupOrdinaryName, true);
+ LookupResult result;
+ LookupQualifiedName(result, DC, Name, LookupOrdinaryName, true);
CanQualType CQT = Context.getCanonicalType(T);
@@ -1708,11 +1388,12 @@
// of type T2 or "reference to (possibly cv-qualified) T2",
// when T2 is an enumeration type, are candidate functions.
DeclarationName OpName = Context.DeclarationNames.getCXXOperatorName(Op);
- LookupResult Operators = LookupName(S, OpName, LookupOperatorName);
+ LookupResult Operators;
+ LookupName(Operators, S, OpName, LookupOperatorName);
assert(!Operators.isAmbiguous() && "Operator lookup cannot be ambiguous");
- if (!Operators)
+ if (Operators.empty())
return;
for (LookupResult::iterator Op = Operators.begin(), OpEnd = Operators.end();
Modified: cfe/trunk/lib/Sema/SemaOverload.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaOverload.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaOverload.cpp (original)
+++ cfe/trunk/lib/Sema/SemaOverload.cpp Fri Oct 9 16:13:30 2009
@@ -2762,8 +2762,9 @@
if (RequireCompleteType(OpLoc, T1, PartialDiagnostic(0)))
return;
- LookupResult Operators = LookupQualifiedName(T1Rec->getDecl(), OpName,
- LookupOrdinaryName, false);
+ LookupResult Operators;
+ LookupQualifiedName(Operators, T1Rec->getDecl(), OpName,
+ LookupOrdinaryName, false);
for (LookupResult::iterator Oper = Operators.begin(),
OperEnd = Operators.end();
Oper != OperEnd;
@@ -5070,8 +5071,8 @@
OverloadCandidateSet CandidateSet;
const RecordType *BaseRecord = Base->getType()->getAs<RecordType>();
- LookupResult R = LookupQualifiedName(BaseRecord->getDecl(), OpName,
- LookupOrdinaryName);
+ LookupResult R;
+ LookupQualifiedName(R, BaseRecord->getDecl(), OpName, LookupOrdinaryName);
for (LookupResult::iterator Oper = R.begin(), OperEnd = R.end();
Oper != OperEnd; ++Oper)
Modified: cfe/trunk/lib/Sema/SemaTemplate.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaTemplate.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaTemplate.cpp (original)
+++ cfe/trunk/lib/Sema/SemaTemplate.cpp Fri Oct 9 16:13:30 2009
@@ -135,7 +135,7 @@
if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(*SS))
return TNK_Non_template;
- Found = LookupQualifiedName(LookupCtx, &II, LookupOrdinaryName);
+ LookupQualifiedName(Found, LookupCtx, &II, LookupOrdinaryName);
if (ObjectTypePtr && Found.getKind() == LookupResult::NotFound) {
// C++ [basic.lookup.classref]p1:
@@ -150,7 +150,7 @@
//
// FIXME: When we're instantiating a template, do we actually have to
// look in the scope of the template? Seems fishy...
- Found = LookupName(S, &II, LookupOrdinaryName);
+ LookupName(Found, S, &II, LookupOrdinaryName);
ObjectTypeSearchedInScope = true;
}
} else if (isDependent) {
@@ -158,14 +158,15 @@
return TNK_Non_template;
} else {
// Perform unqualified name lookup in the current scope.
- Found = LookupName(S, &II, LookupOrdinaryName);
+ LookupName(Found, S, &II, LookupOrdinaryName);
}
// FIXME: Cope with ambiguous name-lookup results.
assert(!Found.isAmbiguous() &&
"Cannot handle template name-lookup ambiguities");
- NamedDecl *Template = isAcceptableTemplateName(Context, Found);
+ NamedDecl *Template
+ = isAcceptableTemplateName(Context, Found.getAsSingleDecl(Context));
if (!Template)
return TNK_Non_template;
@@ -175,9 +176,11 @@
// template, the name is also looked up in the context of the entire
// postfix-expression and [...]
//
- LookupResult FoundOuter = LookupName(S, &II, LookupOrdinaryName);
+ LookupResult FoundOuter;
+ LookupName(FoundOuter, S, &II, LookupOrdinaryName);
// FIXME: Handle ambiguities in this lookup better
- NamedDecl *OuterTemplate = isAcceptableTemplateName(Context, FoundOuter);
+ NamedDecl *OuterTemplate
+ = isAcceptableTemplateName(Context, FoundOuter.getAsSingleDecl(Context));
if (!OuterTemplate) {
// - if the name is not found, the name found in the class of the
@@ -284,7 +287,7 @@
bool Invalid = false;
if (ParamName) {
- NamedDecl *PrevDecl = LookupName(S, ParamName, LookupTagName);
+ NamedDecl *PrevDecl = LookupSingleName(S, ParamName, LookupTagName);
if (PrevDecl && PrevDecl->isTemplateParameter())
Invalid = Invalid || DiagnoseTemplateParameterShadow(ParamNameLoc,
PrevDecl);
@@ -402,7 +405,7 @@
IdentifierInfo *ParamName = D.getIdentifier();
if (ParamName) {
- NamedDecl *PrevDecl = LookupName(S, ParamName, LookupTagName);
+ NamedDecl *PrevDecl = LookupSingleName(S, ParamName, LookupTagName);
if (PrevDecl && PrevDecl->isTemplateParameter())
Invalid = Invalid || DiagnoseTemplateParameterShadow(D.getIdentifierLoc(),
PrevDecl);
@@ -577,11 +580,11 @@
return true;
}
- Previous = LookupQualifiedName(SemanticContext, Name, LookupOrdinaryName,
+ LookupQualifiedName(Previous, SemanticContext, Name, LookupOrdinaryName,
true);
} else {
SemanticContext = CurContext;
- Previous = LookupName(S, Name, LookupOrdinaryName, true);
+ LookupName(Previous, S, Name, LookupOrdinaryName, true);
}
assert(!Previous.isAmbiguous() && "Ambiguity in class template redecl?");
@@ -3581,8 +3584,9 @@
= ExternLoc.isInvalid()? TSK_ExplicitInstantiationDefinition
: TSK_ExplicitInstantiationDeclaration;
- LookupResult Previous = LookupParsedName(S, &D.getCXXScopeSpec(),
- Name, LookupOrdinaryName);
+ LookupResult Previous;
+ LookupParsedName(Previous, S, &D.getCXXScopeSpec(),
+ Name, LookupOrdinaryName);
if (!R->isFunctionType()) {
// C++ [temp.explicit]p1:
@@ -3594,14 +3598,15 @@
D.getSourceRange());
}
- VarDecl *Prev = dyn_cast_or_null<VarDecl>(Previous.getAsDecl());
+ VarDecl *Prev = dyn_cast_or_null<VarDecl>(
+ Previous.getAsSingleDecl(Context));
if (!Prev || !Prev->isStaticDataMember()) {
// We expect to see a data data member here.
Diag(D.getIdentifierLoc(), diag::err_explicit_instantiation_not_known)
<< Name;
for (LookupResult::iterator P = Previous.begin(), PEnd = Previous.end();
P != PEnd; ++P)
- Diag(P->getLocation(), diag::note_explicit_instantiation_here);
+ Diag((*P)->getLocation(), diag::note_explicit_instantiation_here);
return true;
}
@@ -3824,8 +3829,8 @@
assert(Ctx && "No declaration context?");
DeclarationName Name(&II);
- LookupResult Result = LookupQualifiedName(Ctx, Name, LookupOrdinaryName,
- false);
+ LookupResult Result;
+ LookupQualifiedName(Result, Ctx, Name, LookupOrdinaryName, false);
unsigned DiagID = 0;
Decl *Referenced = 0;
switch (Result.getKind()) {
@@ -3837,7 +3842,7 @@
break;
case LookupResult::Found:
- if (TypeDecl *Type = dyn_cast<TypeDecl>(Result.getAsDecl())) {
+ if (TypeDecl *Type = dyn_cast<TypeDecl>(Result.getFoundDecl())) {
// We found a type. Build a QualifiedNameType, since the
// typename-specifier was just sugar. FIXME: Tell
// QualifiedNameType that it has a "typename" prefix.
@@ -3845,7 +3850,7 @@
}
DiagID = diag::err_typename_nested_not_type;
- Referenced = Result.getAsDecl();
+ Referenced = Result.getFoundDecl();
break;
case LookupResult::FoundOverloaded:
Modified: cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaTemplateInstantiateDecl.cpp Fri Oct 9 16:13:30 2009
@@ -657,8 +657,9 @@
NamedDecl *PrevDecl = 0;
if (!FunctionTemplate || TemplateParams) {
- PrevDecl = SemaRef.LookupQualifiedName(Owner, Name,
- Sema::LookupOrdinaryName, true);
+ Sema::LookupResult R;
+ SemaRef.LookupQualifiedName(R, Owner, Name, Sema::LookupOrdinaryName, true);
+ PrevDecl = R.getAsSingleDecl(SemaRef.Context);
// In C++, the previous declaration we find might be a tag type
// (class or enum). In this case, the new declaration will hide the
Modified: cfe/trunk/test/SemaCXX/class-names.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaCXX/class-names.cpp?rev=83674&r1=83673&r2=83674&view=diff
==============================================================================
--- cfe/trunk/test/SemaCXX/class-names.cpp (original)
+++ cfe/trunk/test/SemaCXX/class-names.cpp Fri Oct 9 16:13:30 2009
@@ -5,7 +5,7 @@
void D(int);
-class D {}; // expected-note {{previous use is here}}
+class D {};
void foo()
{
@@ -13,7 +13,7 @@
class D d;
}
-class D;
+class D; // expected-note {{previous use is here}}
enum D; // expected-error {{use of 'D' with tag type that does not match previous declaration}}
More information about the cfe-commits
mailing list