From: Douglas Gregor Date: Wed, 23 Sep 2009 23:04:10 +0000 (+0000) Subject: Improve diagnostic location information when checking the initialization of a reference X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=739d8283149d999f598a7514c6ec2b42598f51d3;p=clang Improve diagnostic location information when checking the initialization of a reference git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@82666 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h index 771af4bf0c..542acb6058 100644 --- a/lib/Sema/Sema.h +++ b/lib/Sema/Sema.h @@ -3571,6 +3571,7 @@ public: bool& DerivedToBase); bool CheckReferenceInit(Expr *&simpleInit_or_initList, QualType declType, + SourceLocation DeclLoc, bool SuppressUserConversions, bool AllowExplicit, bool ForceRValue, diff --git a/lib/Sema/SemaCXXCast.cpp b/lib/Sema/SemaCXXCast.cpp index f0ae9a1330..d1a8b6dedf 100644 --- a/lib/Sema/SemaCXXCast.cpp +++ b/lib/Sema/SemaCXXCast.cpp @@ -787,6 +787,7 @@ TryStaticImplicitCast(Sema &Self, Expr *SrcExpr, QualType DestType, // get error messages. ImplicitConversionSequence ICS; bool failed = Self.CheckReferenceInit(SrcExpr, DestType, + OpRange.getBegin(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false, diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 3e83202575..c2adc4fcc2 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -3363,6 +3363,7 @@ Sema::CompareReferenceRelationship(QualType T1, QualType T2, /// When @p ForceRValue, we unconditionally treat the initializer as an rvalue. bool Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, + SourceLocation DeclLoc, bool SuppressUserConversions, bool AllowExplicit, bool ForceRValue, ImplicitConversionSequence *ICS) { @@ -3381,7 +3382,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, // Since we're performing this reference-initialization for // real, update the initializer with the resulting function. if (!ICS) { - if (DiagnoseUseOfDecl(Fn, Init->getSourceRange().getBegin())) + if (DiagnoseUseOfDecl(Fn, DeclLoc)) return true; FixOverloadedFunctionReference(Init, Fn); @@ -3416,7 +3417,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, // A&& r = b; if (isRValRef && InitLvalue == Expr::LV_Valid) { if (!ICS) - Diag(Init->getSourceRange().getBegin(), diag::err_lvalue_to_rvalue_ref) + Diag(DeclLoc, diag::err_lvalue_to_rvalue_ref) << Init->getSourceRange(); return true; } @@ -3502,7 +3503,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, } OverloadCandidateSet::iterator Best; - switch (BestViableFunction(CandidateSet, Init->getLocStart(), Best)) { + switch (BestViableFunction(CandidateSet, DeclLoc, Best)) { case OR_Success: // This is a direct binding. BindsDirectly = true; @@ -3528,7 +3529,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, return false; } else { OwningExprResult InitConversion = - BuildCXXCastArgument(Init->getLocStart(), QualType(), + BuildCXXCastArgument(DeclLoc, QualType(), CastExpr::CK_UserDefinedConversion, cast(Best->Function), Owned(Init)); @@ -3565,8 +3566,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, // ambiguity (or inaccessibility) unless the reference binding // actually happens. if (DerivedToBase) - return CheckDerivedToBaseConversion(T2, T1, - Init->getSourceRange().getBegin(), + return CheckDerivedToBaseConversion(T2, T1, DeclLoc, Init->getSourceRange()); else return false; @@ -3577,8 +3577,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, // rvalue reference and the initializer expression shall be an rvalue. if (!isRValRef && T1.getCVRQualifiers() != QualType::Const) { if (!ICS) - Diag(Init->getSourceRange().getBegin(), - diag::err_not_reference_to_const_init) + Diag(DeclLoc, diag::err_not_reference_to_const_init) << T1 << (InitLvalue != Expr::LV_Valid? "temporary" : "value") << T2 << Init->getSourceRange(); return true; @@ -3642,8 +3641,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, // added qualification. But that wasn't the case, so the reference // initialization fails. if (!ICS) - Diag(Init->getSourceRange().getBegin(), - diag::err_reference_init_drops_quals) + Diag(DeclLoc, diag::err_reference_init_drops_quals) << T1 << (InitLvalue != Expr::LV_Valid? "temporary" : "value") << T2 << Init->getSourceRange(); return true; @@ -3657,8 +3655,7 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, if (SuppressUserConversions && RefRelationship == Ref_Incompatible && (T1->isRecordType() || T2->isRecordType())) { if (!ICS) - Diag(Init->getSourceRange().getBegin(), - diag::err_typecheck_convert_incompatible) + Diag(DeclLoc, diag::err_typecheck_convert_incompatible) << DeclType << Init->getType() << "initializing" << Init->getSourceRange(); return true; } @@ -3709,8 +3706,8 @@ Sema::CheckReferenceInit(Expr *&Init, QualType DeclType, } } else - Diag(Init->getSourceRange().getBegin(), diag::err_lvalue_to_rvalue_ref) - << Init->getSourceRange(); + Diag(DeclLoc, diag::err_lvalue_to_rvalue_ref) + << Init->getSourceRange(); } return badConversion; } diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp index f500e132de..ff6ae50533 100644 --- a/lib/Sema/SemaExprCXX.cpp +++ b/lib/Sema/SemaExprCXX.cpp @@ -1356,6 +1356,7 @@ static bool TryClassUnification(Sema &Self, Expr *From, Expr *To, // conversion the reference must bind directly to E1. if (!Self.CheckReferenceInit(From, Self.Context.getLValueReferenceType(To->getType()), + To->getLocStart(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false, @@ -1477,6 +1478,7 @@ static bool ConvertForConditional(Sema &Self, Expr *&E, // redoing all the work. return Self.CheckReferenceInit(E, Self.Context.getLValueReferenceType( TargetType(ICS)), + /*FIXME:*/E->getLocStart(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false); @@ -1487,6 +1489,7 @@ static bool ConvertForConditional(Sema &Self, Expr *&E, "TryClassUnification should never generate indirect ref bindings"); return Self.CheckReferenceInit(E, Self.Context.getLValueReferenceType( TargetType(ICS)), + /*FIXME:*/E->getLocStart(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false); diff --git a/lib/Sema/SemaInit.cpp b/lib/Sema/SemaInit.cpp index c430751c2e..27f0896807 100644 --- a/lib/Sema/SemaInit.cpp +++ b/lib/Sema/SemaInit.cpp @@ -144,7 +144,7 @@ bool Sema::CheckInitializerTypes(Expr *&Init, QualType &DeclType, // (8.3.2), shall be initialized by an object, or function, of // type T or by an object that can be converted into a T. if (DeclType->isReferenceType()) - return CheckReferenceInit(Init, DeclType, + return CheckReferenceInit(Init, DeclType, InitLoc, /*SuppressUserConversions=*/false, /*AllowExplicit=*/DirectInit, /*ForceRValue=*/false); @@ -801,6 +801,7 @@ void InitListChecker::CheckReferenceType(InitListExpr *IList, QualType DeclType, Expr *savExpr = expr; // Might be promoted by CheckSingleInitializer. if (SemaRef.CheckReferenceInit(expr, DeclType, + /*FIXME:*/expr->getLocStart(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false)) diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp index 12eb58733b..4232d54f4b 100644 --- a/lib/Sema/SemaOverload.cpp +++ b/lib/Sema/SemaOverload.cpp @@ -1963,6 +1963,7 @@ Sema::TryCopyInitialization(Expr *From, QualType ToType, if (ToType->isReferenceType()) { ImplicitConversionSequence ICS; CheckReferenceInit(From, ToType, + /*FIXME:*/From->getLocStart(), SuppressUserConversions, /*AllowExplicit=*/false, ForceRValue, @@ -2000,6 +2001,7 @@ bool Sema::PerformCopyInitialization(Expr *&From, QualType ToType, if (ToType->isReferenceType()) return CheckReferenceInit(From, ToType, + /*FIXME:*/From->getLocStart(), /*SuppressUserConversions=*/false, /*AllowExplicit=*/false, /*ForceRValue=*/false);