From: Nico Weber Date: Fri, 22 Jun 2012 16:39:39 +0000 (+0000) Subject: Show fixit for unqualified calls to methods of dependent bases X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=94c4d61625122e7a7ac9a45418e88ad742fcc661;p=clang Show fixit for unqualified calls to methods of dependent bases when the calling site is a member function template. Effectively reverts r111675. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@159004 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp index 2d10a4973b..286d6d73a3 100644 --- a/lib/Sema/SemaExpr.cpp +++ b/lib/Sema/SemaExpr.cpp @@ -1477,36 +1477,40 @@ bool Sema::DiagnoseEmptyLookup(Scope *S, CXXScopeSpec &SS, LookupResult &R, if (getLangOpts().MicrosoftMode) diagnostic = diag::warn_found_via_dependent_bases_lookup; if (isInstance) { + Diag(R.getNameLoc(), diagnostic) << Name + << FixItHint::CreateInsertion(R.getNameLoc(), "this->"); UnresolvedLookupExpr *ULE = cast( CallsUndergoingInstantiation.back()->getCallee()); - CXXMethodDecl *DepMethod = cast_or_null( - CurMethod->getInstantiatedFromMemberFunction()); - if (DepMethod) { - Diag(R.getNameLoc(), diagnostic) << Name - << FixItHint::CreateInsertion(R.getNameLoc(), "this->"); - QualType DepThisType = DepMethod->getThisType(Context); - CheckCXXThisCapture(R.getNameLoc()); - CXXThisExpr *DepThis = new (Context) CXXThisExpr( - R.getNameLoc(), DepThisType, false); - TemplateArgumentListInfo TList; - if (ULE->hasExplicitTemplateArgs()) - ULE->copyTemplateArgumentsInto(TList); - - CXXScopeSpec SS; - SS.Adopt(ULE->getQualifierLoc()); - CXXDependentScopeMemberExpr *DepExpr = - CXXDependentScopeMemberExpr::Create( - Context, DepThis, DepThisType, true, SourceLocation(), - SS.getWithLocInContext(Context), - ULE->getTemplateKeywordLoc(), 0, - R.getLookupNameInfo(), - ULE->hasExplicitTemplateArgs() ? &TList : 0); - CallsUndergoingInstantiation.back()->setCallee(DepExpr); - } else { - // FIXME: we should be able to handle this case too. It is correct - // to add this-> here. This is a workaround for PR7947. - Diag(R.getNameLoc(), diagnostic) << Name; - } + + + CXXMethodDecl *DepMethod; + if (CurMethod->getTemplatedKind() == + FunctionDecl::TK_FunctionTemplateSpecialization) + DepMethod = cast(CurMethod->getPrimaryTemplate()-> + getInstantiatedFromMemberTemplate()->getTemplatedDecl()); + else + DepMethod = cast( + CurMethod->getInstantiatedFromMemberFunction()); + assert(DepMethod && "No template pattern found"); + + QualType DepThisType = DepMethod->getThisType(Context); + CheckCXXThisCapture(R.getNameLoc()); + CXXThisExpr *DepThis = new (Context) CXXThisExpr( + R.getNameLoc(), DepThisType, false); + TemplateArgumentListInfo TList; + if (ULE->hasExplicitTemplateArgs()) + ULE->copyTemplateArgumentsInto(TList); + + CXXScopeSpec SS; + SS.Adopt(ULE->getQualifierLoc()); + CXXDependentScopeMemberExpr *DepExpr = + CXXDependentScopeMemberExpr::Create( + Context, DepThis, DepThisType, true, SourceLocation(), + SS.getWithLocInContext(Context), + ULE->getTemplateKeywordLoc(), 0, + R.getLookupNameInfo(), + ULE->hasExplicitTemplateArgs() ? &TList : 0); + CallsUndergoingInstantiation.back()->setCallee(DepExpr); } else { Diag(R.getNameLoc(), diagnostic) << Name; } diff --git a/test/SemaTemplate/recovery-crash.cpp b/test/SemaTemplate/recovery-crash.cpp index 0ed3258b68..61e880bf5b 100644 --- a/test/SemaTemplate/recovery-crash.cpp +++ b/test/SemaTemplate/recovery-crash.cpp @@ -1,7 +1,6 @@ // RUN: %clang_cc1 -fsyntax-only -verify %s -// We don't expect a fix-it to be applied in this case. Clang used to crash -// trying to recover while adding 'this->' before Work(x); +// Clang used to crash trying to recover while adding 'this->' before Work(x); template struct A { static void Work(int); // expected-note{{must qualify identifier}}