diff options
author | John McCall <rjmccall@apple.com> | 2010-05-01 00:40:08 +0000 |
---|---|---|
committer | John McCall <rjmccall@apple.com> | 2010-05-01 00:40:08 +0000 |
commit | 77bb1aa78bcd26e42c0382043e65a2b03242be4d (patch) | |
tree | 89f763410c2fae9ecf90794c55bef618b65a9d42 /lib/Sema | |
parent | cdb65d8724428664af7394451863b4aa6123f52b (diff) |
It turns out that basically every caller to RequireCompleteDeclContext
already knows what context it's looking in. Just pass that context in
instead of (questionably) recalculating it.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@102818 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema')
-rw-r--r-- | lib/Sema/Sema.h | 2 | ||||
-rw-r--r-- | lib/Sema/SemaCXXScopeSpec.cpp | 27 | ||||
-rw-r--r-- | lib/Sema/SemaCodeComplete.cpp | 2 | ||||
-rw-r--r-- | lib/Sema/SemaDecl.cpp | 15 | ||||
-rw-r--r-- | lib/Sema/SemaDeclCXX.cpp | 4 | ||||
-rw-r--r-- | lib/Sema/SemaExpr.cpp | 4 | ||||
-rw-r--r-- | lib/Sema/SemaLookup.cpp | 2 | ||||
-rw-r--r-- | lib/Sema/SemaTemplate.cpp | 54 |
8 files changed, 49 insertions, 61 deletions
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h index a5b43e8a04..a79b0007f7 100644 --- a/lib/Sema/Sema.h +++ b/lib/Sema/Sema.h @@ -2365,7 +2365,7 @@ public: virtual OwningExprResult ActOnFinishFullExpr(ExprArg Expr); // Marks SS invalid if it represents an incomplete type. - bool RequireCompleteDeclContext(CXXScopeSpec &SS); + bool RequireCompleteDeclContext(CXXScopeSpec &SS, DeclContext *DC); DeclContext *computeDeclContext(QualType T); DeclContext *computeDeclContext(const CXXScopeSpec &SS, diff --git a/lib/Sema/SemaCXXScopeSpec.cpp b/lib/Sema/SemaCXXScopeSpec.cpp index 10adc6762f..c0ec9e997d 100644 --- a/lib/Sema/SemaCXXScopeSpec.cpp +++ b/lib/Sema/SemaCXXScopeSpec.cpp @@ -186,21 +186,10 @@ CXXRecordDecl *Sema::getCurrentInstantiationOf(NestedNameSpecifier *NNS) { /// that is currently being defined. Or, if we have a type that names /// a class template specialization that is not a complete type, we /// will attempt to instantiate that class template. -bool Sema::RequireCompleteDeclContext(CXXScopeSpec &SS) { - if (!SS.isSet() || SS.isInvalid()) - return false; +bool Sema::RequireCompleteDeclContext(CXXScopeSpec &SS, + DeclContext *DC) { + assert(DC != 0 && "given null context"); - DeclContext *DC = computeDeclContext(SS, true); - if (!DC) { - // It's dependent. - assert(isDependentScopeSpecifier(SS) && - "No context for non-dependent scope specifier?"); - Diag(SS.getRange().getBegin(), diag::err_dependent_nested_name_spec) - << SS.getRange(); - SS.setScopeRep(0); - return true; - } - if (TagDecl *Tag = dyn_cast<TagDecl>(DC)) { // If this is a dependent type, then we consider it complete. if (Tag->isDependentContext()) @@ -216,7 +205,7 @@ bool Sema::RequireCompleteDeclContext(CXXScopeSpec &SS) { if (RequireCompleteType(SS.getRange().getBegin(), Context.getTypeDeclType(Tag), PDiag(diag::err_incomplete_nested_name_spec) - << SS.getRange())) { + << SS.getRange())) { SS.setScopeRep(0); // Mark the ScopeSpec invalid. return true; } @@ -322,7 +311,8 @@ bool Sema::isNonTypeNestedNameSpecifier(Scope *S, CXXScopeSpec &SS, // nested-name-specifier. // The declaration context must be complete. - if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(SS)) + if (!LookupCtx->isDependentContext() && + RequireCompleteDeclContext(SS, LookupCtx)) return false; LookupQualifiedName(Found, LookupCtx); @@ -392,7 +382,8 @@ Sema::CXXScopeTy *Sema::BuildCXXNestedNameSpecifier(Scope *S, // nested-name-specifier. // The declaration context must be complete. - if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(SS)) + if (!LookupCtx->isDependentContext() && + RequireCompleteDeclContext(SS, LookupCtx)) return 0; LookupQualifiedName(Found, LookupCtx); @@ -656,7 +647,7 @@ bool Sema::ActOnCXXEnterDeclaratorScope(Scope *S, CXXScopeSpec &SS) { // Before we enter a declarator's context, we need to make sure that // it is a complete declaration context. - if (!DC->isDependentContext() && RequireCompleteDeclContext(SS)) + if (!DC->isDependentContext() && RequireCompleteDeclContext(SS, DC)) return true; EnterDeclaratorContext(S, DC); diff --git a/lib/Sema/SemaCodeComplete.cpp b/lib/Sema/SemaCodeComplete.cpp index 35bb6977ef..c075d16170 100644 --- a/lib/Sema/SemaCodeComplete.cpp +++ b/lib/Sema/SemaCodeComplete.cpp @@ -2286,7 +2286,7 @@ void Sema::CodeCompleteQualifiedId(Scope *S, CXXScopeSpec &SS, // Try to instantiate any non-dependent declaration contexts before // we look in them. - if (!isDependentScopeSpecifier(SS) && RequireCompleteDeclContext(SS)) + if (!isDependentScopeSpecifier(SS) && RequireCompleteDeclContext(SS, Ctx)) return; ResultBuilder Results(*this); diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp index 7a70c32877..3e4c923285 100644 --- a/lib/Sema/SemaDecl.cpp +++ b/lib/Sema/SemaDecl.cpp @@ -97,7 +97,8 @@ Sema::TypeTy *Sema::getTypeName(IdentifierInfo &II, SourceLocation NameLoc, return 0; } - if (!LookupCtx->isDependentContext() && RequireCompleteDeclContext(*SS)) + if (!LookupCtx->isDependentContext() && + RequireCompleteDeclContext(*SS, LookupCtx)) return 0; } @@ -2030,7 +2031,7 @@ Sema::HandleDeclarator(Scope *S, Declarator &D, bool IsDependentContext = DC->isDependentContext(); if (!IsDependentContext && - RequireCompleteDeclContext(D.getCXXScopeSpec())) + RequireCompleteDeclContext(D.getCXXScopeSpec(), DC)) return DeclPtrTy(); if (isa<CXXRecordDecl>(DC) && !cast<CXXRecordDecl>(DC)->hasDefinition()) { @@ -4940,12 +4941,18 @@ Sema::DeclPtrTy Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK, IsDependent = true; return DeclPtrTy(); } + } else { + DC = computeDeclContext(SS, true); + if (!DC) { + Diag(SS.getRange().getBegin(), diag::err_dependent_nested_name_spec) + << SS.getRange(); + return DeclPtrTy(); + } } - if (RequireCompleteDeclContext(SS)) + if (RequireCompleteDeclContext(SS, DC)) return DeclPtrTy::make((Decl *)0); - DC = computeDeclContext(SS, true); SearchDC = DC; // Look-up name inside 'foo::'. LookupQualifiedName(Previous, DC); diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 854f204ab0..c73c6caf29 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -3724,7 +3724,7 @@ NamedDecl *Sema::BuildUsingDeclaration(Scope *S, AccessSpecifier AS, if (!LookupContext) return D; UsingDecl *UD = cast<UsingDecl>(D); - if (RequireCompleteDeclContext(SS)) { + if (RequireCompleteDeclContext(SS, LookupContext)) { UD->setInvalidDecl(); return UD; } @@ -5251,11 +5251,11 @@ Sema::ActOnFriendFunctionDecl(Scope *S, LookupResult Previous(*this, Name, D.getIdentifierLoc(), LookupOrdinaryName, ForRedeclaration); if (!ScopeQual.isInvalid() && ScopeQual.isSet()) { - // FIXME: RequireCompleteDeclContext DC = computeDeclContext(ScopeQual); // FIXME: handle dependent contexts if (!DC) return DeclPtrTy(); + if (RequireCompleteDeclContext(ScopeQual, DC)) return DeclPtrTy(); LookupQualifiedName(Previous, DC); diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp index d8d525e992..a1b66cd946 100644 --- a/lib/Sema/SemaExpr.cpp +++ b/lib/Sema/SemaExpr.cpp @@ -1238,7 +1238,7 @@ Sema::BuildQualifiedDeclarationNameExpr(CXXScopeSpec &SS, if (!(DC = computeDeclContext(SS, false)) || DC->isDependentContext()) return BuildDependentDeclRefExpr(SS, Name, NameLoc, 0); - if (RequireCompleteDeclContext(SS)) + if (RequireCompleteDeclContext(SS, DC)) return ExprError(); LookupResult R(*this, Name, NameLoc, LookupOrdinaryName); @@ -2582,7 +2582,7 @@ LookupMemberExprInRecord(Sema &SemaRef, LookupResult &R, // nested-name-specifier. DC = SemaRef.computeDeclContext(SS, false); - if (SemaRef.RequireCompleteDeclContext(SS)) { + if (SemaRef.RequireCompleteDeclContext(SS, DC)) { SemaRef.Diag(SS.getRange().getEnd(), diag::err_typecheck_incomplete_tag) << SS.getRange() << DC; return true; diff --git a/lib/Sema/SemaLookup.cpp b/lib/Sema/SemaLookup.cpp index bdbbc119c6..337a4a3ce3 100644 --- a/lib/Sema/SemaLookup.cpp +++ b/lib/Sema/SemaLookup.cpp @@ -1261,7 +1261,7 @@ bool Sema::LookupParsedName(LookupResult &R, Scope *S, CXXScopeSpec *SS, if (DeclContext *DC = computeDeclContext(*SS, EnteringContext)) { // We have resolved the scope specifier to a particular declaration // contex, and will perform name lookup in that context. - if (!DC->isDependentContext() && RequireCompleteDeclContext(*SS)) + if (!DC->isDependentContext() && RequireCompleteDeclContext(*SS, DC)) return false; R.setContextRange(SS->getRange()); diff --git a/lib/Sema/SemaTemplate.cpp b/lib/Sema/SemaTemplate.cpp index 56410a2cfa..694b21c839 100644 --- a/lib/Sema/SemaTemplate.cpp +++ b/lib/Sema/SemaTemplate.cpp @@ -210,7 +210,7 @@ void Sema::LookupTemplateName(LookupResult &Found, isDependent = isDependentScopeSpecifier(SS); // The declaration context must be complete. - if (LookupCtx && RequireCompleteDeclContext(SS)) + if (LookupCtx && RequireCompleteDeclContext(SS, LookupCtx)) return; } @@ -753,15 +753,15 @@ Sema::CheckClassTemplate(Scope *S, unsigned TagSpec, TagUseKind TUK, LookupResult Previous(*this, Name, NameLoc, LookupOrdinaryName, ForRedeclaration); if (SS.isNotEmpty() && !SS.isInvalid()) { - if (RequireCompleteDeclContext(SS)) - return true; - SemanticContext = computeDeclContext(SS, true); if (!SemanticContext) { // FIXME: Produce a reasonable diagnostic here return true; } + if (RequireCompleteDeclContext(SS, SemanticContext)) + return true; + LookupQualifiedName(Previous, SemanticContext); } else { SemanticContext = CurContext; @@ -1633,7 +1633,7 @@ Sema::BuildQualifiedTemplateIdExpr(CXXScopeSpec &SS, DeclContext *DC; if (!(DC = computeDeclContext(SS, false)) || DC->isDependentContext() || - RequireCompleteDeclContext(SS)) + RequireCompleteDeclContext(SS, DC)) return BuildDependentDeclRefExpr(SS, Name, NameLoc, &TemplateArgs); LookupResult R(*this, Name, NameLoc, LookupOrdinaryName); @@ -5260,36 +5260,26 @@ QualType Sema::CheckTypenameType(ElaboratedTypeKeyword Keyword, NestedNameSpecifier *NNS, const IdentifierInfo &II, SourceRange Range) { - CXXRecordDecl *CurrentInstantiation = 0; - if (NNS->isDependent()) { - CurrentInstantiation = getCurrentInstantiationOf(NNS); - - // If the nested-name-specifier does not refer to the current - // instantiation, then build a typename type. - if (!CurrentInstantiation) - return Context.getDependentNameType(Keyword, NNS, &II); - - // The nested-name-specifier refers to the current instantiation, so the - // "typename" keyword itself is superfluous. In C++03, the program is - // actually ill-formed. However, DR 382 (in C++0x CD1) allows such - // extraneous "typename" keywords, and we retroactively apply this DR to - // C++03 code. - } + CXXScopeSpec SS; + SS.setScopeRep(NNS); + SS.setRange(Range); - DeclContext *Ctx = 0; + DeclContext *Ctx = computeDeclContext(SS); + if (!Ctx) { + // If the nested-name-specifier is dependent and couldn't be + // resolved to a type, build a typename type. + assert(NNS->isDependent()); + return Context.getDependentNameType(Keyword, NNS, &II); + } - if (CurrentInstantiation) - Ctx = CurrentInstantiation; - else { - CXXScopeSpec SS; - SS.setScopeRep(NNS); - SS.setRange(Range); - if (RequireCompleteDeclContext(SS)) - return QualType(); + // If the nested-name-specifier refers to the current instantiation, + // the "typename" keyword itself is superfluous. In C++03, the + // program is actually ill-formed. However, DR 382 (in C++0x CD1) + // allows such extraneous "typename" keywords, and we retroactively + // apply this DR to C++03 code. In any case we continue. - Ctx = computeDeclContext(SS); - } - assert(Ctx && "No declaration context?"); + if (RequireCompleteDeclContext(SS, Ctx)) + return QualType(); DeclarationName Name(&II); LookupResult Result(*this, Name, Range.getEnd(), LookupOrdinaryName); |