From 429bb276991ff2dbc7c5b438828b9b7737cb15eb Mon Sep 17 00:00:00 2001 From: John Wiegley Date: Fri, 8 Apr 2011 18:41:53 +0000 Subject: [PATCH] Use ExprResult& instead of Expr *& in Sema This patch authored by Eric Niebler. Many methods on the Sema class (e.g. ConvertPropertyForRValue) take Expr pointers as in/out parameters (Expr *&). This is especially true for the routines that apply implicit conversions to nodes in-place. This design is workable only as long as those conversions cannot fail. If they are allowed to fail, they need a way to report their failures. The typical way of doing this in clang is to use an ExprResult, which has an extra bit to signal a valid/invalid state. Returning ExprResult is de riguour elsewhere in the Sema interface. We suggest changing the Expr *& parameters in the Sema interface to ExprResult &. This increases interface consistency and maintainability. This interface change is important for work supporting MS-style C++ properties. For reasons explained here , seemingly trivial operations like rvalue/lvalue conversions that formerly could not fail now can. (The reason is that given the semantics of the feature, getter/setter method lookup cannot happen until the point of use, at which point it may be found that the method does not exist, or it may have the wrong type, or overload resolution may fail, or it may be inaccessible.) git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@129143 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/Sema/Initialization.h | 2 + include/clang/Sema/Sema.h | 164 +-- lib/Sema/Sema.cpp | 20 +- lib/Sema/SemaCXXCast.cpp | 226 +++-- lib/Sema/SemaChecking.cpp | 38 +- lib/Sema/SemaCodeComplete.cpp | 8 +- lib/Sema/SemaDecl.cpp | 6 +- lib/Sema/SemaDeclCXX.cpp | 24 +- lib/Sema/SemaExpr.cpp | 1454 +++++++++++++++------------ lib/Sema/SemaExprCXX.cpp | 515 +++++----- lib/Sema/SemaExprObjC.cpp | 65 +- lib/Sema/SemaInit.cpp | 157 +-- lib/Sema/SemaOverload.cpp | 338 ++++--- lib/Sema/SemaStmt.cpp | 56 +- lib/Sema/SemaTemplate.cpp | 124 +-- lib/Sema/SemaType.cpp | 9 +- lib/Sema/TreeTransform.h | 56 +- 17 files changed, 1856 insertions(+), 1406 deletions(-) diff --git a/include/clang/Sema/Initialization.h b/include/clang/Sema/Initialization.h index 7ccd27201c..a7caf00ce4 100644 --- a/include/clang/Sema/Initialization.h +++ b/include/clang/Sema/Initialization.h @@ -597,6 +597,8 @@ public: FK_ReferenceInitFailed, /// \brief Implicit conversion failed. FK_ConversionFailed, + /// \brief Implicit conversion failed. + FK_ConversionFromPropertyFailed, /// \brief Too many initializers for scalar FK_TooManyInitsForScalar, /// \brief Reference initialization from an initializer list diff --git a/include/clang/Sema/Sema.h b/include/clang/Sema/Sema.h index 356ffed694..ccf99671a5 100644 --- a/include/clang/Sema/Sema.h +++ b/include/clang/Sema/Sema.h @@ -1161,13 +1161,13 @@ public: ExprResult PerformCopyInitialization(const InitializedEntity &Entity, SourceLocation EqualLoc, ExprResult Init); - bool PerformObjectArgumentInitialization(Expr *&From, - NestedNameSpecifier *Qualifier, - NamedDecl *FoundDecl, - CXXMethodDecl *Method); + ExprResult PerformObjectArgumentInitialization(Expr *From, + NestedNameSpecifier *Qualifier, + NamedDecl *FoundDecl, + CXXMethodDecl *Method); - bool PerformContextuallyConvertToBool(Expr *&From); - bool PerformContextuallyConvertToObjCId(Expr *&From); + ExprResult PerformContextuallyConvertToBool(Expr *From); + ExprResult PerformContextuallyConvertToObjCId(Expr *From); ExprResult ConvertToIntegralOrEnumerationType(SourceLocation Loc, Expr *FromE, @@ -1179,10 +1179,10 @@ public: const PartialDiagnostic &AmbigNote, const PartialDiagnostic &ConvDiag); - bool PerformObjectMemberConversion(Expr *&From, - NestedNameSpecifier *Qualifier, - NamedDecl *FoundDecl, - NamedDecl *Member); + ExprResult PerformObjectMemberConversion(Expr *From, + NestedNameSpecifier *Qualifier, + NamedDecl *FoundDecl, + NamedDecl *Member); // Members have to be NamespaceDecl* or TranslationUnitDecl*. // TODO: make this is a typesafe union. @@ -2049,7 +2049,7 @@ public: const TemplateArgumentListInfo *TemplateArgs, bool SuppressQualifierCheck = false); - ExprResult LookupMemberExpr(LookupResult &R, Expr *&Base, + ExprResult LookupMemberExpr(LookupResult &R, ExprResult &Base, bool &IsArrow, SourceLocation OpLoc, CXXScopeSpec &SS, Decl *ObjCImpDecl, @@ -2474,7 +2474,7 @@ public: //// ActOnCXXThrow - Parse throw expressions. ExprResult ActOnCXXThrow(SourceLocation OpLoc, Expr *expr); - bool CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E); + ExprResult CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *E); /// ActOnCXXTypeConstructExpr - Parse construction of a specified type. /// Can be interpreted either as function-style casting ("int(x)") @@ -3387,10 +3387,10 @@ public: TypeSourceInfo *Arg); bool CheckTemplateArgumentPointerToMember(Expr *Arg, TemplateArgument &Converted); - bool CheckTemplateArgument(NonTypeTemplateParmDecl *Param, - QualType InstantiatedParamType, Expr *&Arg, - TemplateArgument &Converted, - CheckTemplateArgumentKind CTAK = CTAK_Specified); + ExprResult CheckTemplateArgument(NonTypeTemplateParmDecl *Param, + QualType InstantiatedParamType, Expr *Arg, + TemplateArgument &Converted, + CheckTemplateArgumentKind CTAK = CTAK_Specified); bool CheckTemplateArgument(TemplateTemplateParmDecl *Param, const TemplateArgumentLoc &Arg); @@ -4745,9 +4745,9 @@ public: /// ImpCastExprToType - If Expr is not of type 'Type', insert an implicit /// cast. If there is already an implicit cast, merge into the existing one. /// If isLvalue, the result of the cast is an lvalue. - void ImpCastExprToType(Expr *&Expr, QualType Type, CastKind CK, - ExprValueKind VK = VK_RValue, - const CXXCastPath *BasePath = 0); + ExprResult ImpCastExprToType(Expr *E, QualType Type, CastKind CK, + ExprValueKind VK = VK_RValue, + const CXXCastPath *BasePath = 0); /// ScalarTypeToBooleanCastKind - Returns the cast kind corresponding /// to the conversion from scalar type ScalarTy to the Boolean type. @@ -4756,31 +4756,31 @@ public: /// IgnoredValueConversions - Given that an expression's result is /// syntactically ignored, perform any conversions that are /// required. - void IgnoredValueConversions(Expr *&expr); + ExprResult IgnoredValueConversions(Expr *E); // UsualUnaryConversions - promotes integers (C99 6.3.1.1p2) and converts // functions and arrays to their respective pointers (C99 6.3.2.1). - Expr *UsualUnaryConversions(Expr *&expr); + ExprResult UsualUnaryConversions(Expr *E); // DefaultFunctionArrayConversion - converts functions and arrays // to their respective pointers (C99 6.3.2.1). - void DefaultFunctionArrayConversion(Expr *&expr); + ExprResult DefaultFunctionArrayConversion(Expr *E); // DefaultFunctionArrayLvalueConversion - converts functions and // arrays to their respective pointers and performs the // lvalue-to-rvalue conversion. - void DefaultFunctionArrayLvalueConversion(Expr *&expr); + ExprResult DefaultFunctionArrayLvalueConversion(Expr *E); // DefaultLvalueConversion - performs lvalue-to-rvalue conversion on // the operand. This is DefaultFunctionArrayLvalueConversion, // except that it assumes the operand isn't of function or array // type. - void DefaultLvalueConversion(Expr *&expr); + ExprResult DefaultLvalueConversion(Expr *E); // DefaultArgumentPromotion (C99 6.5.2.2p6). Used for function calls that // do not have a prototype. Integer promotions are performed on each // argument, and arguments that have type float are promoted to double. - void DefaultArgumentPromotion(Expr *&Expr); + ExprResult DefaultArgumentPromotion(Expr *E); // Used for emitting the right warning by DefaultVariadicArgumentPromotion enum VariadicCallType { @@ -4803,15 +4803,15 @@ public: // DefaultVariadicArgumentPromotion - Like DefaultArgumentPromotion, but // will warn if the resulting type is not a POD type. - bool DefaultVariadicArgumentPromotion(Expr *&Expr, VariadicCallType CT, - FunctionDecl *FDecl); + ExprResult DefaultVariadicArgumentPromotion(Expr *E, VariadicCallType CT, + FunctionDecl *FDecl); // UsualArithmeticConversions - performs the UsualUnaryConversions on it's // operands and then handles various conversions that are common to binary // operators (C99 6.3.1.8). If both operands aren't arithmetic, this // routine returns the first non-arithmetic type found. The client is // responsible for emitting appropriate error diagnostics. - QualType UsualArithmeticConversions(Expr *&lExpr, Expr *&rExpr, + QualType UsualArithmeticConversions(ExprResult &lExpr, ExprResult &rExpr, bool isCompAssign = false); /// AssignConvertType - All of the 'assignment' semantic checks return this @@ -4899,94 +4899,102 @@ public: /// Check assignment constraints and prepare for a conversion of the /// RHS to the LHS type. - AssignConvertType CheckAssignmentConstraints(QualType lhs, Expr *&rhs, + AssignConvertType CheckAssignmentConstraints(QualType lhs, ExprResult &rhs, CastKind &Kind); // CheckSingleAssignmentConstraints - Currently used by // CheckAssignmentOperands, and ActOnReturnStmt. Prior to type checking, // this routine performs the default function/array converions. AssignConvertType CheckSingleAssignmentConstraints(QualType lhs, - Expr *&rExpr); + ExprResult &rExprRes); // \brief If the lhs type is a transparent union, check whether we // can initialize the transparent union with the given expression. AssignConvertType CheckTransparentUnionArgumentConstraints(QualType lhs, - Expr *&rExpr); + ExprResult &rExpr); bool IsStringLiteralToNonConstPointerConversion(Expr *From, QualType ToType); bool CheckExceptionSpecCompatibility(Expr *From, QualType ToType); - bool PerformImplicitConversion(Expr *&From, QualType ToType, - AssignmentAction Action, - bool AllowExplicit = false); - bool PerformImplicitConversion(Expr *&From, QualType ToType, - AssignmentAction Action, - bool AllowExplicit, - ImplicitConversionSequence& ICS); - bool PerformImplicitConversion(Expr *&From, QualType ToType, - const ImplicitConversionSequence& ICS, - AssignmentAction Action, - bool CStyle = false); - bool PerformImplicitConversion(Expr *&From, QualType ToType, - const StandardConversionSequence& SCS, - AssignmentAction Action, - bool CStyle); + ExprResult PerformImplicitConversion(Expr *From, QualType ToType, + AssignmentAction Action, + bool AllowExplicit = false); + ExprResult PerformImplicitConversion(Expr *From, QualType ToType, + AssignmentAction Action, + bool AllowExplicit, + ImplicitConversionSequence& ICS); + ExprResult PerformImplicitConversion(Expr *From, QualType ToType, + const ImplicitConversionSequence& ICS, + AssignmentAction Action, + bool CStyle = false); + ExprResult PerformImplicitConversion(Expr *From, QualType ToType, + const StandardConversionSequence& SCS, + AssignmentAction Action, + bool CStyle); /// the following "Check" methods will return a valid/converted QualType /// or a null QualType (indicating an error diagnostic was issued). /// type checking binary operators (subroutines of CreateBuiltinBinOp). - QualType InvalidOperands(SourceLocation l, Expr *&lex, Expr *&rex); + QualType InvalidOperands(SourceLocation l, ExprResult &lex, ExprResult &rex); QualType CheckPointerToMemberOperands( // C++ 5.5 - Expr *&lex, Expr *&rex, ExprValueKind &VK, + ExprResult &lex, ExprResult &rex, ExprValueKind &VK, SourceLocation OpLoc, bool isIndirect); QualType CheckMultiplyDivideOperands( // C99 6.5.5 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, bool isCompAssign, + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, bool isCompAssign, bool isDivide); QualType CheckRemainderOperands( // C99 6.5.5 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, bool isCompAssign = false); + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, bool isCompAssign = false); QualType CheckAdditionOperands( // C99 6.5.6 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, QualType* CompLHSTy = 0); + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, QualType* CompLHSTy = 0); QualType CheckSubtractionOperands( // C99 6.5.6 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, QualType* CompLHSTy = 0); + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, QualType* CompLHSTy = 0); QualType CheckShiftOperands( // C99 6.5.7 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, unsigned Opc, + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, unsigned Opc, bool isCompAssign = false); QualType CheckCompareOperands( // C99 6.5.8/9 - Expr *&lex, Expr *&rex, SourceLocation OpLoc, unsigned Opc, + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, unsigned Opc, bool isRelational); QualType CheckBitwiseOperands( // C99 6.5.[10...12] - Expr *&lex, Expr *&rex, SourceLocation OpLoc, bool isCompAssign = false); + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, bool isCompAssign = false); QualType CheckLogicalOperands( // C99 6.5.[13,14] - Expr *&lex, Expr *&rex, SourceLocation OpLoc, unsigned Opc); + ExprResult &lex, ExprResult &rex, SourceLocation OpLoc, unsigned Opc); // CheckAssignmentOperands is used for both simple and compound assignment. // For simple assignment, pass both expressions and a null converted type. // For compound assignment, pass both expressions and the converted type. QualType CheckAssignmentOperands( // C99 6.5.16.[1,2] - Expr *lex, Expr *&rex, SourceLocation OpLoc, QualType convertedType); + Expr *lex, ExprResult &rex, SourceLocation OpLoc, QualType convertedType); - void ConvertPropertyForRValue(Expr *&E); - void ConvertPropertyForLValue(Expr *&LHS, Expr *&RHS, QualType& LHSTy); + void ConvertPropertyForLValue(ExprResult &LHS, ExprResult &RHS, QualType& LHSTy); + ExprResult ConvertPropertyForRValue(Expr *E); QualType CheckConditionalOperands( // C99 6.5.15 - Expr *&cond, Expr *&lhs, Expr *&rhs, + ExprResult &cond, ExprResult &lhs, ExprResult &rhs, ExprValueKind &VK, ExprObjectKind &OK, SourceLocation questionLoc); QualType CXXCheckConditionalOperands( // C++ 5.16 - Expr *&cond, Expr *&lhs, Expr *&rhs, + ExprResult &cond, ExprResult &lhs, ExprResult &rhs, ExprValueKind &VK, ExprObjectKind &OK, SourceLocation questionLoc); QualType FindCompositePointerType(SourceLocation Loc, Expr *&E1, Expr *&E2, bool *NonStandardCompositeType = 0); + QualType FindCompositePointerType(SourceLocation Loc, ExprResult &E1, ExprResult &E2, + bool *NonStandardCompositeType = 0) { + Expr *E1Tmp = E1.take(), *E2Tmp = E2.take(); + QualType Composite = FindCompositePointerType(Loc, E1Tmp, E2Tmp, NonStandardCompositeType); + E1 = Owned(E1Tmp); + E2 = Owned(E2Tmp); + return Composite; + } - QualType FindCompositeObjCPointerType(Expr *&LHS, Expr *&RHS, + QualType FindCompositeObjCPointerType(ExprResult &LHS, ExprResult &RHS, SourceLocation questionLoc); bool DiagnoseConditionalForNull(Expr *LHS, Expr *RHS, SourceLocation QuestionLoc); /// type checking for vector binary operators. - QualType CheckVectorOperands(SourceLocation l, Expr *&lex, Expr *&rex); - QualType CheckVectorCompareOperands(Expr *&lex, Expr *&rx, + QualType CheckVectorOperands(SourceLocation l, ExprResult &lex, ExprResult &rex); + QualType CheckVectorCompareOperands(ExprResult &lex, ExprResult &rx, SourceLocation l, bool isRel); /// type checking declaration initializers (C99 6.7.8) @@ -5024,13 +5032,13 @@ public: /// CheckCastTypes - Check type constraints for casting between types under /// C semantics, or forward to CXXCheckCStyleCast in C++. - bool CheckCastTypes(SourceRange TyRange, QualType CastTy, Expr *&CastExpr, - CastKind &Kind, ExprValueKind &VK, CXXCastPath &BasePath, - bool FunctionalStyle = false); + ExprResult CheckCastTypes(SourceRange TyRange, QualType CastTy, Expr *CastExpr, + CastKind &Kind, ExprValueKind &VK, CXXCastPath &BasePath, + bool FunctionalStyle = false); - bool checkUnknownAnyCast(SourceRange TyRange, QualType castType, - Expr *&castExpr, CastKind &castKind, - ExprValueKind &valueKind, CXXCastPath &BasePath); + ExprResult checkUnknownAnyCast(SourceRange TyRange, QualType castType, + Expr *castExpr, CastKind &castKind, + ExprValueKind &valueKind, CXXCastPath &BasePath); // CheckVectorCast - check type constraints for vectors. // Since vectors are an extension, there are no C standard reference for this. @@ -5043,15 +5051,15 @@ public: // Since vectors are an extension, there are no C standard reference for this. // We allow casting between vectors and integer datatypes of the same size, // or vectors and the element type of that vector. - // returns true if the cast is invalid - bool CheckExtVectorCast(SourceRange R, QualType VectorTy, Expr *&CastExpr, - CastKind &Kind); + // returns the cast expr + ExprResult CheckExtVectorCast(SourceRange R, QualType VectorTy, Expr *CastExpr, + CastKind &Kind); /// CXXCheckCStyleCast - Check constraints of a C-style or function-style /// cast under C++ semantics. - bool CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, - Expr *&CastExpr, CastKind &Kind, - CXXCastPath &BasePath, bool FunctionalStyle); + ExprResult CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, + Expr *CastExpr, CastKind &Kind, + CXXCastPath &BasePath, bool FunctionalStyle); /// CheckMessageArgumentTypes - Check types in an Obj-C message send. /// \param Method - May be null. @@ -5070,7 +5078,7 @@ public: /// \param Loc - A location associated with the condition, e.g. the /// 'if' keyword. /// \return true iff there were any errors - bool CheckBooleanCondition(Expr *&CondExpr, SourceLocation Loc); + ExprResult CheckBooleanCondition(Expr *CondExpr, SourceLocation Loc); ExprResult ActOnBooleanCondition(Scope *S, SourceLocation Loc, Expr *SubExpr); @@ -5084,7 +5092,7 @@ public: void DiagnoseEqualityWithExtraParens(ParenExpr *parenE); /// CheckCXXBooleanCondition - Returns true if conversion to bool is invalid. - bool CheckCXXBooleanCondition(Expr *&CondExpr); + ExprResult CheckCXXBooleanCondition(Expr *CondExpr); /// ConvertIntegerToTypeWarnOnOverflow - Convert the specified APInt to have /// the specified width and sign. If an overflow occurs, detect it and emit diff --git a/lib/Sema/Sema.cpp b/lib/Sema/Sema.cpp index 0e783018ec..a83722d824 100644 --- a/lib/Sema/Sema.cpp +++ b/lib/Sema/Sema.cpp @@ -203,36 +203,36 @@ Sema::~Sema() { /// ImpCastExprToType - If Expr is not of type 'Type', insert an implicit cast. /// If there is already an implicit cast, merge into the existing one. /// The result is of the given category. -void Sema::ImpCastExprToType(Expr *&Expr, QualType Ty, - CastKind Kind, ExprValueKind VK, - const CXXCastPath *BasePath) { - QualType ExprTy = Context.getCanonicalType(Expr->getType()); +ExprResult Sema::ImpCastExprToType(Expr *E, QualType Ty, + CastKind Kind, ExprValueKind VK, + const CXXCastPath *BasePath) { + QualType ExprTy = Context.getCanonicalType(E->getType()); QualType TypeTy = Context.getCanonicalType(Ty); if (ExprTy == TypeTy) - return; + return Owned(E); // If this is a derived-to-base cast to a through a virtual base, we // need a vtable. if (Kind == CK_DerivedToBase && BasePathInvolvesVirtualBase(*BasePath)) { - QualType T = Expr->getType(); + QualType T = E->getType(); if (const PointerType *Pointer = T->getAs()) T = Pointer->getPointeeType(); if (const RecordType *RecordTy = T->getAs()) - MarkVTableUsed(Expr->getLocStart(), + MarkVTableUsed(E->getLocStart(), cast(RecordTy->getDecl())); } - if (ImplicitCastExpr *ImpCast = dyn_cast(Expr)) { + if (ImplicitCastExpr *ImpCast = dyn_cast(E)) { if (ImpCast->getCastKind() == Kind && (!BasePath || BasePath->empty())) { ImpCast->setType(Ty); ImpCast->setValueKind(VK); - return; + return Owned(E); } } - Expr = ImplicitCastExpr::Create(Context, Ty, Kind, Expr, BasePath, VK); + return Owned(ImplicitCastExpr::Create(Context, Ty, Kind, E, BasePath, VK)); } /// ScalarTypeToBooleanCastKind - Returns the cast kind corresponding diff --git a/lib/Sema/SemaCXXCast.cpp b/lib/Sema/SemaCXXCast.cpp index e519d1db17..989be96d21 100644 --- a/lib/Sema/SemaCXXCast.cpp +++ b/lib/Sema/SemaCXXCast.cpp @@ -42,21 +42,21 @@ enum CastType { -static void CheckConstCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +static void CheckConstCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange); -static void CheckReinterpretCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +static void CheckReinterpretCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange, CastKind &Kind); -static void CheckStaticCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +static void CheckStaticCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, CastKind &Kind, CXXCastPath &BasePath); -static void CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +static void CheckDynamicCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange, @@ -100,7 +100,7 @@ static TryCastResult TryStaticDowncast(Sema &Self, CanQualType SrcType, QualType OrigDestType, unsigned &msg, CastKind &Kind, CXXCastPath &BasePath); -static TryCastResult TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryStaticMemberPointerUpcast(Sema &Self, ExprResult &SrcExpr, QualType SrcType, QualType DestType,bool CStyle, const SourceRange &OpRange, @@ -108,12 +108,12 @@ static TryCastResult TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, CastKind &Kind, CXXCastPath &BasePath); -static TryCastResult TryStaticImplicitCast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryStaticImplicitCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, CastKind &Kind); -static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryStaticCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, @@ -121,7 +121,7 @@ static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, CXXCastPath &BasePath); static TryCastResult TryConstCast(Sema &Self, Expr *SrcExpr, QualType DestType, bool CStyle, unsigned &msg); -static TryCastResult TryReinterpretCast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryReinterpretCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, @@ -148,8 +148,9 @@ Sema::ActOnCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, ExprResult Sema::BuildCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, - TypeSourceInfo *DestTInfo, Expr *Ex, + TypeSourceInfo *DestTInfo, Expr *E, SourceRange AngleBrackets, SourceRange Parens) { + ExprResult Ex = Owned(E); QualType DestType = DestTInfo->getType(); SourceRange OpRange(OpLoc, Parens.getEnd()); @@ -157,11 +158,11 @@ Sema::BuildCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, // If the type is dependent, we won't do the semantic analysis now. // FIXME: should we check this in a more fine-grained manner? - bool TypeDependent = DestType->isDependentType() || Ex->isTypeDependent(); + bool TypeDependent = DestType->isDependentType() || Ex.get()->isTypeDependent(); - if (Ex->isBoundMemberFunction(Context)) - Diag(Ex->getLocStart(), diag::err_invalid_use_of_bound_member_func) - << Ex->getSourceRange(); + if (Ex.get()->isBoundMemberFunction(Context)) + Diag(Ex.get()->getLocStart(), diag::err_invalid_use_of_bound_member_func) + << Ex.get()->getSourceRange(); ExprValueKind VK = VK_RValue; if (TypeDependent) @@ -171,42 +172,54 @@ Sema::BuildCXXNamedCast(SourceLocation OpLoc, tok::TokenKind Kind, default: llvm_unreachable("Unknown C++ cast!"); case tok::kw_const_cast: - if (!TypeDependent) + if (!TypeDependent) { CheckConstCast(*this, Ex, DestType, VK, OpRange, DestRange); + if (Ex.isInvalid()) + return ExprError(); + } return Owned(CXXConstCastExpr::Create(Context, DestType.getNonLValueExprType(Context), - VK, Ex, DestTInfo, OpLoc, + VK, Ex.take(), DestTInfo, OpLoc, Parens.getEnd())); case tok::kw_dynamic_cast: { CastKind Kind = CK_Dependent; CXXCastPath BasePath; - if (!TypeDependent) + if (!TypeDependent) { CheckDynamicCast(*this, Ex, DestType, VK, OpRange, DestRange, Kind, BasePath); + if (Ex.isInvalid()) + return ExprError(); + } return Owned(CXXDynamicCastExpr::Create(Context, DestType.getNonLValueExprType(Context), - VK, Kind, Ex, &BasePath, DestTInfo, + VK, Kind, Ex.take(), &BasePath, DestTInfo, OpLoc, Parens.getEnd())); } case tok::kw_reinterpret_cast: { CastKind Kind = CK_Dependent; - if (!TypeDependent) + if (!TypeDependent) { CheckReinterpretCast(*this, Ex, DestType, VK, OpRange, DestRange, Kind); + if (Ex.isInvalid()) + return ExprError(); + } return Owned(CXXReinterpretCastExpr::Create(Context, DestType.getNonLValueExprType(Context), - VK, Kind, Ex, 0, + VK, Kind, Ex.take(), 0, DestTInfo, OpLoc, Parens.getEnd())); } case tok::kw_static_cast: { CastKind Kind = CK_Dependent; CXXCastPath BasePath; - if (!TypeDependent) + if (!TypeDependent) { CheckStaticCast(*this, Ex, DestType, VK, OpRange, Kind, BasePath); + if (Ex.isInvalid()) + return ExprError(); + } return Owned(CXXStaticCastExpr::Create(Context, DestType.getNonLValueExprType(Context), - VK, Kind, Ex, &BasePath, + VK, Kind, Ex.take(), &BasePath, DestTInfo, OpLoc, Parens.getEnd())); } } @@ -413,11 +426,11 @@ CastsAwayConstness(Sema &Self, QualType SrcType, QualType DestType) { /// Refer to C++ 5.2.7 for details. Dynamic casts are used mostly for runtime- /// checked downcasts in class hierarchies. static void -CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +CheckDynamicCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange, CastKind &Kind, CXXCastPath &BasePath) { - QualType OrigDestType = DestType, OrigSrcType = SrcExpr->getType(); + QualType OrigDestType = DestType, OrigSrcType = SrcExpr.get()->getType(); DestType = Self.Context.getCanonicalType(DestType); // C++ 5.2.7p1: T shall be a pointer or reference to a complete class type, @@ -464,11 +477,11 @@ CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, SrcPointee = SrcPointer->getPointeeType(); } else { Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_ptr) - << OrigSrcType << SrcExpr->getSourceRange(); + << OrigSrcType << SrcExpr.get()->getSourceRange(); return; } } else if (DestReference->isLValueReferenceType()) { - if (!SrcExpr->isLValue()) { + if (!SrcExpr.get()->isLValue()) { Self.Diag(OpRange.getBegin(), diag::err_bad_cxx_cast_rvalue) << CT_Dynamic << OrigSrcType << OrigDestType << OpRange; } @@ -481,11 +494,11 @@ CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, if (SrcRecord) { if (Self.RequireCompleteType(OpRange.getBegin(), SrcPointee, Self.PDiag(diag::err_bad_dynamic_cast_incomplete) - << SrcExpr->getSourceRange())) + << SrcExpr.get()->getSourceRange())) return; } else { Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_class) - << SrcPointee.getUnqualifiedType() << SrcExpr->getSourceRange(); + << SrcPointee.getUnqualifiedType() << SrcExpr.get()->getSourceRange(); return; } @@ -532,7 +545,7 @@ CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, assert(SrcDecl && "Definition missing"); if (!cast(SrcDecl)->isPolymorphic()) { Self.Diag(OpRange.getBegin(), diag::err_bad_dynamic_cast_not_polymorphic) - << SrcPointee.getUnqualifiedType() << SrcExpr->getSourceRange(); + << SrcPointee.getUnqualifiedType() << SrcExpr.get()->getSourceRange(); } Self.MarkVTableUsed(OpRange.getBegin(), cast(SrcRecord->getDecl())); @@ -547,17 +560,20 @@ CheckDynamicCast(Sema &Self, Expr *&SrcExpr, QualType DestType, /// const char *str = "literal"; /// legacy_function(const_cast\(str)); void -CheckConstCast(Sema &Self, Expr *&SrcExpr, QualType DestType, ExprValueKind &VK, +CheckConstCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange) { VK = Expr::getValueKindForType(DestType); - if (VK == VK_RValue) - Self.DefaultFunctionArrayLvalueConversion(SrcExpr); + if (VK == VK_RValue) { + SrcExpr = Self.DefaultFunctionArrayLvalueConversion(SrcExpr.take()); + if (SrcExpr.isInvalid()) // if conversion failed, don't report another error + return; + } unsigned msg = diag::err_bad_cxx_cast_generic; - if (TryConstCast(Self, SrcExpr, DestType, /*CStyle*/false, msg) != TC_Success + if (TryConstCast(Self, SrcExpr.get(), DestType, /*CStyle*/false, msg) != TC_Success && msg != 0) Self.Diag(OpRange.getBegin(), msg) << CT_Const - << SrcExpr->getType() << DestType << OpRange; + << SrcExpr.get()->getType() << DestType << OpRange; } /// CheckReinterpretCast - Check that a reinterpret_cast\(SrcExpr) is @@ -566,27 +582,32 @@ CheckConstCast(Sema &Self, Expr *&SrcExpr, QualType DestType, ExprValueKind &VK, /// like this: /// char *bytes = reinterpret_cast\(int_ptr); void -CheckReinterpretCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +CheckReinterpretCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, const SourceRange &DestRange, CastKind &Kind) { VK = Expr::getValueKindForType(DestType); - if (VK == VK_RValue) - Self.DefaultFunctionArrayLvalueConversion(SrcExpr); + if (VK == VK_RValue) { + SrcExpr = Self.DefaultFunctionArrayLvalueConversion(SrcExpr.take()); + if (SrcExpr.isInvalid()) // if conversion failed, don't report another error + return; + } unsigned msg = diag::err_bad_cxx_cast_generic; if (TryReinterpretCast(Self, SrcExpr, DestType, /*CStyle*/false, OpRange, msg, Kind) != TC_Success && msg != 0) { - if (SrcExpr->getType() == Self.Context.OverloadTy) { + if (SrcExpr.isInvalid()) // if conversion failed, don't report another error + return; + if (SrcExpr.get()->getType() == Self.Context.OverloadTy) { //FIXME: &f; is overloaded and resolvable Self.Diag(OpRange.getBegin(), diag::err_bad_reinterpret_cast_overload) - << OverloadExpr::find(SrcExpr).Expression->getName() + << OverloadExpr::find(SrcExpr.get()).Expression->getName() << DestType << OpRange; - Self.NoteAllOverloadCandidates(SrcExpr); + Self.NoteAllOverloadCandidates(SrcExpr.get()); } else { - diagnoseBadCast(Self, msg, CT_Reinterpret, OpRange, SrcExpr, DestType); + diagnoseBadCast(Self, msg, CT_Reinterpret, OpRange, SrcExpr.get(), DestType); } } } @@ -596,23 +617,25 @@ CheckReinterpretCast(Sema &Self, Expr *&SrcExpr, QualType DestType, /// Refer to C++ 5.2.9 for details. Static casts are mostly used for making /// implicit conversions explicit and getting rid of data loss warnings. void -CheckStaticCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +CheckStaticCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, ExprValueKind &VK, const SourceRange &OpRange, CastKind &Kind, CXXCastPath &BasePath) { // This test is outside everything else because it's the only case where // a non-lvalue-reference target type does not lead to decay. // C++ 5.2.9p4: Any expression can be explicitly converted to type "cv void". if (DestType->isVoidType()) { - Self.IgnoredValueConversions(SrcExpr); - if (SrcExpr->getType() == Self.Context.OverloadTy) { + SrcExpr = Self.IgnoredValueConversions(SrcExpr.take()); + if (SrcExpr.isInvalid()) // if conversion failed, don't report another error + return; + if (SrcExpr.get()->getType() == Self.Context.OverloadTy) { ExprResult SingleFunctionExpression = - Self.ResolveAndFixSingleFunctionTemplateSpecialization(SrcExpr, + Self.ResolveAndFixSingleFunctionTemplateSpecialization(SrcExpr.get(), false, // Decay Function to ptr true, // Complain OpRange, DestType, diag::err_bad_static_cast_overload); if (SingleFunctionExpression.isUsable()) { - SrcExpr = SingleFunctionExpression.release(); + SrcExpr = SingleFunctionExpression; Kind = CK_ToVoid; } } @@ -622,30 +645,35 @@ CheckStaticCast(Sema &Self, Expr *&SrcExpr, QualType DestType, } VK = Expr::getValueKindForType(DestType); - if (VK == VK_RValue && !DestType->isRecordType()) - Self.DefaultFunctionArrayLvalueConversion(SrcExpr); + if (VK == VK_RValue && !DestType->isRecordType()) { + SrcExpr = Self.DefaultFunctionArrayLvalueConversion(SrcExpr.take()); + if (SrcExpr.isInvalid()) // if conversion failed, don't report another error + return; + } unsigned msg = diag::err_bad_cxx_cast_generic; if (TryStaticCast(Self, SrcExpr, DestType, /*CStyle*/false, OpRange, msg, Kind, BasePath) != TC_Success && msg != 0) { - if (SrcExpr->getType() == Self.Context.OverloadTy) { - OverloadExpr* oe = OverloadExpr::find(SrcExpr).Expression; + if (SrcExpr.isInvalid()) + return; + if (SrcExpr.get()->getType() == Self.Context.OverloadTy) { + OverloadExpr* oe = OverloadExpr::find(SrcExpr.get()).Expression; Self.Diag(OpRange.getBegin(), diag::err_bad_static_cast_overload) << oe->getName() << DestType << OpRange << oe->getQualifierLoc().getSourceRange(); - Self.NoteAllOverloadCandidates(SrcExpr); + Self.NoteAllOverloadCandidates(SrcExpr.get()); } else { - diagnoseBadCast(Self, msg, CT_Static, OpRange, SrcExpr, DestType); + diagnoseBadCast(Self, msg, CT_Static, OpRange, SrcExpr.get(), DestType); } } else if (Kind == CK_BitCast) - Self.CheckCastAlign(SrcExpr, DestType, OpRange); + Self.CheckCastAlign(SrcExpr.get(), DestType, OpRange); } /// TryStaticCast - Check if a static cast can be performed, and do so if /// possible. If @p CStyle, ignore access restrictions on hierarchy casting /// and casting away constness. -static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryStaticCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, CastKind &Kind, @@ -670,7 +698,7 @@ static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, // C++ 5.2.9p5, reference downcast. // See the function for details. // DR 427 specifies that this is to be applied before paragraph 2. - tcr = TryStaticReferenceDowncast(Self, SrcExpr, DestType, CStyle, OpRange, + tcr = TryStaticReferenceDowncast(Self, SrcExpr.get(), DestType, CStyle, OpRange, msg, Kind, BasePath); if (tcr != TC_NotApplicable) return tcr; @@ -678,7 +706,7 @@ static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, // C++0x [expr.static.cast]p3: // A glvalue of type "cv1 T1" can be cast to type "rvalue reference to cv2 // T2" if "cv2 T2" is reference-compatible with "cv1 T1". - tcr = TryLValueToRValueCast(Self, SrcExpr, DestType, CStyle, Kind, BasePath, + tcr = TryLValueToRValueCast(Self, SrcExpr.get(), DestType, CStyle, Kind, BasePath, msg); if (tcr != TC_NotApplicable) return tcr; @@ -687,6 +715,8 @@ static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, // [...] if the declaration "T t(e);" is well-formed, [...]. tcr = TryStaticImplicitCast(Self, SrcExpr, DestType, CStyle, OpRange, msg, Kind); + if (SrcExpr.isInvalid()) + return TC_Failed; if (tcr != TC_NotApplicable) return tcr; @@ -698,7 +728,7 @@ static TryCastResult TryStaticCast(Sema &Self, Expr *&SrcExpr, // In the CStyle case, the earlier attempt to const_cast should have taken // care of reverse qualification conversions. - QualType SrcType = Self.Context.getCanonicalType(SrcExpr->getType()); + QualType SrcType = Self.Context.getCanonicalType(SrcExpr.get()->getType()); // C++0x 5.2.9p9: A value of a scoped enumeration type can be explicitly // converted to an integral type. [...] A value of a scoped enumeration type @@ -1028,7 +1058,7 @@ TryStaticDowncast(Sema &Self, CanQualType SrcType, CanQualType DestType, /// where B is a base class of D [...]. /// TryCastResult -TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, QualType SrcType, +TryStaticMemberPointerUpcast(Sema &Self, ExprResult &SrcExpr, QualType SrcType, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, CastKind &Kind, @@ -1039,9 +1069,9 @@ TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, QualType SrcType, bool WasOverloadedFunction = false; DeclAccessPair FoundOverload; - if (SrcExpr->getType() == Self.Context.OverloadTy) { + if (SrcExpr.get()->getType() == Self.Context.OverloadTy) { if (FunctionDecl *Fn - = Self.ResolveAddressOfOverloadedFunction(SrcExpr, DestType, false, + = Self.ResolveAddressOfOverloadedFunction(SrcExpr.get(), DestType, false, FoundOverload)) { CXXMethodDecl *M = cast(Fn); SrcType = Self.Context.getMemberPointerType(Fn->getType(), @@ -1112,7 +1142,7 @@ TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, QualType SrcType, if (WasOverloadedFunction) { // Resolve the address of the overloaded function again, this time // allowing complaints if something goes wrong. - FunctionDecl *Fn = Self.ResolveAddressOfOverloadedFunction(SrcExpr, + FunctionDecl *Fn = Self.ResolveAddressOfOverloadedFunction(SrcExpr.get(), DestType, true, FoundOverload); @@ -1122,7 +1152,7 @@ TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, QualType SrcType, } SrcExpr = Self.FixOverloadedFunctionReference(SrcExpr, FoundOverload, Fn); - if (!SrcExpr) { + if (!SrcExpr.isUsable()) { msg = 0; return TC_Failed; } @@ -1139,7 +1169,7 @@ TryStaticMemberPointerUpcast(Sema &Self, Expr *&SrcExpr, QualType SrcType, /// An expression e can be explicitly converted to a type T using a /// @c static_cast if the declaration "T t(e);" is well-formed [...]. TryCastResult -TryStaticImplicitCast(Sema &Self, Expr *&SrcExpr, QualType DestType, +TryStaticImplicitCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, CastKind &Kind) { if (DestType->isRecordType()) { @@ -1153,7 +1183,8 @@ TryStaticImplicitCast(Sema &Self, Expr *&SrcExpr, QualType DestType, InitializedEntity Entity = InitializedEntity::InitializeTemporary(DestType); InitializationKind InitKind = InitializationKind::CreateCast(/*FIXME:*/OpRange, CStyle); - InitializationSequence InitSeq(Self, Entity, InitKind, &SrcExpr, 1); + Expr *SrcExprRaw = SrcExpr.get(); + InitializationSequence InitSeq(Self, Entity, InitKind, &SrcExprRaw, 1); // At this point of CheckStaticCast, if the destination is a reference, // or the expression is an overload expression this has to work. @@ -1166,7 +1197,7 @@ TryStaticImplicitCast(Sema &Self, Expr *&SrcExpr, QualType DestType, return TC_NotApplicable; ExprResult Result - = InitSeq.Perform(Self, Entity, InitKind, MultiExprArg(Self, &SrcExpr, 1)); + = InitSeq.Perform(Self, Entity, InitKind, MultiExprArg(Self, &SrcExprRaw, 1)); if (Result.isInvalid()) { msg = 0; return TC_Failed; @@ -1177,7 +1208,7 @@ TryStaticImplicitCast(Sema &Self, Expr *&SrcExpr, QualType DestType, else Kind = CK_NoOp; - SrcExpr = Result.takeAs(); + SrcExpr = move(Result); return TC_Success; } @@ -1250,9 +1281,7 @@ static TryCastResult TryConstCast(Sema &Self, Expr *SrcExpr, QualType DestType, } - - -static TryCastResult TryReinterpretCast(Sema &Self, Expr *&SrcExpr, +static TryCastResult TryReinterpretCast(Sema &Self, ExprResult &SrcExpr, QualType DestType, bool CStyle, const SourceRange &OpRange, unsigned &msg, @@ -1260,19 +1289,19 @@ static TryCastResult TryReinterpretCast(Sema &Self, Expr *&SrcExpr, bool IsLValueCast = false; DestType = Self.Context.getCanonicalType(DestType); - QualType SrcType = SrcExpr->getType(); + QualType SrcType = SrcExpr.get()->getType(); // Is the source an overloaded name? (i.e. &foo) // If so, reinterpret_cast can not help us here (13.4, p1, bullet 5) ... if (SrcType == Self.Context.OverloadTy) { // ... unless foo resolves to an lvalue unambiguously ExprResult SingleFunctionExpr = - Self.ResolveAndFixSingleFunctionTemplateSpecialization(SrcExpr, + Self.ResolveAndFixSingleFunctionTemplateSpecialization(SrcExpr.get(), Expr::getValueKindForType(DestType) == VK_RValue // Convert Fun to Ptr ); if (SingleFunctionExpr.isUsable()) { - SrcExpr = SingleFunctionExpr.release(); - SrcType = SrcExpr->getType(); + SrcExpr = move(SingleFunctionExpr); + SrcType = SrcExpr.get()->getType(); } else return TC_NotApplicable; @@ -1280,7 +1309,7 @@ static TryCastResult TryReinterpretCast(Sema &Self, Expr *&SrcExpr, if (const ReferenceType *DestTypeTmp = DestType->getAs()) { bool LValue = DestTypeTmp->isLValueReferenceType(); - if (LValue && !SrcExpr->isLValue()) { + if (LValue && !SrcExpr.get()->isLValue()) { // Cannot cast non-lvalue to lvalue reference type. See the similar // comment in const_cast. msg = diag::err_bad_cxx_cast_rvalue; @@ -1482,21 +1511,25 @@ static TryCastResult TryReinterpretCast(Sema &Self, Expr *&SrcExpr, return TC_Success; } -bool +ExprResult Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, - Expr *&CastExpr, CastKind &Kind, + Expr *CastExpr, CastKind &Kind, CXXCastPath &BasePath, bool FunctionalStyle) { - if (CastExpr->isBoundMemberFunction(Context)) - return Diag(CastExpr->getLocStart(), - diag::err_invalid_use_of_bound_member_func) + if (CastExpr->isBoundMemberFunction(Context)) { + Diag(CastExpr->getLocStart(), diag::err_invalid_use_of_bound_member_func) << CastExpr->getSourceRange(); + return ExprError(); + } // This test is outside everything else because it's the only case where // a non-lvalue-reference target type does not lead to decay. // C++ 5.2.9p4: Any expression can be explicitly converted to type "cv void". if (CastTy->isVoidType()) { - IgnoredValueConversions(CastExpr); + ExprResult CastExprRes = IgnoredValueConversions(CastExpr); + if (CastExprRes.isInvalid()) + return ExprError(); + CastExpr = CastExprRes.take(); bool ret = false; // false is 'able to convert' if (CastExpr->getType() == Context.OverloadTy) { ExprResult SingleFunctionExpr = @@ -1506,7 +1539,7 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, diag::err_bad_cstyle_cast_overload); if (SingleFunctionExpr.isUsable()) { - CastExpr = SingleFunctionExpr.release(); + CastExpr = SingleFunctionExpr.take(); Kind = CK_ToVoid; } else @@ -1514,7 +1547,7 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, } else Kind = CK_ToVoid; - return ret; + return ret ? ExprError() : Owned(CastExpr); } // Case of AltiVec vector initialization with a single literal @@ -1524,7 +1557,7 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, && (CastExpr->getType()->isIntegerType() || CastExpr->getType()->isFloatingType())) { Kind = CK_VectorSplat; - return false; + return Owned(CastExpr); } // Make sure we determine the value kind before we bail out for @@ -1534,11 +1567,15 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, // If the type is dependent, we won't do any other semantic analysis now. if (CastTy->isDependentType() || CastExpr->isTypeDependent()) { Kind = CK_Dependent; - return false; + return Owned(CastExpr); } - if (VK == VK_RValue && !CastTy->isRecordType()) - DefaultFunctionArrayLvalueConversion(CastExpr); + if (VK == VK_RValue && !CastTy->isRecordType()) { + ExprResult CastExprRes = DefaultFunctionArrayLvalueConversion(CastExpr); + if (CastExprRes.isInvalid()) + return ExprError(); + CastExpr = CastExprRes.take(); + } // C++ [expr.cast]p5: The conversions performed by // - a const_cast, @@ -1559,19 +1596,27 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, if (tcr == TC_NotApplicable) { // ... or if that is not possible, a static_cast, ignoring const, ... - tcr = TryStaticCast(*this, CastExpr, CastTy, /*CStyle*/true, R, msg, Kind, + ExprResult CastExprRes = Owned(CastExpr); + tcr = TryStaticCast(*this, CastExprRes, CastTy, /*CStyle*/true, R, msg, Kind, BasePath); + if (CastExprRes.isInvalid()) + return ExprError(); + CastExpr = CastExprRes.take(); if (tcr == TC_NotApplicable) { // ... and finally a reinterpret_cast, ignoring const. - tcr = TryReinterpretCast(*this, CastExpr, CastTy, /*CStyle*/true, R, msg, + CastExprRes = Owned(CastExpr); + tcr = TryReinterpretCast(*this, CastExprRes, CastTy, /*CStyle*/true, R, msg, Kind); + if (CastExprRes.isInvalid()) + return ExprError(); + CastExpr = CastExprRes.take(); } } if (tcr != TC_Success && msg != 0) { if (CastExpr->getType() == Context.OverloadTy) { DeclAccessPair Found; - FunctionDecl *Fn = ResolveAddressOfOverloadedFunction(CastExpr, + FunctionDecl *Fn = ResolveAddressOfOverloadedFunction(CastExpr, CastTy, /* Complain */ true, Found); @@ -1588,6 +1633,9 @@ Sema::CXXCheckCStyleCast(SourceRange R, QualType CastTy, ExprValueKind &VK, else if (Kind == CK_BitCast) CheckCastAlign(CastExpr, CastTy, R); - return tcr != TC_Success; + if (tcr != TC_Success) + return ExprError(); + + return Owned(CastExpr); } diff --git a/lib/Sema/SemaChecking.cpp b/lib/Sema/SemaChecking.cpp index bdadf5aab8..105fb52ddb 100644 --- a/lib/Sema/SemaChecking.cpp +++ b/lib/Sema/SemaChecking.cpp @@ -492,14 +492,14 @@ Sema::SemaBuiltinAtomicOverloaded(ExprResult TheCallResult) { // deduce the types of the rest of the arguments accordingly. Walk // the remaining arguments, converting them to the deduced value type. for (unsigned i = 0; i != NumFixed; ++i) { - Expr *Arg = TheCall->getArg(i+1); + ExprResult Arg = TheCall->getArg(i+1); // If the argument is an implicit cast, then there was a promotion due to // "...", just remove it now. - if (ImplicitCastExpr *ICE = dyn_cast(Arg)) { + if (ImplicitCastExpr *ICE = dyn_cast(Arg.get())) { Arg = ICE->getSubExpr(); ICE->setSubExpr(0); - TheCall->setArg(i+1, Arg); + TheCall->setArg(i+1, Arg.get()); } // GCC does an implicit conversion to the pointer or integer ValType. This @@ -507,7 +507,8 @@ Sema::SemaBuiltinAtomicOverloaded(ExprResult TheCallResult) { CastKind Kind = CK_Invalid; ExprValueKind VK = VK_RValue; CXXCastPath BasePath; - if (CheckCastTypes(Arg->getSourceRange(), ValType, Arg, Kind, VK, BasePath)) + Arg = CheckCastTypes(Arg.get()->getSourceRange(), ValType, Arg.take(), Kind, VK, BasePath); + if (Arg.isInvalid()) return ExprError(); // Okay, we have something that *can* be converted to the right type. Check @@ -516,8 +517,8 @@ Sema::SemaBuiltinAtomicOverloaded(ExprResult TheCallResult) { // pass in 42. The 42 gets converted to char. This is even more strange // for things like 45.123 -> char, etc. // FIXME: Do this check. - ImpCastExprToType(Arg, ValType, Kind, VK, &BasePath); - TheCall->setArg(i+1, Arg); + Arg = ImpCastExprToType(Arg.take(), ValType, Kind, VK, &BasePath); + TheCall->setArg(i+1, Arg.get()); } // Switch the DeclRefExpr to refer to the new decl. @@ -526,9 +527,10 @@ Sema::SemaBuiltinAtomicOverloaded(ExprResult TheCallResult) { // Set the callee in the CallExpr. // FIXME: This leaks the original parens and implicit casts. - Expr *PromotedCall = DRE; - UsualUnaryConversions(PromotedCall); - TheCall->setCallee(PromotedCall); + ExprResult PromotedCall = UsualUnaryConversions(DRE); + if (PromotedCall.isInvalid()) + return ExprError(); + TheCall->setCallee(PromotedCall.take()); // Change the result type of the call to match the original value type. This // is arbitrary, but the codegen for these builtins ins design to handle it @@ -645,29 +647,31 @@ bool Sema::SemaBuiltinUnorderedCompare(CallExpr *TheCall) { << SourceRange(TheCall->getArg(2)->getLocStart(), (*(TheCall->arg_end()-1))->getLocEnd()); - Expr *OrigArg0 = TheCall->getArg(0); - Expr *OrigArg1 = TheCall->getArg(1); + ExprResult OrigArg0 = TheCall->getArg(0); + ExprResult OrigArg1 = TheCall->getArg(1); // Do standard promotions between the two arguments, returning their common // type. QualType Res = UsualArithmeticConversions(OrigArg0, OrigArg1, false); + if (OrigArg0.isInvalid() || OrigArg1.isInvalid()) + return true; // Make sure any conversions are pushed back into the call; this is // type safe since unordered compare builtins are declared as "_Bool // foo(...)". - TheCall->setArg(0, OrigArg0); - TheCall->setArg(1, OrigArg1); + TheCall->setArg(0, OrigArg0.get()); + TheCall->setArg(1, OrigArg1.get()); - if (OrigArg0->isTypeDependent() || OrigArg1->isTypeDependent()) + if (OrigArg0.get()->isTypeDependent() || OrigArg1.get()->isTypeDependent()) return false; // If the common type isn't a real floating type, then the arguments were // invalid for this operation. if (!Res->isRealFloatingType()) - return Diag(OrigArg0->getLocStart(), + return Diag(OrigArg0.get()->getLocStart(), diag::err_typecheck_call_invalid_ordered_compare) - << OrigArg0->getType() << OrigArg1->getType() - << SourceRange(OrigArg0->getLocStart(), OrigArg1->getLocEnd()); + << OrigArg0.get()->getType() << OrigArg1.get()->getType() + << SourceRange(OrigArg0.get()->getLocStart(), OrigArg1.get()->getLocEnd()); return false; } diff --git a/lib/Sema/SemaCodeComplete.cpp b/lib/Sema/SemaCodeComplete.cpp index df3722f2e8..72074ae820 100644 --- a/lib/Sema/SemaCodeComplete.cpp +++ b/lib/Sema/SemaCodeComplete.cpp @@ -4816,8 +4816,12 @@ void Sema::CodeCompleteObjCInstanceMessage(Scope *S, ExprTy *Receiver, // If necessary, apply function/array conversion to the receiver. // C99 6.7.5.3p[7,8]. - if (RecExpr) - DefaultFunctionArrayLvalueConversion(RecExpr); + if (RecExpr) { + ExprResult Conv = DefaultFunctionArrayLvalueConversion(RecExpr); + if (Conv.isInvalid()) // conversion failed. bail. + return; + RecExpr = Conv.take(); + } QualType ReceiverType = RecExpr? RecExpr->getType() : Super? Context.getObjCObjectPointerType( Context.getObjCInterfaceType(Super)) diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp index 8bf6c84c0b..32fd9a1204 100644 --- a/lib/Sema/SemaDecl.cpp +++ b/lib/Sema/SemaDecl.cpp @@ -7783,7 +7783,7 @@ EnumConstantDecl *Sema::CheckEnumConstant(EnumDecl *Enum, << (EnumVal.isUnsigned() || EnumVal.isNonNegative()); else if (!Context.hasSameType(Val->getType(), Context.IntTy)) { // Force the type of the expression to 'int'. - ImpCastExprToType(Val, Context.IntTy, CK_IntegralCast); + Val = ImpCastExprToType(Val, Context.IntTy, CK_IntegralCast).take(); } } @@ -7796,12 +7796,12 @@ EnumConstantDecl *Sema::CheckEnumConstant(EnumDecl *Enum, if (!isRepresentableIntegerValue(Context, EnumVal, EltTy)) { if (getLangOptions().Microsoft) { Diag(IdLoc, diag::ext_enumerator_too_large) << EltTy; - ImpCastExprToType(Val, EltTy, CK_IntegralCast); + Val = ImpCastExprToType(Val, EltTy, CK_IntegralCast).take(); } else Diag(IdLoc, diag::err_enumerator_too_large) << EltTy; } else - ImpCastExprToType(Val, EltTy, CK_IntegralCast); + Val = ImpCastExprToType(Val, EltTy, CK_IntegralCast).take(); } else { // C++0x [dcl.enum]p5: diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index 67396be3b0..6d50267289 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -1765,9 +1765,9 @@ BuildImplicitBaseInitializer(Sema &SemaRef, CXXConstructorDecl *Constructor, CXXCastPath BasePath; BasePath.push_back(BaseSpec); - SemaRef.ImpCastExprToType(CopyCtorArg, ArgTy, - CK_UncheckedDerivedToBase, - VK_LValue, &BasePath); + CopyCtorArg = SemaRef.ImpCastExprToType(CopyCtorArg, ArgTy, + CK_UncheckedDerivedToBase, + VK_LValue, &BasePath).take(); InitializationKind InitKind = InitializationKind::CreateDirect(Constructor->getLocation(), @@ -5603,21 +5603,19 @@ void Sema::DefineImplicitCopyAssignment(SourceLocation CurrentLocation, // Construct the "from" expression, which is an implicit cast to the // appropriately-qualified base type. Expr *From = OtherRef; - ImpCastExprToType(From, Context.getQualifiedType(BaseType, OtherQuals), - CK_UncheckedDerivedToBase, - VK_LValue, &BasePath); + From = ImpCastExprToType(From, Context.getQualifiedType(BaseType, OtherQuals), + CK_UncheckedDerivedToBase, + VK_LValue, &BasePath).take(); // Dereference "this". ExprResult To = CreateBuiltinUnaryOp(Loc, UO_Deref, This); // Implicitly cast "this" to the appropriately-qualified base type. - Expr *ToE = To.takeAs(); - ImpCastExprToType(ToE, - Context.getCVRQualifiedType(BaseType, - CopyAssignOperator->getTypeQualifiers()), - CK_UncheckedDerivedToBase, - VK_LValue, &BasePath); - To = Owned(ToE); + To = ImpCastExprToType(To.take(), + Context.getCVRQualifiedType(BaseType, + CopyAssignOperator->getTypeQualifiers()), + CK_UncheckedDerivedToBase, + VK_LValue, &BasePath); // Build the copy. StmtResult Copy = BuildSingleCopyAssign(*this, Loc, BaseType, diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp index a822c45b90..e8488f9ac4 100644 --- a/lib/Sema/SemaExpr.cpp +++ b/lib/Sema/SemaExpr.cpp @@ -256,13 +256,13 @@ SourceRange Sema::getExprRange(ExprTy *E) const { //===----------------------------------------------------------------------===// /// DefaultFunctionArrayConversion (C99 6.3.2.1p3, C99 6.3.2.1p4). -void Sema::DefaultFunctionArrayConversion(Expr *&E) { +ExprResult Sema::DefaultFunctionArrayConversion(Expr *E) { QualType Ty = E->getType(); assert(!Ty.isNull() && "DefaultFunctionArrayConversion - missing type"); if (Ty->isFunctionType()) - ImpCastExprToType(E, Context.getPointerType(Ty), - CK_FunctionToPointerDecay); + E = ImpCastExprToType(E, Context.getPointerType(Ty), + CK_FunctionToPointerDecay).take(); else if (Ty->isArrayType()) { // In C90 mode, arrays only promote to pointers if the array expression is // an lvalue. The relevant legalese is C90 6.2.2.1p3: "an lvalue that has @@ -276,25 +276,29 @@ void Sema::DefaultFunctionArrayConversion(Expr *&E) { // T" can be converted to an rvalue of type "pointer to T". // if (getLangOptions().C99 || getLangOptions().CPlusPlus || E->isLValue()) - ImpCastExprToType(E, Context.getArrayDecayedType(Ty), - CK_ArrayToPointerDecay); + E = ImpCastExprToType(E, Context.getArrayDecayedType(Ty), + CK_ArrayToPointerDecay).take(); } + return Owned(E); } -void Sema::DefaultLvalueConversion(Expr *&E) { +ExprResult Sema::DefaultLvalueConversion(Expr *E) { // C++ [conv.lval]p1: // A glvalue of a non-function, non-array type T can be // converted to a prvalue. - if (!E->isGLValue()) return; + if (!E->isGLValue()) return Owned(E); QualType T = E->getType(); assert(!T.isNull() && "r-value conversion on typeless expression?"); // Create a load out of an ObjCProperty l-value, if necessary. if (E->getObjectKind() == OK_ObjCProperty) { - ConvertPropertyForRValue(E); + ExprResult Res = ConvertPropertyForRValue(E); + if (Res.isInvalid()) + return Owned(E); + E = Res.take(); if (!E->isGLValue()) - return; + return Owned(E); } // We don't want to throw lvalue-to-rvalue casts on top of @@ -303,7 +307,7 @@ void Sema::DefaultLvalueConversion(Expr *&E) { (E->getType() == Context.OverloadTy || T->isDependentType() || T->isRecordType())) - return; + return Owned(E); // The C standard is actually really unclear on this point, and // DR106 tells us what the result should be but not why. It's @@ -311,7 +315,7 @@ void Sema::DefaultLvalueConversion(Expr *&E) { // lvalue-to-rvalue at all. Note that expressions of unqualified // 'void' type are never l-values, but qualified void can be. if (T->isVoidType()) - return; + return Owned(E); // C++ [conv.lval]p1: // [...] If T is a non-class type, the type of the prvalue is the @@ -327,13 +331,18 @@ void Sema::DefaultLvalueConversion(Expr *&E) { CheckArrayAccess(E); - E = ImplicitCastExpr::Create(Context, T, CK_LValueToRValue, - E, 0, VK_RValue); + return Owned(ImplicitCastExpr::Create(Context, T, CK_LValueToRValue, + E, 0, VK_RValue)); } -void Sema::DefaultFunctionArrayLvalueConversion(Expr *&E) { - DefaultFunctionArrayConversion(E); - DefaultLvalueConversion(E); +ExprResult Sema::DefaultFunctionArrayLvalueConversion(Expr *E) { + ExprResult Res = DefaultFunctionArrayConversion(E); + if (Res.isInvalid()) + return ExprError(); + Res = DefaultLvalueConversion(Res.take()); + if (Res.isInvalid()) + return ExprError(); + return move(Res); } @@ -342,9 +351,12 @@ void Sema::DefaultFunctionArrayLvalueConversion(Expr *&E) { /// sometimes surpressed. For example, the array->pointer conversion doesn't /// apply if the array is an argument to the sizeof or address (&) operators. /// In these instances, this routine should *not* be called. -Expr *Sema::UsualUnaryConversions(Expr *&E) { +ExprResult Sema::UsualUnaryConversions(Expr *E) { // First, convert to an r-value. - DefaultFunctionArrayLvalueConversion(E); + ExprResult Res = DefaultFunctionArrayLvalueConversion(E); + if (Res.isInvalid()) + return Owned(E); + E = Res.take(); QualType Ty = E->getType(); assert(!Ty.isNull() && "UsualUnaryConversions - missing type"); @@ -368,60 +380,66 @@ Expr *Sema::UsualUnaryConversions(Expr *&E) { QualType PTy = Context.isPromotableBitField(E); if (!PTy.isNull()) { - ImpCastExprToType(E, PTy, CK_IntegralCast); - return E; + E = ImpCastExprToType(E, PTy, CK_IntegralCast).take(); + return Owned(E); } if (Ty->isPromotableIntegerType()) { QualType PT = Context.getPromotedIntegerType(Ty); - ImpCastExprToType(E, PT, CK_IntegralCast); - return E; + E = ImpCastExprToType(E, PT, CK_IntegralCast).take(); + return Owned(E); } } - - return E; + return Owned(E); } /// DefaultArgumentPromotion (C99 6.5.2.2p6). Used for function calls that /// do not have a prototype. Arguments that have type float are promoted to /// double. All other argument types are converted by UsualUnaryConversions(). -void Sema::DefaultArgumentPromotion(Expr *&Expr) { - QualType Ty = Expr->getType(); +ExprResult Sema::DefaultArgumentPromotion(Expr *E) { + QualType Ty = E->getType(); assert(!Ty.isNull() && "DefaultArgumentPromotion - missing type"); - UsualUnaryConversions(Expr); + ExprResult Res = UsualUnaryConversions(E); + if (Res.isInvalid()) + return Owned(E); + E = Res.take(); // If this is a 'float' (CVR qualified or typedef) promote to double. if (Ty->isSpecificBuiltinType(BuiltinType::Float)) - return ImpCastExprToType(Expr, Context.DoubleTy, CK_FloatingCast); + E = ImpCastExprToType(E, Context.DoubleTy, CK_FloatingCast).take(); + + return Owned(E); } /// DefaultVariadicArgumentPromotion - Like DefaultArgumentPromotion, but /// will warn if the resulting type is not a POD type, and rejects ObjC -/// interfaces passed by value. This returns true if the argument type is -/// completely illegal. -bool Sema::DefaultVariadicArgumentPromotion(Expr *&Expr, VariadicCallType CT, +/// interfaces passed by value. +ExprResult Sema::DefaultVariadicArgumentPromotion(Expr *E, VariadicCallType CT, FunctionDecl *FDecl) { - DefaultArgumentPromotion(Expr); + ExprResult ExprRes = DefaultArgumentPromotion(E); + if (ExprRes.isInvalid()) + return ExprError(); + E = ExprRes.take(); // __builtin_va_start takes the second argument as a "varargs" argument, but // it doesn't actually do anything with it. It doesn't need to be non-pod // etc. if (FDecl && FDecl->getBuiltinID() == Builtin::BI__builtin_va_start) - return false; + return Owned(E); - if (Expr->getType()->isObjCObjectType() && - DiagRuntimeBehavior(Expr->getLocStart(), 0, + if (E->getType()->isObjCObjectType() && + DiagRuntimeBehavior(E->getLocStart(), 0, PDiag(diag::err_cannot_pass_objc_interface_to_vararg) - << Expr->getType() << CT)) - return true; + << E->getType() << CT)) + return ExprError(); - if (!Expr->getType()->isPODType() && - DiagRuntimeBehavior(Expr->getLocStart(), 0, + if (!E->getType()->isPODType() && + DiagRuntimeBehavior(E->getLocStart(), 0, PDiag(diag::warn_cannot_pass_non_pod_arg_to_vararg) - << Expr->getType() << CT)) - return true; + << E->getType() << CT)) + return ExprError(); - return false; + return Owned(E); } /// UsualArithmeticConversions - Performs various conversions that are common to @@ -430,19 +448,24 @@ bool Sema::DefaultVariadicArgumentPromotion(Expr *&Expr, VariadicCallType CT, /// responsible for emitting appropriate error diagnostics. /// FIXME: verify the conversion rules for "complex int" are consistent with /// GCC. -QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, +QualType Sema::UsualArithmeticConversions(ExprResult &lhsExpr, ExprResult &rhsExpr, bool isCompAssign) { - if (!isCompAssign) - UsualUnaryConversions(lhsExpr); + if (!isCompAssign) { + lhsExpr = UsualUnaryConversions(lhsExpr.take()); + if (lhsExpr.isInvalid()) + return QualType(); + } - UsualUnaryConversions(rhsExpr); + rhsExpr = UsualUnaryConversions(rhsExpr.take()); + if (rhsExpr.isInvalid()) + return QualType(); // For conversion purposes, we ignore any qualifiers. // For example, "const float" and "float" are equivalent. QualType lhs = - Context.getCanonicalType(lhsExpr->getType()).getUnqualifiedType(); + Context.getCanonicalType(lhsExpr.get()->getType()).getUnqualifiedType(); QualType rhs = - Context.getCanonicalType(rhsExpr->getType()).getUnqualifiedType(); + Context.getCanonicalType(rhsExpr.get()->getType()).getUnqualifiedType(); // If both types are identical, no conversion is needed. if (lhs == rhs) @@ -457,11 +480,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, QualType lhs_unpromoted = lhs; if (lhs->isPromotableIntegerType()) lhs = Context.getPromotedIntegerType(lhs); - QualType LHSBitfieldPromoteTy = Context.isPromotableBitField(lhsExpr); + QualType LHSBitfieldPromoteTy = Context.isPromotableBitField(lhsExpr.get()); if (!LHSBitfieldPromoteTy.isNull()) lhs = LHSBitfieldPromoteTy; if (lhs != lhs_unpromoted && !isCompAssign) - ImpCastExprToType(lhsExpr, lhs, CK_IntegralCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), lhs, CK_IntegralCast); // If both types are identical, no conversion is needed. if (lhs == rhs) @@ -478,11 +501,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (!RHSComplexFloat && !rhs->isRealFloatingType()) { if (rhs->isIntegerType()) { QualType fp = cast(lhs)->getElementType(); - ImpCastExprToType(rhsExpr, fp, CK_IntegralToFloating); - ImpCastExprToType(rhsExpr, lhs, CK_FloatingRealToComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), fp, CK_IntegralToFloating); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_FloatingRealToComplex); } else { assert(rhs->isComplexIntegerType()); - ImpCastExprToType(rhsExpr, lhs, CK_IntegralComplexToFloatingComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralComplexToFloatingComplex); } return lhs; } @@ -492,11 +515,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // int -> float -> _Complex float if (lhs->isIntegerType()) { QualType fp = cast(rhs)->getElementType(); - ImpCastExprToType(lhsExpr, fp, CK_IntegralToFloating); - ImpCastExprToType(lhsExpr, rhs, CK_FloatingRealToComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), fp, CK_IntegralToFloating); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_FloatingRealToComplex); } else { assert(lhs->isComplexIntegerType()); - ImpCastExprToType(lhsExpr, rhs, CK_IntegralComplexToFloatingComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralComplexToFloatingComplex); } } return rhs; @@ -518,13 +541,13 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (LHSComplexFloat && RHSComplexFloat) { if (order > 0) { // _Complex float -> _Complex double - ImpCastExprToType(rhsExpr, lhs, CK_FloatingComplexCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_FloatingComplexCast); return lhs; } else if (order < 0) { // _Complex float -> _Complex double if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_FloatingComplexCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_FloatingComplexCast); return rhs; } return lhs; @@ -536,8 +559,8 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (order > 0) { // LHS is wider // float -> _Complex double QualType fp = cast(lhs)->getElementType(); - ImpCastExprToType(rhsExpr, fp, CK_FloatingCast); - ImpCastExprToType(rhsExpr, lhs, CK_FloatingRealToComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), fp, CK_FloatingCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_FloatingRealToComplex); return lhs; } @@ -545,11 +568,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, QualType result = (order == 0 ? lhs : Context.getComplexType(rhs)); // double -> _Complex double - ImpCastExprToType(rhsExpr, result, CK_FloatingRealToComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), result, CK_FloatingRealToComplex); // _Complex float -> _Complex double if (!isCompAssign && order < 0) - ImpCastExprToType(lhsExpr, result, CK_FloatingComplexCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), result, CK_FloatingComplexCast); return result; } @@ -562,8 +585,8 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // float -> _Complex double if (!isCompAssign) { QualType fp = cast(rhs)->getElementType(); - ImpCastExprToType(lhsExpr, fp, CK_FloatingCast); - ImpCastExprToType(lhsExpr, rhs, CK_FloatingRealToComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), fp, CK_FloatingCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_FloatingRealToComplex); } return rhs; } @@ -573,11 +596,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // double -> _Complex double if (!isCompAssign) - ImpCastExprToType(lhsExpr, result, CK_FloatingRealToComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), result, CK_FloatingRealToComplex); // _Complex float -> _Complex double if (order > 0) - ImpCastExprToType(rhsExpr, result, CK_FloatingComplexCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), result, CK_FloatingComplexCast); return result; } @@ -591,13 +614,13 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (LHSFloat && RHSFloat) { int order = Context.getFloatingTypeOrder(lhs, rhs); if (order > 0) { - ImpCastExprToType(rhsExpr, lhs, CK_FloatingCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_FloatingCast); return lhs; } assert(order < 0 && "illegal float comparison"); if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_FloatingCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_FloatingCast); return rhs; } @@ -605,7 +628,7 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (LHSFloat) { if (rhs->isIntegerType()) { // Convert rhs to the lhs floating point type. - ImpCastExprToType(rhsExpr, lhs, CK_IntegralToFloating); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralToFloating); return lhs; } @@ -614,11 +637,11 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, QualType result = Context.getComplexType(lhs); // _Complex int -> _Complex float - ImpCastExprToType(rhsExpr, result, CK_IntegralComplexToFloatingComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), result, CK_IntegralComplexToFloatingComplex); // float -> _Complex float if (!isCompAssign) - ImpCastExprToType(lhsExpr, result, CK_FloatingRealToComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), result, CK_FloatingRealToComplex); return result; } @@ -627,7 +650,7 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (lhs->isIntegerType()) { // Convert lhs to the rhs floating point type. if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralToFloating); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralToFloating); return rhs; } @@ -637,10 +660,10 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // _Complex int -> _Complex float if (!isCompAssign) - ImpCastExprToType(lhsExpr, result, CK_IntegralComplexToFloatingComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), result, CK_IntegralComplexToFloatingComplex); // float -> _Complex float - ImpCastExprToType(rhsExpr, result, CK_FloatingRealToComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), result, CK_FloatingRealToComplex); return result; } @@ -656,21 +679,21 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, assert(order && "inequal types with equal element ordering"); if (order > 0) { // _Complex int -> _Complex long - ImpCastExprToType(rhsExpr, lhs, CK_IntegralComplexCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralComplexCast); return lhs; } if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralComplexCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralComplexCast); return rhs; } else if (lhsComplexInt) { // int -> _Complex int - ImpCastExprToType(rhsExpr, lhs, CK_IntegralRealToComplex); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralRealToComplex); return lhs; } else if (rhsComplexInt) { // int -> _Complex int if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralRealToComplex); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralRealToComplex); return rhs; } @@ -682,29 +705,29 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, if (lhsSigned == rhsSigned) { // Same signedness; use the higher-ranked type if (compare >= 0) { - ImpCastExprToType(rhsExpr, lhs, CK_IntegralCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralCast); return lhs; } else if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralCast); return rhs; } else if (compare != (lhsSigned ? 1 : -1)) { // The unsigned type has greater than or equal rank to the // signed type, so use the unsigned type if (rhsSigned) { - ImpCastExprToType(rhsExpr, lhs, CK_IntegralCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralCast); return lhs; } else if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralCast); return rhs; } else if (Context.getIntWidth(lhs) != Context.getIntWidth(rhs)) { // The two types are different widths; if we are here, that // means the signed type is larger than the unsigned type, so // use the signed type. if (lhsSigned) { - ImpCastExprToType(rhsExpr, lhs, CK_IntegralCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), lhs, CK_IntegralCast); return lhs; } else if (!isCompAssign) - ImpCastExprToType(lhsExpr, rhs, CK_IntegralCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), rhs, CK_IntegralCast); return rhs; } else { // The signed type is higher-ranked than the unsigned type, @@ -713,9 +736,9 @@ QualType Sema::UsualArithmeticConversions(Expr *&lhsExpr, Expr *&rhsExpr, // to the signed type. QualType result = Context.getCorrespondingUnsignedType(lhsSigned ? lhs : rhs); - ImpCastExprToType(rhsExpr, result, CK_IntegralCast); + rhsExpr = ImpCastExprToType(rhsExpr.take(), result, CK_IntegralCast); if (!isCompAssign) - ImpCastExprToType(lhsExpr, result, CK_IntegralCast); + lhsExpr = ImpCastExprToType(lhsExpr.take(), result, CK_IntegralCast); return result; } } @@ -1887,13 +1910,14 @@ Sema::LookupInObjCMethod(LookupResult &Lookup, Scope *S, if (SelfExpr.isInvalid()) return ExprError(); - Expr *SelfE = SelfExpr.take(); - DefaultLvalueConversion(SelfE); + SelfExpr = DefaultLvalueConversion(SelfExpr.take()); + if (SelfExpr.isInvalid()) + return ExprError(); MarkDeclarationReferenced(Loc, IV); return Owned(new (Context) ObjCIvarRefExpr(IV, IV->getType(), Loc, - SelfE, true, true)); + SelfExpr.take(), true, true)); } } else if (CurMethod->isInstanceMethod()) { // We should warn if a local variable hides an ivar. @@ -1939,14 +1963,14 @@ Sema::LookupInObjCMethod(LookupResult &Lookup, Scope *S, /// * Finally we cast from the declaring class to the "true" /// declaring class of the member. This conversion does not /// obey access control. -bool -Sema::PerformObjectMemberConversion(Expr *&From, +ExprResult +Sema::PerformObjectMemberConversion(Expr *From, NestedNameSpecifier *Qualifier, NamedDecl *FoundDecl, NamedDecl *Member) { CXXRecordDecl *RD = dyn_cast(Member->getDeclContext()); if (!RD) - return false; + return Owned(From); QualType DestRecordType; QualType DestType; @@ -1966,7 +1990,7 @@ Sema::PerformObjectMemberConversion(Expr *&From, } } else if (CXXMethodDecl *Method = dyn_cast(Member)) { if (Method->isStatic()) - return false; + return Owned(From); DestType = Method->getThisType(Context); DestRecordType = DestType->getPointeeType(); @@ -1980,15 +2004,15 @@ Sema::PerformObjectMemberConversion(Expr *&From, } } else { // No conversion necessary. - return false; + return Owned(From); } if (DestType->isDependentType() || FromType->isDependentType()) - return false; + return Owned(From); // If the unqualified types are the same, no conversion is necessary. if (Context.hasSameUnqualifiedType(FromRecordType, DestRecordType)) - return false; + return Owned(From); SourceRange FromRange = From->getSourceRange(); SourceLocation FromLoc = FromRange.getBegin(); @@ -2027,12 +2051,12 @@ Sema::PerformObjectMemberConversion(Expr *&From, CXXCastPath BasePath; if (CheckDerivedToBaseConversion(FromRecordType, QRecordType, FromLoc, FromRange, &BasePath)) - return true; + return ExprError(); if (PointerConversions) QType = Context.getPointerType(QType); - ImpCastExprToType(From, QType, CK_UncheckedDerivedToBase, - VK, &BasePath); + From = ImpCastExprToType(From, QType, CK_UncheckedDerivedToBase, + VK, &BasePath).take(); FromType = QType; FromRecordType = QRecordType; @@ -2040,7 +2064,7 @@ Sema::PerformObjectMemberConversion(Expr *&From, // If the qualifier type was the same as the destination type, // we're done. if (Context.hasSameUnqualifiedType(FromRecordType, DestRecordType)) - return false; + return Owned(From); } } @@ -2063,13 +2087,13 @@ Sema::PerformObjectMemberConversion(Expr *&From, CXXCastPath BasePath; if (CheckDerivedToBaseConversion(FromRecordType, URecordType, FromLoc, FromRange, &BasePath)) - return true; + return ExprError(); QualType UType = URecordType; if (PointerConversions) UType = Context.getPointerType(UType); - ImpCastExprToType(From, UType, CK_UncheckedDerivedToBase, - VK, &BasePath); + From = ImpCastExprToType(From, UType, CK_UncheckedDerivedToBase, + VK, &BasePath).take(); FromType = UType; FromRecordType = URecordType; } @@ -2083,11 +2107,10 @@ Sema::PerformObjectMemberConversion(Expr *&From, if (CheckDerivedToBaseConversion(FromRecordType, DestRecordType, FromLoc, FromRange, &BasePath, IgnoreAccess)) - return true; + return ExprError(); - ImpCastExprToType(From, DestType, CK_UncheckedDerivedToBase, - VK, &BasePath); - return false; + return ImpCastExprToType(From, DestType, CK_UncheckedDerivedToBase, + VK, &BasePath); } /// \brief Build a MemberExpr AST node. @@ -2153,10 +2176,12 @@ BuildFieldReferenceExpr(Sema &S, Expr *BaseExpr, bool IsArrow, } S.MarkDeclarationReferenced(MemberNameInfo.getLoc(), Field); - if (S.PerformObjectMemberConversion(BaseExpr, SS.getScopeRep(), - FoundDecl, Field)) + ExprResult Base = + S.PerformObjectMemberConversion(BaseExpr, SS.getScopeRep(), + FoundDecl, Field); + if (Base.isInvalid()) return ExprError(); - return S.Owned(BuildMemberExpr(S.Context, BaseExpr, IsArrow, SS, + return S.Owned(BuildMemberExpr(S.Context, Base.take(), IsArrow, SS, Field, FoundDecl, MemberNameInfo, MemberType, VK, OK)); } @@ -2638,10 +2663,10 @@ ExprResult Sema::ActOnNumericConstant(const Token &Tok) { if (Ty == Context.DoubleTy) { if (getLangOptions().SinglePrecisionConstants) { - ImpCastExprToType(Res, Context.FloatTy, CK_FloatingCast); + Res = ImpCastExprToType(Res, Context.FloatTy, CK_FloatingCast).take(); } else if (getLangOptions().OpenCL && !getOpenCLOptions().cl_khr_fp64) { Diag(Tok.getLocation(), diag::warn_double_const_requires_fp64); - ImpCastExprToType(Res, Context.FloatTy, CK_FloatingCast); + Res = ImpCastExprToType(Res, Context.FloatTy, CK_FloatingCast).take(); } } } else if (!Literal.isIntegerLiteral()) { @@ -2931,33 +2956,36 @@ Sema::ActOnUnaryExprOrTypeTraitExpr(SourceLocation OpLoc, return move(Result); } -static QualType CheckRealImagOperand(Sema &S, Expr *&V, SourceLocation Loc, +static QualType CheckRealImagOperand(Sema &S, ExprResult &V, SourceLocation Loc, bool isReal) { - if (V->isTypeDependent()) + if (V.get()->isTypeDependent()) return S.Context.DependentTy; // _Real and _Imag are only l-values for normal l-values. - if (V->getObjectKind() != OK_Ordinary) - S.DefaultLvalueConversion(V); + if (V.get()->getObjectKind() != OK_Ordinary) { + V = S.DefaultLvalueConversion(V.take()); + if (V.isInvalid()) + return QualType(); + } // These operators return the element type of a complex type. - if (const ComplexType *CT = V->getType()->getAs()) + if (const ComplexType *CT = V.get()->getType()->getAs()) return CT->getElementType(); // Otherwise they pass through real integer and floating point types here. - if (V->getType()->isArithmeticType()) - return V->getType(); + if (V.get()->getType()->isArithmeticType()) + return V.get()->getType(); // Test for placeholders. - ExprResult PR = S.CheckPlaceholderExpr(V, Loc); + ExprResult PR = S.CheckPlaceholderExpr(V.get(), Loc); if (PR.isInvalid()) return QualType(); - if (PR.take() != V) { - V = PR.take(); + if (PR.get() != V.get()) { + V = move(PR); return CheckRealImagOperand(S, V, Loc, isReal); } // Reject anything else. - S.Diag(Loc, diag::err_realimag_invalid_type) << V->getType() + S.Diag(Loc, diag::err_realimag_invalid_type) << V.get()->getType() << (isReal ? "__real" : "__imag"); return QualType(); } @@ -3027,9 +3055,16 @@ Sema::CreateBuiltinArraySubscriptExpr(Expr *Base, SourceLocation LLoc, Expr *RHSExp = Idx; // Perform default conversions. - if (!LHSExp->getType()->getAs()) - DefaultFunctionArrayLvalueConversion(LHSExp); - DefaultFunctionArrayLvalueConversion(RHSExp); + if (!LHSExp->getType()->getAs()) { + ExprResult Result = DefaultFunctionArrayLvalueConversion(LHSExp); + if (Result.isInvalid()) + return ExprError(); + LHSExp = Result.take(); + } + ExprResult Result = DefaultFunctionArrayLvalueConversion(RHSExp); + if (Result.isInvalid()) + return ExprError(); + RHSExp = Result.take(); QualType LHSTy = LHSExp->getType(), RHSTy = RHSExp->getType(); ExprValueKind VK = VK_LValue; @@ -3082,8 +3117,8 @@ Sema::CreateBuiltinArraySubscriptExpr(Expr *Base, SourceLocation LLoc, // force the promotion here. Diag(LHSExp->getLocStart(), diag::ext_subscript_non_lvalue) << LHSExp->getSourceRange(); - ImpCastExprToType(LHSExp, Context.getArrayDecayedType(LHSTy), - CK_ArrayToPointerDecay); + LHSExp = ImpCastExprToType(LHSExp, Context.getArrayDecayedType(LHSTy), + CK_ArrayToPointerDecay).take(); LHSTy = LHSExp->getType(); BaseExpr = LHSExp; @@ -3093,8 +3128,8 @@ Sema::CreateBuiltinArraySubscriptExpr(Expr *Base, SourceLocation LLoc, // Same as previous, except for 123[f().a] case Diag(RHSExp->getLocStart(), diag::ext_subscript_non_lvalue) << RHSExp->getSourceRange(); - ImpCastExprToType(RHSExp, Context.getArrayDecayedType(RHSTy), - CK_ArrayToPointerDecay); + RHSExp = ImpCastExprToType(RHSExp, Context.getArrayDecayedType(RHSTy), + CK_ArrayToPointerDecay).take(); RHSTy = RHSExp->getType(); BaseExpr = RHSExp; @@ -3512,10 +3547,15 @@ Sema::BuildMemberReferenceExpr(Expr *Base, QualType BaseType, // Explicit member accesses. } else { + ExprResult BaseResult = Owned(Base); ExprResult Result = - LookupMemberExpr(R, Base, IsArrow, OpLoc, + LookupMemberExpr(R, BaseResult, IsArrow, OpLoc, SS, /*ObjCImpDecl*/ 0, TemplateArgs != 0); + if (BaseResult.isInvalid()) + return ExprError(); + Base = BaseResult.take(); + if (Result.isInvalid()) { Owned(Base); return ExprError(); @@ -3639,8 +3679,12 @@ Sema::BuildMemberReferenceExpr(Expr *BaseExpr, QualType BaseExprType, // Perform a property load on the base regardless of whether we // actually need it for the declaration. - if (BaseExpr->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(BaseExpr); + if (BaseExpr->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(BaseExpr); + if (Result.isInvalid()) + return ExprError(); + BaseExpr = Result.take(); + } if (FieldDecl *FD = dyn_cast(MemberDecl)) return BuildFieldReferenceExpr(*this, BaseExpr, IsArrow, @@ -3699,9 +3743,9 @@ Sema::BuildMemberReferenceExpr(Expr *BaseExpr, QualType BaseExprType, /// types would be profitable. The redefinition type is whatever /// this translation unit tried to typedef to id/Class; we store /// it to the side and then re-use it in places like this. -static bool ShouldTryAgainWithRedefinitionType(Sema &S, Expr *&base) { +static bool ShouldTryAgainWithRedefinitionType(Sema &S, ExprResult &base) { const ObjCObjectPointerType *opty - = base->getType()->getAs(); + = base.get()->getType()->getAs(); if (!opty) return false; const ObjCObjectType *ty = opty->getObjectType(); @@ -3721,7 +3765,7 @@ static bool ShouldTryAgainWithRedefinitionType(Sema &S, Expr *&base) { if (opty && !opty->getObjectType()->getInterface() != 0) return false; - S.ImpCastExprToType(base, redef, CK_BitCast); + base = S.ImpCastExprToType(base.take(), redef, CK_BitCast); return true; } @@ -3736,17 +3780,22 @@ static bool ShouldTryAgainWithRedefinitionType(Sema &S, Expr *&base) { /// The ObjCImpDecl bit is a gross hack that will need to be properly /// fixed for ObjC++. ExprResult -Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, +Sema::LookupMemberExpr(LookupResult &R, ExprResult &BaseExpr, bool &IsArrow, SourceLocation OpLoc, CXXScopeSpec &SS, Decl *ObjCImpDecl, bool HasTemplateArgs) { - assert(BaseExpr && "no base expression"); + assert(BaseExpr.get() && "no base expression"); // Perform default conversions. - DefaultFunctionArrayConversion(BaseExpr); - if (IsArrow) DefaultLvalueConversion(BaseExpr); + BaseExpr = DefaultFunctionArrayConversion(BaseExpr.take()); + + if (IsArrow) { + BaseExpr = DefaultLvalueConversion(BaseExpr.take()); + if (BaseExpr.isInvalid()) + return ExprError(); + } - QualType BaseType = BaseExpr->getType(); + QualType BaseType = BaseExpr.get()->getType(); assert(!BaseType->isDependentType()); DeclarationName MemberName = R.getLookupName(); @@ -3770,19 +3819,19 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, // overloaded operator->, but that should have been dealt with // by now. Diag(OpLoc, diag::err_typecheck_member_reference_suggestion) - << BaseType << int(IsArrow) << BaseExpr->getSourceRange() + << BaseType << int(IsArrow) << BaseExpr.get()->getSourceRange() << FixItHint::CreateReplacement(OpLoc, "."); IsArrow = false; } else { Diag(MemberLoc, diag::err_typecheck_member_reference_arrow) - << BaseType << BaseExpr->getSourceRange(); + << BaseType << BaseExpr.get()->getSourceRange(); return ExprError(); } } // Handle field access to simple records. if (const RecordType *RTy = BaseType->getAs()) { - if (LookupMemberExprInRecord(*this, R, BaseExpr->getSourceRange(), + if (LookupMemberExprInRecord(*this, R, BaseExpr.get()->getSourceRange(), RTy, OpLoc, SS, HasTemplateArgs)) return ExprError(); @@ -3805,7 +3854,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, // But we only actually find it this way on objects of type 'id', // apparently. if (OTy->isObjCId() && Member->isStr("isa")) - return Owned(new (Context) ObjCIsaExpr(BaseExpr, IsArrow, MemberLoc, + return Owned(new (Context) ObjCIsaExpr(BaseExpr.take(), IsArrow, MemberLoc, Context.getObjCClassType())); if (ShouldTryAgainWithRedefinitionType(*this, BaseExpr)) @@ -3838,7 +3887,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, Diag(MemberLoc, diag::err_typecheck_member_reference_ivar) << IDecl->getDeclName() << MemberName - << BaseExpr->getSourceRange(); + << BaseExpr.get()->getSourceRange(); return ExprError(); } } @@ -3884,7 +3933,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, } return Owned(new (Context) ObjCIvarRefExpr(IV, IV->getType(), - MemberLoc, BaseExpr, + MemberLoc, BaseExpr.take(), IsArrow)); } @@ -3892,8 +3941,11 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, const ObjCObjectPointerType *OPT; if (!IsArrow && (OPT = BaseType->getAs())) { // This actually uses the base as an r-value. - DefaultLvalueConversion(BaseExpr); - assert(Context.hasSameUnqualifiedType(BaseType, BaseExpr->getType())); + BaseExpr = DefaultLvalueConversion(BaseExpr.take()); + if (BaseExpr.isInvalid()) + return ExprError(); + + assert(Context.hasSameUnqualifiedType(BaseType, BaseExpr.get()->getType())); IdentifierInfo *Member = MemberName.getAsIdentifierInfo(); @@ -3913,7 +3965,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, VK_LValue, OK_ObjCProperty, MemberLoc, - BaseExpr)); + BaseExpr.take())); } if (ObjCMethodDecl *OMD = dyn_cast(PMDecl)) { @@ -3937,7 +3989,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, return Owned(new (Context) ObjCPropertyRefExpr(OMD, SMD, PType, VK, OK, - MemberLoc, BaseExpr)); + MemberLoc, BaseExpr.take())); } } // Use of id.member can only be for a property reference. Do not @@ -4008,7 +4060,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, // FIXME: we must check that the setter has property type. return Owned(new (Context) ObjCPropertyRefExpr(Getter, Setter, PType, VK, OK, - MemberLoc, BaseExpr)); + MemberLoc, BaseExpr.take())); } if (ShouldTryAgainWithRedefinitionType(*this, BaseExpr)) @@ -4020,7 +4072,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, } // Normal property access. - return HandleExprPropertyRefExpr(OPT, BaseExpr, MemberName, MemberLoc, + return HandleExprPropertyRefExpr(OPT, BaseExpr.get(), MemberName, MemberLoc, SourceLocation(), QualType(), false); } @@ -4028,13 +4080,13 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, if (BaseType->isExtVectorType()) { // FIXME: this expr should store IsArrow. IdentifierInfo *Member = MemberName.getAsIdentifierInfo(); - ExprValueKind VK = (IsArrow ? VK_LValue : BaseExpr->getValueKind()); + ExprValueKind VK = (IsArrow ? VK_LValue : BaseExpr.get()->getValueKind()); QualType ret = CheckExtVectorComponent(*this, BaseType, VK, OpLoc, Member, MemberLoc); if (ret.isNull()) return ExprError(); - return Owned(new (Context) ExtVectorElementExpr(ret, VK, BaseExpr, + return Owned(new (Context) ExtVectorElementExpr(ret, VK, BaseExpr.take(), *Member, MemberLoc)); } @@ -4043,7 +4095,8 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, if (IsArrow && BaseType->isSpecificBuiltinType(BuiltinType::ObjCSel) && !Context.ObjCSelRedefinitionType->isObjCSelType()) { - ImpCastExprToType(BaseExpr, Context.ObjCSelRedefinitionType, CK_BitCast); + BaseExpr = ImpCastExprToType(BaseExpr.take(), Context.ObjCSelRedefinitionType, + CK_BitCast); return LookupMemberExpr(R, BaseExpr, IsArrow, OpLoc, SS, ObjCImpDecl, HasTemplateArgs); } @@ -4062,7 +4115,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, if (!IsArrow && Ptr->getPointeeType()->isRecordType() && MemberName.getNameKind() != DeclarationName::CXXDestructorName) { Diag(OpLoc, diag::err_typecheck_member_reference_suggestion) - << BaseType << int(IsArrow) << BaseExpr->getSourceRange() + << BaseType << int(IsArrow) << BaseExpr.get()->getSourceRange() << FixItHint::CreateReplacement(OpLoc, "->"); // Recurse as an -> access. @@ -4077,11 +4130,11 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, bool TryCall = false; bool Overloaded = false; UnresolvedSet<8> AllOverloads; - if (const OverloadExpr *Overloads = dyn_cast(BaseExpr)) { + if (const OverloadExpr *Overloads = dyn_cast(BaseExpr.get())) { AllOverloads.append(Overloads->decls_begin(), Overloads->decls_end()); TryCall = true; Overloaded = true; - } else if (DeclRefExpr *DeclRef = dyn_cast(BaseExpr)) { + } else if (DeclRefExpr *DeclRef = dyn_cast(BaseExpr.get())) { if (FunctionDecl* Fun = dyn_cast(DeclRef->getDecl())) { AllOverloads.addDecl(Fun); TryCall = true; @@ -4111,9 +4164,9 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, } if (!HasViableZeroArgOverload || ViableOverloads.size() != 1) { - Diag(BaseExpr->getExprLoc(), diag::err_member_reference_needs_call) + Diag(BaseExpr.get()->getExprLoc(), diag::err_member_reference_needs_call) << (AllOverloads.size() > 1) << 0 - << BaseExpr->getSourceRange(); + << BaseExpr.get()->getSourceRange(); int ViableOverloadCount = ViableOverloads.size(); int I; for (I = 0; I < ViableOverloadCount; ++I) { @@ -4126,7 +4179,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, diag::note_member_ref_possible_intended_overload); } if (I != ViableOverloadCount) { - Diag(BaseExpr->getExprLoc(), diag::note_ovl_too_many_candidates) + Diag(BaseExpr.get()->getExprLoc(), diag::note_ovl_too_many_candidates) << int(ViableOverloadCount - I); } return ExprError(); @@ -4162,24 +4215,24 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, // can emit a fixit and carry on pretending that BaseExpr was actually a // CallExpr. SourceLocation ParenInsertionLoc = - PP.getLocForEndOfToken(BaseExpr->getLocEnd()); - Diag(BaseExpr->getExprLoc(), diag::err_member_reference_needs_call) + PP.getLocForEndOfToken(BaseExpr.get()->getLocEnd()); + Diag(BaseExpr.get()->getExprLoc(), diag::err_member_reference_needs_call) << int(Overloaded) << 1 - << BaseExpr->getSourceRange() + << BaseExpr.get()->getSourceRange() << FixItHint::CreateInsertion(ParenInsertionLoc, "()"); - ExprResult NewBase = ActOnCallExpr(0, BaseExpr, ParenInsertionLoc, + ExprResult NewBase = ActOnCallExpr(0, BaseExpr.take(), ParenInsertionLoc, MultiExprArg(*this, 0, 0), ParenInsertionLoc); if (NewBase.isInvalid()) return ExprError(); - BaseExpr = NewBase.takeAs(); - DefaultFunctionArrayConversion(BaseExpr); + BaseExpr = NewBase; + BaseExpr = DefaultFunctionArrayConversion(BaseExpr.take()); return LookupMemberExpr(R, BaseExpr, IsArrow, OpLoc, SS, ObjCImpDecl, HasTemplateArgs); } Diag(MemberLoc, diag::err_typecheck_member_reference_struct_union) - << BaseType << BaseExpr->getSourceRange(); + << BaseType << BaseExpr.get()->getSourceRange(); return ExprError(); } @@ -4241,8 +4294,12 @@ ExprResult Sema::ActOnMemberAccessExpr(Scope *S, Expr *Base, NameInfo, TemplateArgs); } else { LookupResult R(*this, NameInfo, LookupMemberName); - Result = LookupMemberExpr(R, Base, IsArrow, OpLoc, + ExprResult BaseResult = Owned(Base); + Result = LookupMemberExpr(R, BaseResult, IsArrow, OpLoc, SS, ObjCImpDecl, TemplateArgs != 0); + if (BaseResult.isInvalid()) + return ExprError(); + Base = BaseResult.take(); if (Result.isInvalid()) { Owned(Base); @@ -4477,9 +4534,9 @@ bool Sema::GatherArgumentsForCall(SourceLocation CallLoc, if (CallType != VariadicDoesNotApply) { // Promote the arguments (C99 6.5.2.2p7). for (unsigned i = ArgIx; i != NumArgs; ++i) { - Expr *Arg = Args[i]; - Invalid |= DefaultVariadicArgumentPromotion(Arg, CallType, FDecl); - AllArgs.push_back(Arg); + ExprResult Arg = DefaultVariadicArgumentPromotion(Args[i], CallType, FDecl); + Invalid |= Arg.isInvalid(); + AllArgs.push_back(Arg.take()); } } return Invalid; @@ -4714,7 +4771,10 @@ Sema::BuildResolvedCallExpr(Expr *Fn, NamedDecl *NDecl, FunctionDecl *FDecl = dyn_cast_or_null(NDecl); // Promote the function operand. - UsualUnaryConversions(Fn); + ExprResult Result = UsualUnaryConversions(Fn); + if (Result.isInvalid()) + return ExprError(); + Fn = Result.take(); // Make the call expr early, before semantic checks. This guarantees cleanup // of arguments and function on error. @@ -4832,7 +4892,12 @@ Sema::BuildResolvedCallExpr(Expr *Fn, NamedDecl *NDecl, Arg = ArgE.takeAs(); } else { - DefaultArgumentPromotion(Arg); + ExprResult ArgE = DefaultArgumentPromotion(Arg); + + if (ArgE.isInvalid()) + return true; + + Arg = ArgE.takeAs(); } if (RequireCompleteType(Arg->getSourceRange().getBegin(), @@ -4948,12 +5013,12 @@ Sema::ActOnInitList(SourceLocation LBraceLoc, MultiExprArg initlist, /// Prepares for a scalar cast, performing all the necessary stages /// except the final cast and returning the kind required. -static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { +static CastKind PrepareScalarCast(Sema &S, ExprResult &Src, QualType DestTy) { // Both Src and Dest are scalar types, i.e. arithmetic or pointer. // Also, callers should have filtered out the invalid cases with // pointers. Everything else should be possible. - QualType SrcTy = Src->getType(); + QualType SrcTy = Src.get()->getType(); if (S.Context.hasSameUnqualifiedType(SrcTy, DestTy)) return CK_NoOp; @@ -4983,7 +5048,7 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { case Type::STK_Integral: switch (DestTy->getScalarTypeKind()) { case Type::STK_Pointer: - if (Src->isNullPointerConstant(S.Context, Expr::NPC_ValueDependentIsNull)) + if (Src.get()->isNullPointerConstant(S.Context, Expr::NPC_ValueDependentIsNull)) return CK_NullToPointer; return CK_IntegralToPointer; case Type::STK_Bool: @@ -4993,12 +5058,12 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { case Type::STK_Floating: return CK_IntegralToFloating; case Type::STK_IntegralComplex: - S.ImpCastExprToType(Src, DestTy->getAs()->getElementType(), - CK_IntegralCast); + Src = S.ImpCastExprToType(Src.take(), DestTy->getAs()->getElementType(), + CK_IntegralCast); return CK_IntegralRealToComplex; case Type::STK_FloatingComplex: - S.ImpCastExprToType(Src, DestTy->getAs()->getElementType(), - CK_IntegralToFloating); + Src = S.ImpCastExprToType(Src.take(), DestTy->getAs()->getElementType(), + CK_IntegralToFloating); return CK_FloatingRealToComplex; case Type::STK_MemberPointer: llvm_unreachable("member pointer type in C"); @@ -5014,12 +5079,12 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { case Type::STK_Integral: return CK_FloatingToIntegral; case Type::STK_FloatingComplex: - S.ImpCastExprToType(Src, DestTy->getAs()->getElementType(), - CK_FloatingCast); + Src = S.ImpCastExprToType(Src.take(), DestTy->getAs()->getElementType(), + CK_FloatingCast); return CK_FloatingRealToComplex; case Type::STK_IntegralComplex: - S.ImpCastExprToType(Src, DestTy->getAs()->getElementType(), - CK_FloatingToIntegral); + Src = S.ImpCastExprToType(Src.take(), DestTy->getAs()->getElementType(), + CK_FloatingToIntegral); return CK_IntegralRealToComplex; case Type::STK_Pointer: llvm_unreachable("valid float->pointer cast?"); @@ -5038,14 +5103,14 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { QualType ET = SrcTy->getAs()->getElementType(); if (S.Context.hasSameType(ET, DestTy)) return CK_FloatingComplexToReal; - S.ImpCastExprToType(Src, ET, CK_FloatingComplexToReal); + Src = S.ImpCastExprToType(Src.take(), ET, CK_FloatingComplexToReal); return CK_FloatingCast; } case Type::STK_Bool: return CK_FloatingComplexToBoolean; case Type::STK_Integral: - S.ImpCastExprToType(Src, SrcTy->getAs()->getElementType(), - CK_FloatingComplexToReal); + Src = S.ImpCastExprToType(Src.take(), SrcTy->getAs()->getElementType(), + CK_FloatingComplexToReal); return CK_FloatingToIntegral; case Type::STK_Pointer: llvm_unreachable("valid complex float->pointer cast?"); @@ -5064,14 +5129,14 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { QualType ET = SrcTy->getAs()->getElementType(); if (S.Context.hasSameType(ET, DestTy)) return CK_IntegralComplexToReal; - S.ImpCastExprToType(Src, ET, CK_IntegralComplexToReal); + Src = S.ImpCastExprToType(Src.take(), ET, CK_IntegralComplexToReal); return CK_IntegralCast; } case Type::STK_Bool: return CK_IntegralComplexToBoolean; case Type::STK_Floating: - S.ImpCastExprToType(Src, SrcTy->getAs()->getElementType(), - CK_IntegralComplexToReal); + Src = S.ImpCastExprToType(Src.take(), SrcTy->getAs()->getElementType(), + CK_IntegralComplexToReal); return CK_IntegralToFloating; case Type::STK_Pointer: llvm_unreachable("valid complex int->pointer cast?"); @@ -5086,9 +5151,9 @@ static CastKind PrepareScalarCast(Sema &S, Expr *&Src, QualType DestTy) { } /// CheckCastTypes - Check type constraints for casting between types. -bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, - Expr *&castExpr, CastKind& Kind, ExprValueKind &VK, - CXXCastPath &BasePath, bool FunctionalStyle) { +ExprResult Sema::CheckCastTypes(SourceRange TyR, QualType castType, + Expr *castExpr, CastKind& Kind, ExprValueKind &VK, + CXXCastPath &BasePath, bool FunctionalStyle) { if (castExpr->getType() == Context.UnknownAnyTy) return checkUnknownAnyCast(TyR, castType, castExpr, Kind, VK, BasePath); @@ -5105,18 +5170,24 @@ bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, // type needs to be scalar. if (castType->isVoidType()) { // We don't necessarily do lvalue-to-rvalue conversions on this. - IgnoredValueConversions(castExpr); + ExprResult castExprRes = IgnoredValueConversions(castExpr); + if (castExprRes.isInvalid()) + return ExprError(); + castExpr = castExprRes.take(); // Cast to void allows any expr type. Kind = CK_ToVoid; - return false; + return Owned(castExpr); } - DefaultFunctionArrayLvalueConversion(castExpr); + ExprResult castExprRes = DefaultFunctionArrayLvalueConversion(castExpr); + if (castExprRes.isInvalid()) + return ExprError(); + castExpr = castExprRes.take(); if (RequireCompleteType(TyR.getBegin(), castType, diag::err_typecheck_cast_to_incomplete)) - return true; + return ExprError(); if (!castType->isScalarType() && !castType->isVectorType()) { if (Context.hasSameUnqualifiedType(castType, castExpr->getType()) && @@ -5126,7 +5197,7 @@ bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, Diag(TyR.getBegin(), diag::ext_typecheck_cast_nonscalar) << castType << castExpr->getSourceRange(); Kind = CK_NoOp; - return false; + return Owned(castExpr); } if (castType->isUnionType()) { @@ -5143,16 +5214,19 @@ bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, break; } } - if (Field == FieldEnd) - return Diag(TyR.getBegin(), diag::err_typecheck_cast_to_union_no_type) + if (Field == FieldEnd) { + Diag(TyR.getBegin(), diag::err_typecheck_cast_to_union_no_type) << castExpr->getType() << castExpr->getSourceRange(); + return ExprError(); + } Kind = CK_ToUnion; - return false; + return Owned(castExpr); } // Reject any other conversions to non-scalar types. - return Diag(TyR.getBegin(), diag::err_typecheck_cond_expect_scalar) + Diag(TyR.getBegin(), diag::err_typecheck_cond_expect_scalar) << castType << castExpr->getSourceRange(); + return ExprError(); } // The type we're casting to is known to be a scalar or vector. @@ -5160,9 +5234,10 @@ bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, // Require the operand to be a scalar or vector. if (!castExpr->getType()->isScalarType() && !castExpr->getType()->isVectorType()) { - return Diag(castExpr->getLocStart(), + Diag(castExpr->getLocStart(), diag::err_typecheck_expect_scalar_operand) << castExpr->getType() << castExpr->getSourceRange(); + return ExprError(); } if (castType->isExtVectorType()) @@ -5174,43 +5249,58 @@ bool Sema::CheckCastTypes(SourceRange TyR, QualType castType, (castExpr->getType()->isIntegerType() || castExpr->getType()->isFloatingType())) { Kind = CK_VectorSplat; - return false; + return Owned(castExpr); + } else if (CheckVectorCast(TyR, castType, castExpr->getType(), Kind)) { + return ExprError(); } else - return CheckVectorCast(TyR, castType, castExpr->getType(), Kind); + return Owned(castExpr); + } + if (castExpr->getType()->isVectorType()) { + if (CheckVectorCast(TyR, castExpr->getType(), castType, Kind)) + return ExprError(); + else + return Owned(castExpr); } - if (castExpr->getType()->isVectorType()) - return CheckVectorCast(TyR, castExpr->getType(), castType, Kind); // The source and target types are both scalars, i.e. // - arithmetic types (fundamental, enum, and complex) // - all kinds of pointers // Note that member pointers were filtered out with C++, above. - if (isa(castExpr)) - return Diag(castExpr->getLocStart(), diag::err_cast_selector_expr); + if (isa(castExpr)) { + Diag(castExpr->getLocStart(), diag::err_cast_selector_expr); + return ExprError(); + } // If either type is a pointer, the other type has to be either an // integer or a pointer. if (!castType->isArithmeticType()) { QualType castExprType = castExpr->getType(); if (!castExprType->isIntegralType(Context) && - castExprType->isArithmeticType()) - return Diag(castExpr->getLocStart(), - diag::err_cast_pointer_from_non_pointer_int) + castExprType->isArithmeticType()) { + Diag(castExpr->getLocStart(), + diag::err_cast_pointer_from_non_pointer_int) << castExprType << castExpr->getSourceRange(); + return ExprError(); + } } else if (!castExpr->getType()->isArithmeticType()) { - if (!castType->isIntegralType(Context) && castType->isArithmeticType()) - return Diag(castExpr->getLocStart(), - diag::err_cast_pointer_to_non_pointer_int) + if (!castType->isIntegralType(Context) && castType->isArithmeticType()) { + Diag(castExpr->getLocStart(), diag::err_cast_pointer_to_non_pointer_int) << castType << castExpr->getSourceRange(); + return ExprError(); + } } - Kind = PrepareScalarCast(*this, castExpr, castType); + castExprRes = Owned(castExpr); + Kind = PrepareScalarCast(*this, castExprRes, castType); + if (castExprRes.isInvalid()) + return ExprError(); + castExpr = castExprRes.take(); if (Kind == CK_BitCast) CheckCastAlign(castExpr, castType, TyR); - return false; + return Owned(castExpr); } bool Sema::CheckVectorCast(SourceRange R, QualType VectorTy, QualType Ty, @@ -5233,8 +5323,8 @@ bool Sema::CheckVectorCast(SourceRange R, QualType VectorTy, QualType Ty, return false; } -bool Sema::CheckExtVectorCast(SourceRange R, QualType DestTy, Expr *&CastExpr, - CastKind &Kind) { +ExprResult Sema::CheckExtVectorCast(SourceRange R, QualType DestTy, + Expr *CastExpr, CastKind &Kind) { assert(DestTy->isExtVectorType() && "Not an extended vector type!"); QualType SrcTy = CastExpr->getType(); @@ -5242,11 +5332,13 @@ bool Sema::CheckExtVectorCast(SourceRange R, QualType DestTy, Expr *&CastExpr, // If SrcTy is a VectorType, the total size must match to explicitly cast to // an ExtVectorType. if (SrcTy->isVectorType()) { - if (Context.getTypeSize(DestTy) != Context.getTypeSize(SrcTy)) - return Diag(R.getBegin(),diag::err_invalid_conversion_between_ext_vectors) + if (Context.getTypeSize(DestTy) != Context.getTypeSize(SrcTy)) { + Diag(R.getBegin(),diag::err_invalid_conversion_between_ext_vectors) << DestTy << SrcTy << R; + return ExprError(); + } Kind = CK_BitCast; - return false; + return Owned(CastExpr); } // All non-pointer scalars can be cast to ExtVector type. The appropriate @@ -5258,11 +5350,14 @@ bool Sema::CheckExtVectorCast(SourceRange R, QualType DestTy, Expr *&CastExpr, << DestTy << SrcTy << R; QualType DestElemTy = DestTy->getAs()->getElementType(); - ImpCastExprToType(CastExpr, DestElemTy, - PrepareScalarCast(*this, CastExpr, DestElemTy)); + ExprResult CastExprRes = Owned(CastExpr); + CastKind CK = PrepareScalarCast(*this, CastExprRes, DestElemTy); + if (CastExprRes.isInvalid()) + return ExprError(); + CastExpr = ImpCastExprToType(CastExprRes.take(), DestElemTy, CK).take(); Kind = CK_VectorSplat; - return false; + return Owned(CastExpr); } ExprResult @@ -5290,12 +5385,15 @@ Sema::BuildCStyleCastExpr(SourceLocation LParenLoc, TypeSourceInfo *Ty, CastKind Kind = CK_Invalid; ExprValueKind VK = VK_RValue; CXXCastPath BasePath; - if (CheckCastTypes(SourceRange(LParenLoc, RParenLoc), Ty->getType(), castExpr, - Kind, VK, BasePath)) + ExprResult CastResult = + CheckCastTypes(SourceRange(LParenLoc, RParenLoc), Ty->getType(), castExpr, + Kind, VK, BasePath); + if (CastResult.isInvalid()) return ExprError(); + castExpr = CastResult.take(); return Owned(CStyleCastExpr::Create(Context, - Ty->getType().getNonLValueExprType(Context), + Ty->getType().getNonLValueExprType(Context), VK, Kind, castExpr, &BasePath, Ty, LParenLoc, RParenLoc)); } @@ -5358,10 +5456,10 @@ Sema::ActOnCastOfParenListExpr(Scope *S, SourceLocation LParenLoc, // be replicated to all the components of the vector if (PE->getNumExprs() == 1) { QualType ElemTy = Ty->getAs()->getElementType(); - Expr *Literal = PE->getExpr(0); - ImpCastExprToType(Literal, ElemTy, - PrepareScalarCast(*this, Literal, ElemTy)); - return BuildCStyleCastExpr(LParenLoc, TInfo, RParenLoc, Literal); + ExprResult Literal = Owned(PE->getExpr(0)); + Literal = ImpCastExprToType(Literal.take(), ElemTy, + PrepareScalarCast(*this, Literal, ElemTy)); + return BuildCStyleCastExpr(LParenLoc, TInfo, RParenLoc, Literal.take()); } else if (PE->getNumExprs() < numElems) { Diag(PE->getExprLoc(), @@ -5447,18 +5545,17 @@ bool Sema::DiagnoseConditionalForNull(Expr *LHS, Expr *RHS, /// Note that lhs is not null here, even if this is the gnu "x ?: y" extension. /// In that case, lhs = cond. /// C99 6.5.15 -QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, +QualType Sema::CheckConditionalOperands(ExprResult &Cond, ExprResult &LHS, ExprResult &RHS, ExprValueKind &VK, ExprObjectKind &OK, SourceLocation QuestionLoc) { - // If either LHS or RHS are overloaded functions, try to resolve them. - ExprResult lhsResult = CheckPlaceholderExpr(LHS, QuestionLoc); + ExprResult lhsResult = CheckPlaceholderExpr(LHS.get(), QuestionLoc); if (!lhsResult.isUsable()) return QualType(); - LHS = lhsResult.take(); + LHS = move(lhsResult); - ExprResult rhsResult = CheckPlaceholderExpr(RHS, QuestionLoc); + ExprResult rhsResult = CheckPlaceholderExpr(RHS.get(), QuestionLoc); if (!rhsResult.isUsable()) return QualType(); - RHS = rhsResult.take(); + RHS = move(rhsResult); // C++ is sufficiently different to merit its own checker. if (getLangOptions().CPlusPlus) @@ -5467,12 +5564,19 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, VK = VK_RValue; OK = OK_Ordinary; - UsualUnaryConversions(Cond); - UsualUnaryConversions(LHS); - UsualUnaryConversions(RHS); - QualType CondTy = Cond->getType(); - QualType LHSTy = LHS->getType(); - QualType RHSTy = RHS->getType(); + Cond = UsualUnaryConversions(Cond.take()); + if (Cond.isInvalid()) + return QualType(); + LHS = UsualUnaryConversions(LHS.take()); + if (LHS.isInvalid()) + return QualType(); + RHS = UsualUnaryConversions(RHS.take()); + if (RHS.isInvalid()) + return QualType(); + + QualType CondTy = Cond.get()->getType(); + QualType LHSTy = LHS.get()->getType(); + QualType RHSTy = RHS.get()->getType(); // first, check the condition. if (!CondTy->isScalarType()) { // C99 6.5.15p2 @@ -5480,14 +5584,14 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // Throw an error if its not either. if (getLangOptions().OpenCL) { if (!CondTy->isVectorType()) { - Diag(Cond->getLocStart(), + Diag(Cond.get()->getLocStart(), diag::err_typecheck_cond_expect_scalar_or_vector) << CondTy; return QualType(); } } else { - Diag(Cond->getLocStart(), diag::err_typecheck_cond_expect_scalar) + Diag(Cond.get()->getLocStart(), diag::err_typecheck_cond_expect_scalar) << CondTy; return QualType(); } @@ -5503,25 +5607,27 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, if (getLangOptions().OpenCL && CondTy->isVectorType()) { // Both operands should be of scalar type. if (!LHSTy->isScalarType()) { - Diag(LHS->getLocStart(), diag::err_typecheck_cond_expect_scalar) + Diag(LHS.get()->getLocStart(), diag::err_typecheck_cond_expect_scalar) << CondTy; return QualType(); } if (!RHSTy->isScalarType()) { - Diag(RHS->getLocStart(), diag::err_typecheck_cond_expect_scalar) + Diag(RHS.get()->getLocStart(), diag::err_typecheck_cond_expect_scalar) << CondTy; return QualType(); } // Implicity convert these scalars to the type of the condition. - ImpCastExprToType(LHS, CondTy, CK_IntegralCast); - ImpCastExprToType(RHS, CondTy, CK_IntegralCast); + LHS = ImpCastExprToType(LHS.take(), CondTy, CK_IntegralCast); + RHS = ImpCastExprToType(RHS.take(), CondTy, CK_IntegralCast); } // If both operands have arithmetic type, do the usual arithmetic conversions // to find a common type: C99 6.5.15p3,5. if (LHSTy->isArithmeticType() && RHSTy->isArithmeticType()) { UsualArithmeticConversions(LHS, RHS); - return LHS->getType(); + if (LHS.isInvalid() || RHS.isInvalid()) + return QualType(); + return LHS.get()->getType(); } // If both operands are the same structure or union type, the result is that @@ -5539,32 +5645,34 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // The following || allows only one side to be void (a GCC-ism). if (LHSTy->isVoidType() || RHSTy->isVoidType()) { if (!LHSTy->isVoidType()) - Diag(RHS->getLocStart(), diag::ext_typecheck_cond_one_void) - << RHS->getSourceRange(); + Diag(RHS.get()->getLocStart(), diag::ext_typecheck_cond_one_void) + << RHS.get()->getSourceRange(); if (!RHSTy->isVoidType()) - Diag(LHS->getLocStart(), diag::ext_typecheck_cond_one_void) - << LHS->getSourceRange(); - ImpCastExprToType(LHS, Context.VoidTy, CK_ToVoid); - ImpCastExprToType(RHS, Context.VoidTy, CK_ToVoid); + Diag(LHS.get()->getLocStart(), diag::ext_typecheck_cond_one_void) + << LHS.get()->getSourceRange(); + LHS = ImpCastExprToType(LHS.take(), Context.VoidTy, CK_ToVoid); + RHS = ImpCastExprToType(RHS.take(), Context.VoidTy, CK_ToVoid); return Context.VoidTy; } // C99 6.5.15p6 - "if one operand is a null pointer constant, the result has // the type of the other operand." if ((LHSTy->isAnyPointerType() || LHSTy->isBlockPointerType()) && - RHS->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { + RHS.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { // promote the null to a pointer. - ImpCastExprToType(RHS, LHSTy, CK_NullToPointer); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_NullToPointer); return LHSTy; } if ((RHSTy->isAnyPointerType() || RHSTy->isBlockPointerType()) && - LHS->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { - ImpCastExprToType(LHS, RHSTy, CK_NullToPointer); + LHS.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { + LHS = ImpCastExprToType(LHS.take(), RHSTy, CK_NullToPointer); return RHSTy; } // All objective-c pointer type analysis is done here. QualType compositeType = FindCompositeObjCPointerType(LHS, RHS, QuestionLoc); + if (LHS.isInvalid() || RHS.isInvalid()) + return QualType(); if (!compositeType.isNull()) return compositeType; @@ -5574,12 +5682,12 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, if (!LHSTy->isBlockPointerType() || !RHSTy->isBlockPointerType()) { if (LHSTy->isVoidPointerType() || RHSTy->isVoidPointerType()) { QualType destType = Context.getPointerType(Context.VoidTy); - ImpCastExprToType(LHS, destType, CK_BitCast); - ImpCastExprToType(RHS, destType, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), destType, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), destType, CK_BitCast); return destType; } Diag(QuestionLoc, diag::err_typecheck_cond_incompatible_operands) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return QualType(); } // We have 2 block pointer types. @@ -5594,18 +5702,18 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, if (!Context.typesAreCompatible(lhptee.getUnqualifiedType(), rhptee.getUnqualifiedType())) { Diag(QuestionLoc, diag::warn_typecheck_cond_incompatible_pointers) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); // In this situation, we assume void* type. No especially good // reason, but this is what gcc does, and we do have to pick // to get a consistent AST. QualType incompatTy = Context.getPointerType(Context.VoidTy); - ImpCastExprToType(LHS, incompatTy, CK_BitCast); - ImpCastExprToType(RHS, incompatTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), incompatTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), incompatTy, CK_BitCast); return incompatTy; } // The block pointer types are compatible. - ImpCastExprToType(LHS, LHSTy, CK_BitCast); - ImpCastExprToType(RHS, LHSTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), LHSTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_BitCast); return LHSTy; } @@ -5622,9 +5730,9 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, = Context.getQualifiedType(lhptee, rhptee.getQualifiers()); QualType destType = Context.getPointerType(destPointee); // Add qualifiers if necessary. - ImpCastExprToType(LHS, destType, CK_NoOp); + LHS = ImpCastExprToType(LHS.take(), destType, CK_NoOp); // Promote to void*. - ImpCastExprToType(RHS, destType, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), destType, CK_BitCast); return destType; } if (rhptee->isVoidType() && lhptee->isIncompleteOrObjectType()) { @@ -5632,9 +5740,9 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, = Context.getQualifiedType(rhptee, lhptee.getQualifiers()); QualType destType = Context.getPointerType(destPointee); // Add qualifiers if necessary. - ImpCastExprToType(RHS, destType, CK_NoOp); + RHS = ImpCastExprToType(RHS.take(), destType, CK_NoOp); // Promote to void*. - ImpCastExprToType(LHS, destType, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), destType, CK_BitCast); return destType; } @@ -5645,13 +5753,13 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, if (!Context.typesAreCompatible(lhptee.getUnqualifiedType(), rhptee.getUnqualifiedType())) { Diag(QuestionLoc, diag::warn_typecheck_cond_incompatible_pointers) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); // In this situation, we assume void* type. No especially good // reason, but this is what gcc does, and we do have to pick // to get a consistent AST. QualType incompatTy = Context.getPointerType(Context.VoidTy); - ImpCastExprToType(LHS, incompatTy, CK_BitCast); - ImpCastExprToType(RHS, incompatTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), incompatTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), incompatTy, CK_BitCast); return incompatTy; } // The pointer types are compatible. @@ -5661,8 +5769,8 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // type. // FIXME: Need to calculate the composite type. // FIXME: Need to add qualifiers - ImpCastExprToType(LHS, LHSTy, CK_BitCast); - ImpCastExprToType(RHS, LHSTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), LHSTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_BitCast); return LHSTy; } @@ -5670,69 +5778,69 @@ QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // null pointers have been filtered out by this point. if (RHSTy->isPointerType() && LHSTy->isIntegerType()) { Diag(QuestionLoc, diag::warn_typecheck_cond_pointer_integer_mismatch) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); - ImpCastExprToType(LHS, RHSTy, CK_IntegralToPointer); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); + LHS = ImpCastExprToType(LHS.take(), RHSTy, CK_IntegralToPointer); return RHSTy; } if (LHSTy->isPointerType() && RHSTy->isIntegerType()) { Diag(QuestionLoc, diag::warn_typecheck_cond_pointer_integer_mismatch) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); - ImpCastExprToType(RHS, LHSTy, CK_IntegralToPointer); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_IntegralToPointer); return LHSTy; } // Emit a better diagnostic if one of the expressions is a null pointer // constant and the other is not a pointer type. In this case, the user most // likely forgot to take the address of the other expression. - if (DiagnoseConditionalForNull(LHS, RHS, QuestionLoc)) + if (DiagnoseConditionalForNull(LHS.get(), RHS.get(), QuestionLoc)) return QualType(); // Otherwise, the operands are not compatible. Diag(QuestionLoc, diag::err_typecheck_cond_incompatible_operands) - << LHSTy << RHSTy << LHS->getSourceRange() << RHS->getSourceRange(); + << LHSTy << RHSTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return QualType(); } /// FindCompositeObjCPointerType - Helper method to find composite type of /// two objective-c pointer types of the two input expressions. -QualType Sema::FindCompositeObjCPointerType(Expr *&LHS, Expr *&RHS, +QualType Sema::FindCompositeObjCPointerType(ExprResult &LHS, ExprResult &RHS, SourceLocation QuestionLoc) { - QualType LHSTy = LHS->getType(); - QualType RHSTy = RHS->getType(); + QualType LHSTy = LHS.get()->getType(); + QualType RHSTy = RHS.get()->getType(); // Handle things like Class and struct objc_class*. Here we case the result // to the pseudo-builtin, because that will be implicitly cast back to the // redefinition type if an attempt is made to access its fields. if (LHSTy->isObjCClassType() && (Context.hasSameType(RHSTy, Context.ObjCClassRedefinitionType))) { - ImpCastExprToType(RHS, LHSTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_BitCast); return LHSTy; } if (RHSTy->isObjCClassType() && (Context.hasSameType(LHSTy, Context.ObjCClassRedefinitionType))) { - ImpCastExprToType(LHS, RHSTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), RHSTy, CK_BitCast); return RHSTy; } // And the same for struct objc_object* / id if (LHSTy->isObjCIdType() && (Context.hasSameType(RHSTy, Context.ObjCIdRedefinitionType))) { - ImpCastExprToType(RHS, LHSTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_BitCast); return LHSTy; } if (RHSTy->isObjCIdType() && (Context.hasSameType(LHSTy, Context.ObjCIdRedefinitionType))) { - ImpCastExprToType(LHS, RHSTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), RHSTy, CK_BitCast); return RHSTy; } // And the same for struct objc_selector* / SEL if (Context.isObjCSelType(LHSTy) && (Context.hasSameType(RHSTy, Context.ObjCSelRedefinitionType))) { - ImpCastExprToType(RHS, LHSTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), LHSTy, CK_BitCast); return LHSTy; } if (Context.isObjCSelType(RHSTy) && (Context.hasSameType(LHSTy, Context.ObjCSelRedefinitionType))) { - ImpCastExprToType(LHS, RHSTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), RHSTy, CK_BitCast); return RHSTy; } // Check constraints for Objective-C object pointers types. @@ -5779,15 +5887,15 @@ QualType Sema::FindCompositeObjCPointerType(Expr *&LHS, Expr *&RHS, else { Diag(QuestionLoc, diag::ext_typecheck_cond_incompatible_operands) << LHSTy << RHSTy - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); QualType incompatTy = Context.getObjCIdType(); - ImpCastExprToType(LHS, incompatTy, CK_BitCast); - ImpCastExprToType(RHS, incompatTy, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), incompatTy, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), incompatTy, CK_BitCast); return incompatTy; } // The object pointer types are compatible. - ImpCastExprToType(LHS, compositeType, CK_BitCast); - ImpCastExprToType(RHS, compositeType, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), compositeType, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), compositeType, CK_BitCast); return compositeType; } // Check Objective-C object pointer types and 'void *' @@ -5798,9 +5906,9 @@ QualType Sema::FindCompositeObjCPointerType(Expr *&LHS, Expr *&RHS, = Context.getQualifiedType(lhptee, rhptee.getQualifiers()); QualType destType = Context.getPointerType(destPointee); // Add qualifiers if necessary. - ImpCastExprToType(LHS, destType, CK_NoOp); + LHS = ImpCastExprToType(LHS.take(), destType, CK_NoOp); // Promote to void*. - ImpCastExprToType(RHS, destType, CK_BitCast); + RHS = ImpCastExprToType(RHS.take(), destType, CK_BitCast); return destType; } if (LHSTy->isObjCObjectPointerType() && RHSTy->isVoidPointerType()) { @@ -5810,9 +5918,9 @@ QualType Sema::FindCompositeObjCPointerType(Expr *&LHS, Expr *&RHS, = Context.getQualifiedType(rhptee, lhptee.getQualifiers()); QualType destType = Context.getPointerType(destPointee); // Add qualifiers if necessary. - ImpCastExprToType(RHS, destType, CK_NoOp); + RHS = ImpCastExprToType(RHS.take(), destType, CK_NoOp); // Promote to void*. - ImpCastExprToType(LHS, destType, CK_BitCast); + LHS = ImpCastExprToType(LHS.take(), destType, CK_BitCast); return destType; } return QualType(); @@ -5840,7 +5948,10 @@ ExprResult Sema::ActOnConditionalOp(SourceLocation QuestionLoc, && commonExpr->isOrdinaryOrBitFieldObject() && RHSExpr->isOrdinaryOrBitFieldObject() && Context.hasSameType(commonExpr->getType(), RHSExpr->getType()))) { - UsualUnaryConversions(commonExpr); + ExprResult commonRes = UsualUnaryConversions(commonExpr); + if (commonRes.isInvalid()) + return ExprError(); + commonExpr = commonRes.take(); } opaqueValue = new (Context) OpaqueValueExpr(commonExpr->getExprLoc(), @@ -5852,19 +5963,21 @@ ExprResult Sema::ActOnConditionalOp(SourceLocation QuestionLoc, ExprValueKind VK = VK_RValue; ExprObjectKind OK = OK_Ordinary; - QualType result = CheckConditionalOperands(CondExpr, LHSExpr, RHSExpr, + ExprResult Cond = Owned(CondExpr), LHS = Owned(LHSExpr), RHS = Owned(RHSExpr); + QualType result = CheckConditionalOperands(Cond, LHS, RHS, VK, OK, QuestionLoc); - if (result.isNull()) + if (result.isNull() || Cond.isInvalid() || LHS.isInvalid() || + RHS.isInvalid()) return ExprError(); if (!commonExpr) - return Owned(new (Context) ConditionalOperator(CondExpr, QuestionLoc, - LHSExpr, ColonLoc, - RHSExpr, result, VK, OK)); + return Owned(new (Context) ConditionalOperator(Cond.take(), QuestionLoc, + LHS.take(), ColonLoc, + RHS.take(), result, VK, OK)); return Owned(new (Context) - BinaryConditionalOperator(commonExpr, opaqueValue, CondExpr, LHSExpr, - RHSExpr, QuestionLoc, ColonLoc, result, VK, OK)); + BinaryConditionalOperator(commonExpr, opaqueValue, Cond.take(), LHS.take(), + RHS.take(), QuestionLoc, ColonLoc, result, VK, OK)); } // checkPointerTypesForAssignment - This is a very tricky routine (despite @@ -6050,7 +6163,7 @@ Sema::CheckAssignmentConstraints(SourceLocation Loc, // adds casts to this they'll be wasted, but fortunately that doesn't // usually happen on valid code. OpaqueValueExpr rhs(Loc, rhsType, VK_RValue); - Expr *rhsPtr = &rhs; + ExprResult rhsPtr = &rhs; CastKind K = CK_Invalid; return CheckAssignmentConstraints(lhsType, rhsPtr, K); @@ -6074,9 +6187,9 @@ Sema::CheckAssignmentConstraints(SourceLocation Loc, /// /// Sets 'Kind' for any result kind except Incompatible. Sema::AssignConvertType -Sema::CheckAssignmentConstraints(QualType lhsType, Expr *&rhs, +Sema::CheckAssignmentConstraints(QualType lhsType, ExprResult &rhs, CastKind &Kind) { - QualType rhsType = rhs->getType(); + QualType rhsType = rhs.get()->getType(); // Get canonical types. We're not formatting these types, just comparing // them. @@ -6115,7 +6228,7 @@ Sema::CheckAssignmentConstraints(QualType lhsType, Expr *&rhs, QualType elType = cast(lhsType)->getElementType(); if (elType != rhsType) { Kind = PrepareScalarCast(*this, rhs, elType); - ImpCastExprToType(rhs, elType, Kind); + rhs = ImpCastExprToType(rhs.take(), elType, Kind); } Kind = CK_VectorSplat; return Compatible; @@ -6316,10 +6429,11 @@ Sema::CheckAssignmentConstraints(QualType lhsType, Expr *&rhs, /// \brief Constructs a transparent union from an expression that is /// used to initialize the transparent union. -static void ConstructTransparentUnion(ASTContext &C, Expr *&E, +static void ConstructTransparentUnion(Sema &S, ASTContext &C, ExprResult &EResult, QualType UnionType, FieldDecl *Field) { // Build an initializer list that designates the appropriate member // of the transparent union. + Expr *E = EResult.take(); InitListExpr *Initializer = new (C) InitListExpr(C, SourceLocation(), &E, 1, SourceLocation()); @@ -6329,13 +6443,14 @@ static void ConstructTransparentUnion(ASTContext &C, Expr *&E, // Build a compound literal constructing a value of the transparent // union type from this initializer list. TypeSourceInfo *unionTInfo = C.getTrivialTypeSourceInfo(UnionType); - E = new (C) CompoundLiteralExpr(SourceLocation(), unionTInfo, UnionType, - VK_RValue, Initializer, false); + EResult = S.Owned( + new (C) CompoundLiteralExpr(SourceLocation(), unionTInfo, UnionType, + VK_RValue, Initializer, false)); } Sema::AssignConvertType -Sema::CheckTransparentUnionArgumentConstraints(QualType ArgType, Expr *&rExpr) { - QualType FromType = rExpr->getType(); +Sema::CheckTransparentUnionArgumentConstraints(QualType ArgType, ExprResult &rExpr) { + QualType FromType = rExpr.get()->getType(); // If the ArgType is a Union type, we want to handle a potential // transparent_union GCC extension. @@ -6356,25 +6471,23 @@ Sema::CheckTransparentUnionArgumentConstraints(QualType ArgType, Expr *&rExpr) { // 2) null pointer constant if (FromType->isPointerType()) if (FromType->getAs()->getPointeeType()->isVoidType()) { - ImpCastExprToType(rExpr, it->getType(), CK_BitCast); + rExpr = ImpCastExprToType(rExpr.take(), it->getType(), CK_BitCast); InitField = *it; break; } - if (rExpr->isNullPointerConstant(Context, + if (rExpr.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { - ImpCastExprToType(rExpr, it->getType(), CK_NullToPointer); + rExpr = ImpCastExprToType(rExpr.take(), it->getType(), CK_NullToPointer); InitField = *it; break; } } - Expr *rhs = rExpr; CastKind Kind = CK_Invalid; - if (CheckAssignmentConstraints(it->getType(), rhs, Kind) + if (CheckAssignmentConstraints(it->getType(), rExpr, Kind) == Compatible) { - ImpCastExprToType(rhs, it->getType(), Kind); - rExpr = rhs; + rExpr = ImpCastExprToType(rExpr.take(), it->getType(), Kind); InitField = *it; break; } @@ -6383,20 +6496,23 @@ Sema::CheckTransparentUnionArgumentConstraints(QualType ArgType, Expr *&rExpr) { if (!InitField) return Incompatible; - ConstructTransparentUnion(Context, rExpr, ArgType, InitField); + ConstructTransparentUnion(*this, Context, rExpr, ArgType, InitField); return Compatible; } Sema::AssignConvertType -Sema::CheckSingleAssignmentConstraints(QualType lhsType, Expr *&rExpr) { +Sema::CheckSingleAssignmentConstraints(QualType lhsType, ExprResult &rExpr) { if (getLangOptions().CPlusPlus) { if (!lhsType->isRecordType()) { // C++ 5.17p3: If the left operand is not of class type, the // expression is implicitly converted (C++ 4) to the // cv-unqualified type of the left operand. - if (PerformImplicitConversion(rExpr, lhsType.getUnqualifiedType(), - AA_Assigning)) + ExprResult Res = PerformImplicitConversion(rExpr.get(), + lhsType.getUnqualifiedType(), + AA_Assigning); + if (Res.isInvalid()) return Incompatible; + rExpr = move(Res); return Compatible; } @@ -6409,9 +6525,9 @@ Sema::CheckSingleAssignmentConstraints(QualType lhsType, Expr *&rExpr) { if ((lhsType->isPointerType() || lhsType->isObjCObjectPointerType() || lhsType->isBlockPointerType()) - && rExpr->isNullPointerConstant(Context, + && rExpr.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { - ImpCastExprToType(rExpr, lhsType, CK_NullToPointer); + rExpr = ImpCastExprToType(rExpr.take(), lhsType, CK_NullToPointer); return Compatible; } @@ -6421,8 +6537,11 @@ Sema::CheckSingleAssignmentConstraints(QualType lhsType, Expr *&rExpr) { // expressions that suppress this implicit conversion (&, sizeof). // // Suppress this for references: C++ 8.5.3p5. - if (!lhsType->isReferenceType()) - DefaultFunctionArrayLvalueConversion(rExpr); + if (!lhsType->isReferenceType()) { + rExpr = DefaultFunctionArrayLvalueConversion(rExpr.take()); + if (rExpr.isInvalid()) + return Incompatible; + } CastKind Kind = CK_Invalid; Sema::AssignConvertType result = @@ -6434,25 +6553,25 @@ Sema::CheckSingleAssignmentConstraints(QualType lhsType, Expr *&rExpr) { // so that we can use references in built-in functions even in C. // The getNonReferenceType() call makes sure that the resulting expression // does not have reference type. - if (result != Incompatible && rExpr->getType() != lhsType) - ImpCastExprToType(rExpr, lhsType.getNonLValueExprType(Context), Kind); + if (result != Incompatible && rExpr.get()->getType() != lhsType) + rExpr = ImpCastExprToType(rExpr.take(), lhsType.getNonLValueExprType(Context), Kind); return result; } -QualType Sema::InvalidOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { +QualType Sema::InvalidOperands(SourceLocation Loc, ExprResult &lex, ExprResult &rex) { Diag(Loc, diag::err_typecheck_invalid_operands) - << lex->getType() << rex->getType() - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getType() << rex.get()->getType() + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } -QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { +QualType Sema::CheckVectorOperands(SourceLocation Loc, ExprResult &lex, ExprResult &rex) { // For conversion purposes, we ignore any qualifiers. // For example, "const float" and "float" are equivalent. QualType lhsType = - Context.getCanonicalType(lex->getType()).getUnqualifiedType(); + Context.getCanonicalType(lex.get()->getType()).getUnqualifiedType(); QualType rhsType = - Context.getCanonicalType(rex->getType()).getUnqualifiedType(); + Context.getCanonicalType(rex.get()->getType()).getUnqualifiedType(); // If the vector types are identical, return. if (lhsType == rhsType) @@ -6466,17 +6585,17 @@ QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { if (LV->getElementType() == RV->getElementType() && LV->getNumElements() == RV->getNumElements()) { if (lhsType->isExtVectorType()) { - ImpCastExprToType(rex, lhsType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lhsType, CK_BitCast); return lhsType; } - ImpCastExprToType(lex, rhsType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rhsType, CK_BitCast); return rhsType; } else if (Context.getTypeSize(lhsType) ==Context.getTypeSize(rhsType)){ // If we are allowing lax vector conversions, and LHS and RHS are both // vectors, the total size only needs to be the same. This is a // bitcast; no bits are changed but the result type is different. - ImpCastExprToType(rex, lhsType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lhsType, CK_BitCast); return lhsType; } } @@ -6486,7 +6605,7 @@ QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { // Handle the case of equivalent AltiVec and GCC vector types if (lhsType->isVectorType() && rhsType->isVectorType() && Context.areCompatibleVectorTypes(lhsType, rhsType)) { - ImpCastExprToType(lex, rhsType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rhsType, CK_BitCast); return rhsType; } @@ -6505,9 +6624,9 @@ QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { if (EltTy->isIntegralType(Context) && rhsType->isIntegralType(Context)) { int order = Context.getIntegerTypeOrder(EltTy, rhsType); if (order > 0) - ImpCastExprToType(rex, EltTy, CK_IntegralCast); + rex = ImpCastExprToType(rex.take(), EltTy, CK_IntegralCast); if (order >= 0) { - ImpCastExprToType(rex, lhsType, CK_VectorSplat); + rex = ImpCastExprToType(rex.take(), lhsType, CK_VectorSplat); if (swapped) std::swap(rex, lex); return lhsType; } @@ -6516,9 +6635,9 @@ QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { rhsType->isRealFloatingType()) { int order = Context.getFloatingTypeOrder(EltTy, rhsType); if (order > 0) - ImpCastExprToType(rex, EltTy, CK_FloatingCast); + rex = ImpCastExprToType(rex.take(), EltTy, CK_FloatingCast); if (order >= 0) { - ImpCastExprToType(rex, lhsType, CK_VectorSplat); + rex = ImpCastExprToType(rex.take(), lhsType, CK_VectorSplat); if (swapped) std::swap(rex, lex); return lhsType; } @@ -6527,72 +6646,78 @@ QualType Sema::CheckVectorOperands(SourceLocation Loc, Expr *&lex, Expr *&rex) { // Vectors of different size or scalar and non-ext-vector are errors. Diag(Loc, diag::err_typecheck_vector_not_convertable) - << lex->getType() << rex->getType() - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getType() << rex.get()->getType() + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } QualType Sema::CheckMultiplyDivideOperands( - Expr *&lex, Expr *&rex, SourceLocation Loc, bool isCompAssign, bool isDiv) { - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) + ExprResult &lex, ExprResult &rex, SourceLocation Loc, bool isCompAssign, bool isDiv) { + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) return CheckVectorOperands(Loc, lex, rex); QualType compType = UsualArithmeticConversions(lex, rex, isCompAssign); + if (lex.isInvalid() || rex.isInvalid()) + return QualType(); - if (!lex->getType()->isArithmeticType() || - !rex->getType()->isArithmeticType()) + if (!lex.get()->getType()->isArithmeticType() || + !rex.get()->getType()->isArithmeticType()) return InvalidOperands(Loc, lex, rex); // Check for division by zero. if (isDiv && - rex->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNotNull)) - DiagRuntimeBehavior(Loc, rex, PDiag(diag::warn_division_by_zero) - << rex->getSourceRange()); + rex.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNotNull)) + DiagRuntimeBehavior(Loc, rex.get(), PDiag(diag::warn_division_by_zero) + << rex.get()->getSourceRange()); return compType; } QualType Sema::CheckRemainderOperands( - Expr *&lex, Expr *&rex, SourceLocation Loc, bool isCompAssign) { - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) { - if (lex->getType()->hasIntegerRepresentation() && - rex->getType()->hasIntegerRepresentation()) + ExprResult &lex, ExprResult &rex, SourceLocation Loc, bool isCompAssign) { + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) { + if (lex.get()->getType()->hasIntegerRepresentation() && + rex.get()->getType()->hasIntegerRepresentation()) return CheckVectorOperands(Loc, lex, rex); return InvalidOperands(Loc, lex, rex); } QualType compType = UsualArithmeticConversions(lex, rex, isCompAssign); + if (lex.isInvalid() || rex.isInvalid()) + return QualType(); - if (!lex->getType()->isIntegerType() || !rex->getType()->isIntegerType()) + if (!lex.get()->getType()->isIntegerType() || !rex.get()->getType()->isIntegerType()) return InvalidOperands(Loc, lex, rex); // Check for remainder by zero. - if (rex->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNotNull)) - DiagRuntimeBehavior(Loc, rex, PDiag(diag::warn_remainder_by_zero) - << rex->getSourceRange()); + if (rex.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNotNull)) + DiagRuntimeBehavior(Loc, rex.get(), PDiag(diag::warn_remainder_by_zero) + << rex.get()->getSourceRange()); return compType; } QualType Sema::CheckAdditionOperands( // C99 6.5.6 - Expr *&lex, Expr *&rex, SourceLocation Loc, QualType* CompLHSTy) { - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) { + ExprResult &lex, ExprResult &rex, SourceLocation Loc, QualType* CompLHSTy) { + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) { QualType compType = CheckVectorOperands(Loc, lex, rex); if (CompLHSTy) *CompLHSTy = compType; return compType; } QualType compType = UsualArithmeticConversions(lex, rex, CompLHSTy); + if (lex.isInvalid() || rex.isInvalid()) + return QualType(); // handle the common case first (both operands are arithmetic). - if (lex->getType()->isArithmeticType() && - rex->getType()->isArithmeticType()) { + if (lex.get()->getType()->isArithmeticType() && + rex.get()->getType()->isArithmeticType()) { if (CompLHSTy) *CompLHSTy = compType; return compType; } // Put any potential pointer into PExp - Expr* PExp = lex, *IExp = rex; + Expr* PExp = lex.get(), *IExp = rex.get(); if (IExp->getType()->isAnyPointerType()) std::swap(PExp, IExp); @@ -6605,23 +6730,23 @@ QualType Sema::CheckAdditionOperands( // C99 6.5.6 if (PointeeTy->isVoidType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_void_type) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } // GNU extension: arithmetic on pointer to void Diag(Loc, diag::ext_gnu_void_ptr) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } else if (PointeeTy->isFunctionType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_function_type) - << lex->getType() << lex->getSourceRange(); + << lex.get()->getType() << lex.get()->getSourceRange(); return QualType(); } // GNU extension: arithmetic on pointer to function Diag(Loc, diag::ext_gnu_ptr_func_arith) - << lex->getType() << lex->getSourceRange(); + << lex.get()->getType() << lex.get()->getSourceRange(); } else { // Check if we require a complete type. if (((PExp->getType()->isPointerType() && @@ -6641,9 +6766,9 @@ QualType Sema::CheckAdditionOperands( // C99 6.5.6 } if (CompLHSTy) { - QualType LHSTy = Context.isPromotableBitField(lex); + QualType LHSTy = Context.isPromotableBitField(lex.get()); if (LHSTy.isNull()) { - LHSTy = lex->getType(); + LHSTy = lex.get()->getType(); if (LHSTy->isPromotableIntegerType()) LHSTy = Context.getPromotedIntegerType(LHSTy); } @@ -6657,28 +6782,30 @@ QualType Sema::CheckAdditionOperands( // C99 6.5.6 } // C99 6.5.6 -QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, +QualType Sema::CheckSubtractionOperands(ExprResult &lex, ExprResult &rex, SourceLocation Loc, QualType* CompLHSTy) { - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) { + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) { QualType compType = CheckVectorOperands(Loc, lex, rex); if (CompLHSTy) *CompLHSTy = compType; return compType; } QualType compType = UsualArithmeticConversions(lex, rex, CompLHSTy); + if (lex.isInvalid() || rex.isInvalid()) + return QualType(); // Enforce type constraints: C99 6.5.6p3. // Handle the common case first (both operands are arithmetic). - if (lex->getType()->isArithmeticType() - && rex->getType()->isArithmeticType()) { + if (lex.get()->getType()->isArithmeticType() && + rex.get()->getType()->isArithmeticType()) { if (CompLHSTy) *CompLHSTy = compType; return compType; } // Either ptr - int or ptr - ptr. - if (lex->getType()->isAnyPointerType()) { - QualType lpointee = lex->getType()->getPointeeType(); + if (lex.get()->getType()->isAnyPointerType()) { + QualType lpointee = lex.get()->getType()->getPointeeType(); // The LHS must be an completely-defined object type. @@ -6687,7 +6814,7 @@ QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, if (lpointee->isVoidType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_void_type) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } @@ -6696,42 +6823,42 @@ QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, } else if (lpointee->isFunctionType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_function_type) - << lex->getType() << lex->getSourceRange(); + << lex.get()->getType() << lex.get()->getSourceRange(); return QualType(); } // GNU C extension: arithmetic on pointer to function - ComplainAboutFunc = lex; + ComplainAboutFunc = lex.get(); } else if (!lpointee->isDependentType() && RequireCompleteType(Loc, lpointee, PDiag(diag::err_typecheck_sub_ptr_object) - << lex->getSourceRange() - << lex->getType())) + << lex.get()->getSourceRange() + << lex.get()->getType())) return QualType(); // Diagnose bad cases where we step over interface counts. if (lpointee->isObjCObjectType() && LangOpts.ObjCNonFragileABI) { Diag(Loc, diag::err_arithmetic_nonfragile_interface) - << lpointee << lex->getSourceRange(); + << lpointee << lex.get()->getSourceRange(); return QualType(); } // The result type of a pointer-int computation is the pointer type. - if (rex->getType()->isIntegerType()) { + if (rex.get()->getType()->isIntegerType()) { if (ComplainAboutVoid) Diag(Loc, diag::ext_gnu_void_ptr) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); if (ComplainAboutFunc) Diag(Loc, diag::ext_gnu_ptr_func_arith) << ComplainAboutFunc->getType() << ComplainAboutFunc->getSourceRange(); - if (CompLHSTy) *CompLHSTy = lex->getType(); - return lex->getType(); + if (CompLHSTy) *CompLHSTy = lex.get()->getType(); + return lex.get()->getType(); } // Handle pointer-pointer subtractions. - if (const PointerType *RHSPTy = rex->getType()->getAs()) { + if (const PointerType *RHSPTy = rex.get()->getType()->getAs()) { QualType rpointee = RHSPTy->getPointeeType(); // RHS must be a completely-type object type. @@ -6739,7 +6866,7 @@ QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, if (rpointee->isVoidType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_void_type) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } @@ -6747,26 +6874,26 @@ QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, } else if (rpointee->isFunctionType()) { if (getLangOptions().CPlusPlus) { Diag(Loc, diag::err_typecheck_pointer_arith_function_type) - << rex->getType() << rex->getSourceRange(); + << rex.get()->getType() << rex.get()->getSourceRange(); return QualType(); } // GNU extension: arithmetic on pointer to function if (!ComplainAboutFunc) - ComplainAboutFunc = rex; + ComplainAboutFunc = rex.get(); } else if (!rpointee->isDependentType() && RequireCompleteType(Loc, rpointee, PDiag(diag::err_typecheck_sub_ptr_object) - << rex->getSourceRange() - << rex->getType())) + << rex.get()->getSourceRange() + << rex.get()->getType())) return QualType(); if (getLangOptions().CPlusPlus) { // Pointee types must be the same: C++ [expr.add] if (!Context.hasSameUnqualifiedType(lpointee, rpointee)) { Diag(Loc, diag::err_typecheck_sub_ptr_compatible) - << lex->getType() << rex->getType() - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getType() << rex.get()->getType() + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } } else { @@ -6775,21 +6902,21 @@ QualType Sema::CheckSubtractionOperands(Expr *&lex, Expr *&rex, Context.getCanonicalType(lpointee).getUnqualifiedType(), Context.getCanonicalType(rpointee).getUnqualifiedType())) { Diag(Loc, diag::err_typecheck_sub_ptr_compatible) - << lex->getType() << rex->getType() - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getType() << rex.get()->getType() + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } } if (ComplainAboutVoid) Diag(Loc, diag::ext_gnu_void_ptr) - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); if (ComplainAboutFunc) Diag(Loc, diag::ext_gnu_ptr_func_arith) << ComplainAboutFunc->getType() << ComplainAboutFunc->getSourceRange(); - if (CompLHSTy) *CompLHSTy = lex->getType(); + if (CompLHSTy) *CompLHSTy = lex.get()->getType(); return Context.getPointerDiffType(); } } @@ -6803,26 +6930,26 @@ static bool isScopedEnumerationType(QualType T) { return false; } -static void DiagnoseBadShiftValues(Sema& S, Expr *&lex, Expr *&rex, +static void DiagnoseBadShiftValues(Sema& S, ExprResult &lex, ExprResult &rex, SourceLocation Loc, unsigned Opc, QualType LHSTy) { llvm::APSInt Right; // Check right/shifter operand - if (rex->isValueDependent() || !rex->isIntegerConstantExpr(Right, S.Context)) + if (rex.get()->isValueDependent() || !rex.get()->isIntegerConstantExpr(Right, S.Context)) return; if (Right.isNegative()) { - S.DiagRuntimeBehavior(Loc, rex, + S.DiagRuntimeBehavior(Loc, rex.get(), S.PDiag(diag::warn_shift_negative) - << rex->getSourceRange()); + << rex.get()->getSourceRange()); return; } llvm::APInt LeftBits(Right.getBitWidth(), - S.Context.getTypeSize(lex->getType())); + S.Context.getTypeSize(lex.get()->getType())); if (Right.uge(LeftBits)) { - S.DiagRuntimeBehavior(Loc, rex, + S.DiagRuntimeBehavior(Loc, rex.get(), S.PDiag(diag::warn_shift_gt_typewidth) - << rex->getSourceRange()); + << rex.get()->getSourceRange()); return; } if (Opc != BO_Shl) @@ -6833,7 +6960,7 @@ static void DiagnoseBadShiftValues(Sema& S, Expr *&lex, Expr *&rex, // integers have defined behavior modulo one more than the maximum value // representable in the result type, so never warn for those. llvm::APSInt Left; - if (lex->isValueDependent() || !lex->isIntegerConstantExpr(Left, S.Context) || + if (lex.get()->isValueDependent() || !lex.get()->isIntegerConstantExpr(Left, S.Context) || LHSTy->hasUnsignedIntegerRepresentation()) return; llvm::APInt ResultBits = @@ -6850,32 +6977,32 @@ static void DiagnoseBadShiftValues(Sema& S, Expr *&lex, Expr *&rex, if (LeftBits == ResultBits - 1) { S.Diag(Loc, diag::warn_shift_result_overrides_sign_bit) << Result.toString(10) << LHSTy - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return; } S.Diag(Loc, diag::warn_shift_result_gt_typewidth) << Result.toString(10) << Result.getMinSignedBits() << LHSTy - << Left.getBitWidth() << lex->getSourceRange() << rex->getSourceRange(); + << Left.getBitWidth() << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } // C99 6.5.7 -QualType Sema::CheckShiftOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, +QualType Sema::CheckShiftOperands(ExprResult &lex, ExprResult &rex, SourceLocation Loc, unsigned Opc, bool isCompAssign) { // C99 6.5.7p2: Each of the operands shall have integer type. - if (!lex->getType()->hasIntegerRepresentation() || - !rex->getType()->hasIntegerRepresentation()) + if (!lex.get()->getType()->hasIntegerRepresentation() || + !rex.get()->getType()->hasIntegerRepresentation()) return InvalidOperands(Loc, lex, rex); // C++0x: Don't allow scoped enums. FIXME: Use something better than // hasIntegerRepresentation() above instead of this. - if (isScopedEnumerationType(lex->getType()) || - isScopedEnumerationType(rex->getType())) { + if (isScopedEnumerationType(lex.get()->getType()) || + isScopedEnumerationType(rex.get()->getType())) { return InvalidOperands(Loc, lex, rex); } // Vector shifts promote their scalar inputs to vector type. - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) return CheckVectorOperands(Loc, lex, rex); // Shifts don't perform usual arithmetic conversions, they just do integer @@ -6883,13 +7010,17 @@ QualType Sema::CheckShiftOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, // For the LHS, do usual unary conversions, but then reset them away // if this is a compound assignment. - Expr *old_lex = lex; - UsualUnaryConversions(lex); - QualType LHSTy = lex->getType(); + ExprResult old_lex = lex; + lex = UsualUnaryConversions(lex.take()); + if (lex.isInvalid()) + return QualType(); + QualType LHSTy = lex.get()->getType(); if (isCompAssign) lex = old_lex; // The RHS is simpler. - UsualUnaryConversions(rex); + rex = UsualUnaryConversions(rex.take()); + if (rex.isInvalid()) + return QualType(); // Sanity-check shift operands DiagnoseBadShiftValues(*this, lex, rex, Loc, Opc, LHSTy); @@ -6909,19 +7040,19 @@ static bool IsWithinTemplateSpecialization(Decl *D) { } // C99 6.5.8, C++ [expr.rel] -QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, +QualType Sema::CheckCompareOperands(ExprResult &lex, ExprResult &rex, SourceLocation Loc, unsigned OpaqueOpc, bool isRelational) { BinaryOperatorKind Opc = (BinaryOperatorKind) OpaqueOpc; // Handle vector comparisons separately. - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) return CheckVectorCompareOperands(lex, rex, Loc, isRelational); - QualType lType = lex->getType(); - QualType rType = rex->getType(); + QualType lType = lex.get()->getType(); + QualType rType = rex.get()->getType(); - Expr *LHSStripped = lex->IgnoreParenImpCasts(); - Expr *RHSStripped = rex->IgnoreParenImpCasts(); + Expr *LHSStripped = lex.get()->IgnoreParenImpCasts(); + Expr *RHSStripped = rex.get()->IgnoreParenImpCasts(); QualType LHSStrippedType = LHSStripped->getType(); QualType RHSStrippedType = RHSStripped->getType(); @@ -6935,15 +7066,15 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, !Context.hasSameUnqualifiedType(LHSStrippedType, RHSStrippedType)) { Diag(Loc, diag::warn_comparison_of_mixed_enum_types) << LHSStrippedType << RHSStrippedType - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } } } if (!lType->hasFloatingRepresentation() && !(lType->isBlockPointerType() && isRelational) && - !lex->getLocStart().isMacroID() && - !rex->getLocStart().isMacroID()) { + !lex.get()->getLocStart().isMacroID() && + !rex.get()->getLocStart().isMacroID()) { // For non-floating point types, check for self-comparisons of the form // x == x, x != x, x < x, etc. These always evaluate to a constant, and // often indicate logic errors in the program. @@ -6999,13 +7130,13 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if ((isa(LHSStripped) || isa(LHSStripped)) && !RHSStripped->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { - literalString = lex; + literalString = lex.get(); literalStringStripped = LHSStripped; } else if ((isa(RHSStripped) || isa(RHSStripped)) && !LHSStripped->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { - literalString = rex; + literalString = rex.get(); literalStringStripped = RHSStripped; } @@ -7029,15 +7160,23 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, } // C99 6.5.8p3 / C99 6.5.9p4 - if (lex->getType()->isArithmeticType() && rex->getType()->isArithmeticType()) + if (lex.get()->getType()->isArithmeticType() && rex.get()->getType()->isArithmeticType()) { UsualArithmeticConversions(lex, rex); + if (lex.isInvalid() || rex.isInvalid()) + return QualType(); + } else { - UsualUnaryConversions(lex); - UsualUnaryConversions(rex); + lex = UsualUnaryConversions(lex.take()); + if (lex.isInvalid()) + return QualType(); + + rex = UsualUnaryConversions(rex.take()); + if (rex.isInvalid()) + return QualType(); } - lType = lex->getType(); - rType = rex->getType(); + lType = lex.get()->getType(); + rType = rex.get()->getType(); // The result of comparisons is 'bool' in C++, 'int' in C. QualType ResultTy = Context.getLogicalOperationType(); @@ -7048,15 +7187,15 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, } else { // Check for comparisons of floating point operands using != and ==. if (lType->hasFloatingRepresentation()) - CheckFloatComparison(Loc,lex,rex); + CheckFloatComparison(Loc, lex.get(), rex.get()); if (lType->isArithmeticType() && rType->isArithmeticType()) return ResultTy; } - bool LHSIsNull = lex->isNullPointerConstant(Context, + bool LHSIsNull = lex.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull); - bool RHSIsNull = rex->isNullPointerConstant(Context, + bool RHSIsNull = rex.get()->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull); // All of the following pointer-related warnings are GCC extensions, except @@ -7082,12 +7221,12 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, isSFINAEContext()? diag::err_typecheck_comparison_of_fptr_to_void : diag::ext_typecheck_comparison_of_fptr_to_void) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); if (isSFINAEContext()) return QualType(); - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); return ResultTy; } } @@ -7105,17 +7244,17 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, isSFINAEContext()? 0 : &NonStandardCompositeType); if (T.isNull()) { Diag(Loc, diag::err_typecheck_comparison_of_distinct_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } else if (NonStandardCompositeType) { Diag(Loc, diag::ext_typecheck_comparison_of_distinct_pointers_nonstandard) << lType << rType << T - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } - ImpCastExprToType(lex, T, CK_BitCast); - ImpCastExprToType(rex, T, CK_BitCast); + lex = ImpCastExprToType(lex.take(), T, CK_BitCast); + rex = ImpCastExprToType(rex.take(), T, CK_BitCast); return ResultTy; } // C99 6.5.9p2 and C99 6.5.8p2 @@ -7124,7 +7263,7 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, // Valid unless a relational comparison of function pointers if (isRelational && LCanPointeeTy->isFunctionType()) { Diag(Loc, diag::ext_typecheck_ordered_comparison_of_function_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } } else if (!isRelational && (LCanPointeeTy->isVoidType() || RCanPointeeTy->isVoidType())) { @@ -7132,18 +7271,18 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if ((LCanPointeeTy->isFunctionType() || RCanPointeeTy->isFunctionType()) && !LHSIsNull && !RHSIsNull) { Diag(Loc, diag::ext_typecheck_comparison_of_fptr_to_void) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } } else { // Invalid Diag(Loc, diag::ext_typecheck_comparison_of_distinct_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } if (LCanPointeeTy != RCanPointeeTy) { if (LHSIsNull && !RHSIsNull) - ImpCastExprToType(lex, rType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rType, CK_BitCast); else - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); } return ResultTy; } @@ -7158,7 +7297,7 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if (RHSIsNull && ((lType->isPointerType() || lType->isNullPtrType()) || (!isRelational && lType->isMemberPointerType()))) { - ImpCastExprToType(rex, lType, + rex = ImpCastExprToType(rex.take(), lType, lType->isMemberPointerType() ? CK_NullToMemberPointer : CK_NullToPointer); @@ -7167,7 +7306,7 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if (LHSIsNull && ((rType->isPointerType() || rType->isNullPtrType()) || (!isRelational && rType->isMemberPointerType()))) { - ImpCastExprToType(lex, rType, + lex = ImpCastExprToType(lex.take(), rType, rType->isMemberPointerType() ? CK_NullToMemberPointer : CK_NullToPointer); @@ -7192,24 +7331,24 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, isSFINAEContext()? 0 : &NonStandardCompositeType); if (T.isNull()) { Diag(Loc, diag::err_typecheck_comparison_of_distinct_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); return QualType(); } else if (NonStandardCompositeType) { Diag(Loc, diag::ext_typecheck_comparison_of_distinct_pointers_nonstandard) << lType << rType << T - << lex->getSourceRange() << rex->getSourceRange(); + << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } - ImpCastExprToType(lex, T, CK_BitCast); - ImpCastExprToType(rex, T, CK_BitCast); + lex = ImpCastExprToType(lex.take(), T, CK_BitCast); + rex = ImpCastExprToType(rex.take(), T, CK_BitCast); return ResultTy; } // Handle scoped enumeration types specifically, since they don't promote // to integers. - if (lex->getType()->isEnumeralType() && - Context.hasSameUnqualifiedType(lex->getType(), rex->getType())) + if (lex.get()->getType()->isEnumeralType() && + Context.hasSameUnqualifiedType(lex.get()->getType(), rex.get()->getType())) return ResultTy; } @@ -7221,11 +7360,12 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if (!LHSIsNull && !RHSIsNull && !Context.typesAreCompatible(lpointee, rpointee)) { Diag(Loc, diag::err_typecheck_comparison_of_distinct_blocks) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); return ResultTy; } + // Allow block pointers to be compared with null pointer constants. if (!isRelational && ((lType->isBlockPointerType() && rType->isPointerType()) @@ -7236,12 +7376,12 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, || (lType->isPointerType() && lType->castAs() ->getPointeeType()->isVoidType()))) Diag(Loc, diag::err_typecheck_comparison_of_distinct_blocks) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } if (LHSIsNull && !RHSIsNull) - ImpCastExprToType(lex, rType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rType, CK_BitCast); else - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); return ResultTy; } @@ -7255,22 +7395,22 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if (!LPtrToVoid && !RPtrToVoid && !Context.typesAreCompatible(lType, rType)) { Diag(Loc, diag::ext_typecheck_comparison_of_distinct_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); } if (LHSIsNull && !RHSIsNull) - ImpCastExprToType(lex, rType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rType, CK_BitCast); else - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); return ResultTy; } if (lType->isObjCObjectPointerType() && rType->isObjCObjectPointerType()) { if (!Context.areComparableObjCPointerTypes(lType, rType)) Diag(Loc, diag::ext_typecheck_comparison_of_distinct_pointers) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); if (LHSIsNull && !RHSIsNull) - ImpCastExprToType(lex, rType, CK_BitCast); + lex = ImpCastExprToType(lex.take(), rType, CK_BitCast); else - ImpCastExprToType(rex, lType, CK_BitCast); + rex = ImpCastExprToType(rex.take(), lType, CK_BitCast); return ResultTy; } } @@ -7292,16 +7432,16 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, if (DiagID) { Diag(Loc, DiagID) - << lType << rType << lex->getSourceRange() << rex->getSourceRange(); + << lType << rType << lex.get()->getSourceRange() << rex.get()->getSourceRange(); if (isError) return QualType(); } if (lType->isIntegerType()) - ImpCastExprToType(lex, rType, + lex = ImpCastExprToType(lex.take(), rType, LHSIsNull ? CK_NullToPointer : CK_IntegralToPointer); else - ImpCastExprToType(rex, lType, + rex = ImpCastExprToType(rex.take(), lType, RHSIsNull ? CK_NullToPointer : CK_IntegralToPointer); return ResultTy; } @@ -7309,12 +7449,12 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, // Handle block pointers. if (!isRelational && RHSIsNull && lType->isBlockPointerType() && rType->isIntegerType()) { - ImpCastExprToType(rex, lType, CK_NullToPointer); + rex = ImpCastExprToType(rex.take(), lType, CK_NullToPointer); return ResultTy; } if (!isRelational && LHSIsNull && lType->isIntegerType() && rType->isBlockPointerType()) { - ImpCastExprToType(lex, rType, CK_NullToPointer); + lex = ImpCastExprToType(lex.take(), rType, CK_NullToPointer); return ResultTy; } @@ -7325,7 +7465,7 @@ QualType Sema::CheckCompareOperands(Expr *&lex, Expr *&rex, SourceLocation Loc, /// operates on extended vector types. Instead of producing an IntTy result, /// like a scalar comparison, a vector comparison produces a vector of integer /// types. -QualType Sema::CheckVectorCompareOperands(Expr *&lex, Expr *&rex, +QualType Sema::CheckVectorCompareOperands(ExprResult &lex, ExprResult &rex, SourceLocation Loc, bool isRelational) { // Check to make sure we're operating on vectors of the same type and width, @@ -7334,8 +7474,8 @@ QualType Sema::CheckVectorCompareOperands(Expr *&lex, Expr *&rex, if (vType.isNull()) return vType; - QualType lType = lex->getType(); - QualType rType = rex->getType(); + QualType lType = lex.get()->getType(); + QualType rType = rex.get()->getType(); // If AltiVec, the comparison results in a numeric type, i.e. // bool for C++, int for C @@ -7346,8 +7486,8 @@ QualType Sema::CheckVectorCompareOperands(Expr *&lex, Expr *&rex, // x == x, x != x, x < x, etc. These always evaluate to a constant, and // often indicate logic errors in the program. if (!lType->hasFloatingRepresentation()) { - if (DeclRefExpr* DRL = dyn_cast(lex->IgnoreParens())) - if (DeclRefExpr* DRR = dyn_cast(rex->IgnoreParens())) + if (DeclRefExpr* DRL = dyn_cast(lex.get()->IgnoreParens())) + if (DeclRefExpr* DRR = dyn_cast(rex.get()->IgnoreParens())) if (DRL->getDecl() == DRR->getDecl()) DiagRuntimeBehavior(Loc, 0, PDiag(diag::warn_comparison_always) @@ -7359,7 +7499,7 @@ QualType Sema::CheckVectorCompareOperands(Expr *&lex, Expr *&rex, // Check for comparisons of floating point operands using != and ==. if (!isRelational && lType->hasFloatingRepresentation()) { assert (rType->hasFloatingRepresentation()); - CheckFloatComparison(Loc,lex,rex); + CheckFloatComparison(Loc, lex.get(), rex.get()); } // Return the type for the comparison, which is the same as vector type for @@ -7381,51 +7521,61 @@ QualType Sema::CheckVectorCompareOperands(Expr *&lex, Expr *&rex, } inline QualType Sema::CheckBitwiseOperands( - Expr *&lex, Expr *&rex, SourceLocation Loc, bool isCompAssign) { - if (lex->getType()->isVectorType() || rex->getType()->isVectorType()) { - if (lex->getType()->hasIntegerRepresentation() && - rex->getType()->hasIntegerRepresentation()) + ExprResult &lex, ExprResult &rex, SourceLocation Loc, bool isCompAssign) { + if (lex.get()->getType()->isVectorType() || rex.get()->getType()->isVectorType()) { + if (lex.get()->getType()->hasIntegerRepresentation() && + rex.get()->getType()->hasIntegerRepresentation()) return CheckVectorOperands(Loc, lex, rex); return InvalidOperands(Loc, lex, rex); } - QualType compType = UsualArithmeticConversions(lex, rex, isCompAssign); + ExprResult lexResult = Owned(lex), rexResult = Owned(rex); + QualType compType = UsualArithmeticConversions(lexResult, rexResult, isCompAssign); + if (lexResult.isInvalid() || rexResult.isInvalid()) + return QualType(); + lex = lexResult.take(); + rex = rexResult.take(); - if (lex->getType()->isIntegralOrUnscopedEnumerationType() && - rex->getType()->isIntegralOrUnscopedEnumerationType()) + if (lex.get()->getType()->isIntegralOrUnscopedEnumerationType() && + rex.get()->getType()->isIntegralOrUnscopedEnumerationType()) return compType; return InvalidOperands(Loc, lex, rex); } inline QualType Sema::CheckLogicalOperands( // C99 6.5.[13,14] - Expr *&lex, Expr *&rex, SourceLocation Loc, unsigned Opc) { + ExprResult &lex, ExprResult &rex, SourceLocation Loc, unsigned Opc) { // Diagnose cases where the user write a logical and/or but probably meant a // bitwise one. We do this when the LHS is a non-bool integer and the RHS // is a constant. - if (lex->getType()->isIntegerType() && !lex->getType()->isBooleanType() && - rex->getType()->isIntegerType() && !rex->isValueDependent() && + if (lex.get()->getType()->isIntegerType() && !lex.get()->getType()->isBooleanType() && + rex.get()->getType()->isIntegerType() && !rex.get()->isValueDependent() && // Don't warn in macros. !Loc.isMacroID()) { // If the RHS can be constant folded, and if it constant folds to something // that isn't 0 or 1 (which indicate a potential logical operation that // happened to fold to true/false) then warn. Expr::EvalResult Result; - if (rex->Evaluate(Result, Context) && !Result.HasSideEffects && + if (rex.get()->Evaluate(Result, Context) && !Result.HasSideEffects && Result.Val.getInt() != 0 && Result.Val.getInt() != 1) { Diag(Loc, diag::warn_logical_instead_of_bitwise) - << rex->getSourceRange() + << rex.get()->getSourceRange() << (Opc == BO_LAnd ? "&&" : "||") << (Opc == BO_LAnd ? "&" : "|"); } } if (!Context.getLangOptions().CPlusPlus) { - UsualUnaryConversions(lex); - UsualUnaryConversions(rex); + lex = UsualUnaryConversions(lex.take()); + if (lex.isInvalid()) + return QualType(); + + rex = UsualUnaryConversions(rex.take()); + if (rex.isInvalid()) + return QualType(); - if (!lex->getType()->isScalarType() || !rex->getType()->isScalarType()) + if (!lex.get()->getType()->isScalarType() || !rex.get()->getType()->isScalarType()) return InvalidOperands(Loc, lex, rex); return Context.IntTy; @@ -7437,9 +7587,15 @@ inline QualType Sema::CheckLogicalOperands( // C99 6.5.[13,14] // C++ [expr.log.and]p1 // C++ [expr.log.or]p1 // The operands are both contextually converted to type bool. - if (PerformContextuallyConvertToBool(lex) || - PerformContextuallyConvertToBool(rex)) + ExprResult lexRes = PerformContextuallyConvertToBool(lex.get()); + if (lexRes.isInvalid()) + return InvalidOperands(Loc, lex, rex); + lex = move(lexRes); + + ExprResult rexRes = PerformContextuallyConvertToBool(rex.get()); + if (rexRes.isInvalid()) return InvalidOperands(Loc, lex, rex); + rex = move(rexRes); // C++ [expr.log.and]p2 // C++ [expr.log.or]p2 @@ -7574,7 +7730,7 @@ static bool CheckForModifiableLvalue(Expr *E, SourceLocation Loc, Sema &S) { // C99 6.5.16.1 -QualType Sema::CheckAssignmentOperands(Expr *LHS, Expr *&RHS, +QualType Sema::CheckAssignmentOperands(Expr *LHS, ExprResult &RHS, SourceLocation Loc, QualType CompoundType) { // Verify that LHS is a modifiable lvalue, and emit error if not. @@ -7582,14 +7738,21 @@ QualType Sema::CheckAssignmentOperands(Expr *LHS, Expr *&RHS, return QualType(); QualType LHSType = LHS->getType(); - QualType RHSType = CompoundType.isNull() ? RHS->getType() : CompoundType; + QualType RHSType = CompoundType.isNull() ? RHS.get()->getType() : CompoundType; AssignConvertType ConvTy; if (CompoundType.isNull()) { QualType LHSTy(LHSType); // Simple assignment "x = y". - if (LHS->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForLValue(LHS, RHS, LHSTy); + if (LHS->getObjectKind() == OK_ObjCProperty) { + ExprResult LHSResult = Owned(LHS); + ConvertPropertyForLValue(LHSResult, RHS, LHSTy); + if (LHSResult.isInvalid()) + return QualType(); + LHS = LHSResult.take(); + } ConvTy = CheckSingleAssignmentConstraints(LHSTy, RHS); + if (RHS.isInvalid()) + return QualType(); // Special case of NSObject attributes on c-style pointer types. if (ConvTy == IncompatiblePointer && ((Context.isObjCNSObjectType(LHSType) && @@ -7607,7 +7770,7 @@ QualType Sema::CheckAssignmentOperands(Expr *LHS, Expr *&RHS, // If the RHS is a unary plus or minus, check to see if they = and + are // right next to each other. If so, the user may have typo'd "x =+ 4" // instead of "x += 4". - Expr *RHSCheck = RHS; + Expr *RHSCheck = RHS.get(); if (ImplicitCastExpr *ICE = dyn_cast(RHSCheck)) RHSCheck = ICE->getSubExpr(); if (UnaryOperator *UO = dyn_cast(RHSCheck)) { @@ -7631,7 +7794,7 @@ QualType Sema::CheckAssignmentOperands(Expr *LHS, Expr *&RHS, } if (DiagnoseAssignmentResult(ConvTy, Loc, LHSType, RHSType, - RHS, AA_Assigning)) + RHS.get(), AA_Assigning)) return QualType(); @@ -7668,18 +7831,14 @@ QualType Sema::CheckAssignmentOperands(Expr *LHS, Expr *&RHS, } // C99 6.5.17 -static QualType CheckCommaOperands(Sema &S, Expr *&LHS, Expr *&RHS, +static QualType CheckCommaOperands(Sema &S, ExprResult &LHS, ExprResult &RHS, SourceLocation Loc) { - S.DiagnoseUnusedExprResult(LHS); - - ExprResult LHSResult = S.CheckPlaceholderExpr(LHS, Loc); - if (LHSResult.isInvalid()) - return QualType(); + S.DiagnoseUnusedExprResult(LHS.get()); - ExprResult RHSResult = S.CheckPlaceholderExpr(RHS, Loc); - if (RHSResult.isInvalid()) + LHS = S.CheckPlaceholderExpr(LHS.take(), Loc); + RHS = S.CheckPlaceholderExpr(RHS.take(), Loc); + if (LHS.isInvalid() || RHS.isInvalid()) return QualType(); - RHS = RHSResult.take(); // C's comma performs lvalue conversion (C99 6.3.2.1) on both its // operands, but not unary promotions. @@ -7687,15 +7846,19 @@ static QualType CheckCommaOperands(Sema &S, Expr *&LHS, Expr *&RHS, // So we treat the LHS as a ignored value, and in C++ we allow the // containing site to determine what should be done with the RHS. - S.IgnoredValueConversions(LHS); + LHS = S.IgnoredValueConversions(LHS.take()); + if (LHS.isInvalid()) + return QualType(); if (!S.getLangOptions().CPlusPlus) { - S.DefaultFunctionArrayLvalueConversion(RHS); - if (!RHS->getType()->isVoidType()) - S.RequireCompleteType(Loc, RHS->getType(), diag::err_incomplete_type); + RHS = S.DefaultFunctionArrayLvalueConversion(RHS.take()); + if (RHS.isInvalid()) + return QualType(); + if (!RHS.get()->getType()->isVoidType()) + S.RequireCompleteType(Loc, RHS.get()->getType(), diag::err_incomplete_type); } - return RHS->getType(); + return RHS.get()->getType(); } /// CheckIncrementDecrementOperand - unlike most "Check" methods, this routine @@ -7785,7 +7948,7 @@ static QualType CheckIncrementDecrementOperand(Sema &S, Expr *Op, } } -void Sema::ConvertPropertyForRValue(Expr *&E) { +ExprResult Sema::ConvertPropertyForRValue(Expr *E) { assert(E->getValueKind() == VK_LValue && E->getObjectKind() == OK_ObjCProperty); const ObjCPropertyRefExpr *PRE = E->getObjCProperty(); @@ -7809,28 +7972,30 @@ void Sema::ConvertPropertyForRValue(Expr *&E) { ExprResult Result = MaybeBindToTemporary(E); if (!Result.isInvalid()) E = Result.take(); + + return Owned(E); } -void Sema::ConvertPropertyForLValue(Expr *&LHS, Expr *&RHS, QualType &LHSTy) { - assert(LHS->getValueKind() == VK_LValue && - LHS->getObjectKind() == OK_ObjCProperty); - const ObjCPropertyRefExpr *PRE = LHS->getObjCProperty(); +void Sema::ConvertPropertyForLValue(ExprResult &LHS, ExprResult &RHS, QualType &LHSTy) { + assert(LHS.get()->getValueKind() == VK_LValue && + LHS.get()->getObjectKind() == OK_ObjCProperty); + const ObjCPropertyRefExpr *PropRef = LHS.get()->getObjCProperty(); - if (PRE->isImplicitProperty()) { + if (PropRef->isImplicitProperty()) { // If using property-dot syntax notation for assignment, and there is a // setter, RHS expression is being passed to the setter argument. So, // type conversion (and comparison) is RHS to setter's argument type. - if (const ObjCMethodDecl *SetterMD = PRE->getImplicitPropertySetter()) { + if (const ObjCMethodDecl *SetterMD = PropRef->getImplicitPropertySetter()) { ObjCMethodDecl::param_iterator P = SetterMD->param_begin(); LHSTy = (*P)->getType(); // Otherwise, if the getter returns an l-value, just call that. } else { - QualType Result = PRE->getImplicitPropertyGetter()->getResultType(); + QualType Result = PropRef->getImplicitPropertyGetter()->getResultType(); ExprValueKind VK = Expr::getValueKindForType(Result); if (VK == VK_LValue) { - LHS = ImplicitCastExpr::Create(Context, LHS->getType(), - CK_GetObjCProperty, LHS, 0, VK); + LHS = ImplicitCastExpr::Create(Context, LHS.get()->getType(), + CK_GetObjCProperty, LHS.take(), 0, VK); return; } } @@ -7839,11 +8004,9 @@ void Sema::ConvertPropertyForLValue(Expr *&LHS, Expr *&RHS, QualType &LHSTy) { if (getLangOptions().CPlusPlus && LHSTy->isRecordType()) { InitializedEntity Entity = InitializedEntity::InitializeParameter(Context, LHSTy); - Expr *Arg = RHS; - ExprResult ArgE = PerformCopyInitialization(Entity, SourceLocation(), - Owned(Arg)); + ExprResult ArgE = PerformCopyInitialization(Entity, SourceLocation(), RHS); if (!ArgE.isInvalid()) - RHS = ArgE.takeAs(); + RHS = ArgE; } } @@ -8056,7 +8219,10 @@ static QualType CheckIndirectionOperand(Sema &S, Expr *Op, ExprValueKind &VK, if (Op->isTypeDependent()) return S.Context.DependentTy; - S.UsualUnaryConversions(Op); + ExprResult ConvResult = S.UsualUnaryConversions(Op); + if (ConvResult.isInvalid()) + return QualType(); + Op = ConvResult.take(); QualType OpTy = Op->getType(); QualType Result; @@ -8193,7 +8359,8 @@ static void DiagnoseSelfAssignment(Sema &S, Expr *lhs, Expr *rhs, /// built-in operations; ActOnBinOp handles overloaded operators. ExprResult Sema::CreateBuiltinBinOp(SourceLocation OpLoc, BinaryOperatorKind Opc, - Expr *lhs, Expr *rhs) { + Expr *lhsExpr, Expr *rhsExpr) { + ExprResult lhs = Owned(lhsExpr), rhs = Owned(rhsExpr); QualType ResultTy; // Result type of the binary operator. // The following two variables are used for compound assignment operators QualType CompLHSTy; // Type of LHS after promotions for computation @@ -8209,25 +8376,25 @@ ExprResult Sema::CreateBuiltinBinOp(SourceLocation OpLoc, // f == 0; // resolve f blindly // void (*p)(int); p = f; // resolve f using target if (Opc != BO_Assign) { - ExprResult resolvedLHS = CheckPlaceholderExpr(lhs, OpLoc); + ExprResult resolvedLHS = CheckPlaceholderExpr(lhs.get(), OpLoc); if (!resolvedLHS.isUsable()) return ExprError(); - lhs = resolvedLHS.take(); + lhs = move(resolvedLHS); - ExprResult resolvedRHS = CheckPlaceholderExpr(rhs, OpLoc); + ExprResult resolvedRHS = CheckPlaceholderExpr(rhs.get(), OpLoc); if (!resolvedRHS.isUsable()) return ExprError(); - rhs = resolvedRHS.take(); + rhs = move(resolvedRHS); } switch (Opc) { case BO_Assign: - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, QualType()); + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, QualType()); if (getLangOptions().CPlusPlus && - lhs->getObjectKind() != OK_ObjCProperty) { - VK = lhs->getValueKind(); - OK = lhs->getObjectKind(); + lhs.get()->getObjectKind() != OK_ObjCProperty) { + VK = lhs.get()->getValueKind(); + OK = lhs.get()->getObjectKind(); } if (!ResultTy.isNull()) - DiagnoseSelfAssignment(*this, lhs, rhs, OpLoc); + DiagnoseSelfAssignment(*this, lhs.get(), rhs.get(), OpLoc); break; case BO_PtrMemD: case BO_PtrMemI: @@ -8276,60 +8443,59 @@ ExprResult Sema::CreateBuiltinBinOp(SourceLocation OpLoc, CompResultTy = CheckMultiplyDivideOperands(lhs, rhs, OpLoc, true, Opc == BO_DivAssign); CompLHSTy = CompResultTy; - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_RemAssign: CompResultTy = CheckRemainderOperands(lhs, rhs, OpLoc, true); CompLHSTy = CompResultTy; - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_AddAssign: CompResultTy = CheckAdditionOperands(lhs, rhs, OpLoc, &CompLHSTy); - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_SubAssign: CompResultTy = CheckSubtractionOperands(lhs, rhs, OpLoc, &CompLHSTy); - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_ShlAssign: case BO_ShrAssign: CompResultTy = CheckShiftOperands(lhs, rhs, OpLoc, Opc, true); CompLHSTy = CompResultTy; - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_AndAssign: case BO_XorAssign: case BO_OrAssign: CompResultTy = CheckBitwiseOperands(lhs, rhs, OpLoc, true); CompLHSTy = CompResultTy; - if (!CompResultTy.isNull()) - ResultTy = CheckAssignmentOperands(lhs, rhs, OpLoc, CompResultTy); + if (!CompResultTy.isNull() && !lhs.isInvalid() && !rhs.isInvalid()) + ResultTy = CheckAssignmentOperands(lhs.get(), rhs, OpLoc, CompResultTy); break; case BO_Comma: ResultTy = CheckCommaOperands(*this, lhs, rhs, OpLoc); - if (getLangOptions().CPlusPlus) { - VK = rhs->getValueKind(); - OK = rhs->getObjectKind(); + if (getLangOptions().CPlusPlus && !rhs.isInvalid()) { + VK = rhs.get()->getValueKind(); + OK = rhs.get()->getObjectKind(); } break; } - if (ResultTy.isNull()) + if (ResultTy.isNull() || lhs.isInvalid() || rhs.isInvalid()) return ExprError(); if (CompResultTy.isNull()) - return Owned(new (Context) BinaryOperator(lhs, rhs, Opc, ResultTy, - VK, OK, OpLoc)); - - if (getLangOptions().CPlusPlus && lhs->getObjectKind() != OK_ObjCProperty) { + return Owned(new (Context) BinaryOperator(lhs.take(), rhs.take(), Opc, + ResultTy, VK, OK, OpLoc)); + if (getLangOptions().CPlusPlus && lhs.get()->getObjectKind() != OK_ObjCProperty) { VK = VK_LValue; - OK = lhs->getObjectKind(); + OK = lhs.get()->getObjectKind(); } - return Owned(new (Context) CompoundAssignOperator(lhs, rhs, Opc, ResultTy, - VK, OK, CompLHSTy, + return Owned(new (Context) CompoundAssignOperator(lhs.take(), rhs.take(), Opc, + ResultTy, VK, OK, CompLHSTy, CompResultTy, OpLoc)); } @@ -8556,7 +8722,8 @@ ExprResult Sema::BuildBinOp(Scope *S, SourceLocation OpLoc, ExprResult Sema::CreateBuiltinUnaryOp(SourceLocation OpLoc, UnaryOperatorKind Opc, - Expr *Input) { + Expr *InputExpr) { + ExprResult Input = Owned(InputExpr); ExprValueKind VK = VK_RValue; ExprObjectKind OK = OK_Ordinary; QualType resultType; @@ -8565,27 +8732,28 @@ ExprResult Sema::CreateBuiltinUnaryOp(SourceLocation OpLoc, case UO_PreDec: case UO_PostInc: case UO_PostDec: - resultType = CheckIncrementDecrementOperand(*this, Input, VK, OpLoc, + resultType = CheckIncrementDecrementOperand(*this, Input.get(), VK, OpLoc, Opc == UO_PreInc || Opc == UO_PostInc, Opc == UO_PreInc || Opc == UO_PreDec); break; case UO_AddrOf: - resultType = CheckAddressOfOperand(*this, Input, OpLoc); + resultType = CheckAddressOfOperand(*this, Input.get(), OpLoc); break; case UO_Deref: { - ExprResult resolved = CheckPlaceholderExpr(Input, OpLoc); + ExprResult resolved = CheckPlaceholderExpr(Input.get(), OpLoc); if (!resolved.isUsable()) return ExprError(); - Input = resolved.take(); - DefaultFunctionArrayLvalueConversion(Input); - resultType = CheckIndirectionOperand(*this, Input, VK, OpLoc); + Input = move(resolved); + Input = DefaultFunctionArrayLvalueConversion(Input.take()); + resultType = CheckIndirectionOperand(*this, Input.get(), VK, OpLoc); break; } case UO_Plus: case UO_Minus: - UsualUnaryConversions(Input); - resultType = Input->getType(); + Input = UsualUnaryConversions(Input.take()); + if (Input.isInvalid()) return ExprError(); + resultType = Input.get()->getType(); if (resultType->isDependentType()) break; if (resultType->isArithmeticType() || // C99 6.5.3.3p1 @@ -8599,38 +8767,42 @@ ExprResult Sema::CreateBuiltinUnaryOp(SourceLocation OpLoc, resultType->isPointerType()) break; else if (resultType->isPlaceholderType()) { - ExprResult PR = CheckPlaceholderExpr(Input, OpLoc); - if (PR.isInvalid()) return ExprError(); - return CreateBuiltinUnaryOp(OpLoc, Opc, PR.take()); + Input = CheckPlaceholderExpr(Input.take(), OpLoc); + if (Input.isInvalid()) return ExprError(); + return CreateBuiltinUnaryOp(OpLoc, Opc, Input.take()); } return ExprError(Diag(OpLoc, diag::err_typecheck_unary_expr) - << resultType << Input->getSourceRange()); + << resultType << Input.get()->getSourceRange()); + case UO_Not: // bitwise complement - UsualUnaryConversions(Input); - resultType = Input->getType(); + Input = UsualUnaryConversions(Input.take()); + if (Input.isInvalid()) return ExprError(); + resultType = Input.get()->getType(); if (resultType->isDependentType()) break; // C99 6.5.3.3p1. We allow complex int and float as a GCC extension. if (resultType->isComplexType() || resultType->isComplexIntegerType()) // C99 does not support '~' for complex conjugation. Diag(OpLoc, diag::ext_integer_complement_complex) - << resultType << Input->getSourceRange(); + << resultType << Input.get()->getSourceRange(); else if (resultType->hasIntegerRepresentation()) break; else if (resultType->isPlaceholderType()) { - ExprResult PR = CheckPlaceholderExpr(Input, OpLoc); - if (PR.isInvalid()) return ExprError(); - return CreateBuiltinUnaryOp(OpLoc, Opc, PR.take()); + Input = CheckPlaceholderExpr(Input.take(), OpLoc); + if (Input.isInvalid()) return ExprError(); + return CreateBuiltinUnaryOp(OpLoc, Opc, Input.take()); } else { return ExprError(Diag(OpLoc, diag::err_typecheck_unary_expr) - << resultType << Input->getSourceRange()); + << resultType << Input.get()->getSourceRange()); } break; + case UO_LNot: // logical negation // Unlike +/-/~, integer promotions aren't done here (C99 6.5.3.3p5). - DefaultFunctionArrayLvalueConversion(Input); - resultType = Input->getType(); + Input = DefaultFunctionArrayLvalueConversion(Input.take()); + if (Input.isInvalid()) return ExprError(); + resultType = Input.get()->getType(); if (resultType->isDependentType()) break; if (resultType->isScalarType()) { @@ -8638,16 +8810,16 @@ ExprResult Sema::CreateBuiltinUnaryOp(SourceLocation OpLoc, if (Context.getLangOptions().CPlusPlus) { // C++03 [expr.unary.op]p8, C++0x [expr.unary.op]p9: // operand contextually converted to bool. - ImpCastExprToType(Input, Context.BoolTy, - ScalarTypeToBooleanCastKind(resultType)); + Input = ImpCastExprToType(Input.take(), Context.BoolTy, + ScalarTypeToBooleanCastKind(resultType)); } } else if (resultType->isPlaceholderType()) { - ExprResult PR = CheckPlaceholderExpr(Input, OpLoc); - if (PR.isInvalid()) return ExprError(); - return CreateBuiltinUnaryOp(OpLoc, Opc, PR.take()); + Input = CheckPlaceholderExpr(Input.take(), OpLoc); + if (Input.isInvalid()) return ExprError(); + return CreateBuiltinUnaryOp(OpLoc, Opc, Input.take()); } else { return ExprError(Diag(OpLoc, diag::err_typecheck_unary_expr) - << resultType << Input->getSourceRange()); + << resultType << Input.get()->getSourceRange()); } // LNot always has type int. C99 6.5.3.3p5. @@ -8658,20 +8830,21 @@ ExprResult Sema::CreateBuiltinUnaryOp(SourceLocation OpLoc, case UO_Imag: resultType = CheckRealImagOperand(*this, Input, OpLoc, Opc == UO_Real); // _Real and _Imag map ordinary l-values into ordinary l-values. - if (Input->getValueKind() != VK_RValue && - Input->getObjectKind() == OK_Ordinary) - VK = Input->getValueKind(); + if (Input.isInvalid()) return ExprError(); + if (Input.get()->getValueKind() != VK_RValue && + Input.get()->getObjectKind() == OK_Ordinary) + VK = Input.get()->getValueKind(); break; case UO_Extension: - resultType = Input->getType(); - VK = Input->getValueKind(); - OK = Input->getObjectKind(); + resultType = Input.get()->getType(); + VK = Input.get()->getValueKind(); + OK = Input.get()->getObjectKind(); break; } - if (resultType.isNull()) + if (resultType.isNull() || Input.isInvalid()) return ExprError(); - return Owned(new (Context) UnaryOperator(Input, Opc, resultType, + return Owned(new (Context) UnaryOperator(Input.take(), Opc, resultType, VK, OK, OpLoc)); } @@ -8738,26 +8911,28 @@ Sema::ActOnStmtExpr(SourceLocation LPLoc, Stmt *SubStmt, LastLabelStmt = Label; LastStmt = Label->getSubStmt(); } - if (Expr *LastExpr = dyn_cast(LastStmt)) { + if (Expr *LastE = dyn_cast(LastStmt)) { // Do function/array conversion on the last expression, but not // lvalue-to-rvalue. However, initialize an unqualified type. - DefaultFunctionArrayConversion(LastExpr); - Ty = LastExpr->getType().getUnqualifiedType(); + ExprResult LastExpr = DefaultFunctionArrayConversion(LastE); + if (LastExpr.isInvalid()) + return ExprError(); + Ty = LastExpr.get()->getType().getUnqualifiedType(); - if (!Ty->isDependentType() && !LastExpr->isTypeDependent()) { - ExprResult Res = PerformCopyInitialization( + if (!Ty->isDependentType() && !LastExpr.get()->isTypeDependent()) { + LastExpr = PerformCopyInitialization( InitializedEntity::InitializeResult(LPLoc, Ty, false), SourceLocation(), - Owned(LastExpr)); - if (Res.isInvalid()) + LastExpr); + if (LastExpr.isInvalid()) return ExprError(); - if ((LastExpr = Res.takeAs())) { + if (LastExpr.get() != 0) { if (!LastLabelStmt) - Compound->setLastStmt(LastExpr); + Compound->setLastStmt(LastExpr.take()); else - LastLabelStmt->setSubStmt(LastExpr); + LastLabelStmt->setSubStmt(LastExpr.take()); StmtExprMayBindToTemp = true; } } @@ -9234,7 +9409,10 @@ ExprResult Sema::BuildVAArgExpr(SourceLocation BuiltinLoc, // a pointer for va_arg. VaListType = Context.getArrayDecayedType(VaListType); // Make sure the input expression also decays appropriately. - UsualUnaryConversions(E); + ExprResult Result = UsualUnaryConversions(E); + if (Result.isInvalid()) + return ExprError(); + E = Result.take(); } else { // Otherwise, the va_list argument must be an l-value because // it is modified by va_arg. @@ -9919,39 +10097,43 @@ void Sema::DiagnoseEqualityWithExtraParens(ParenExpr *parenE) { } } -bool Sema::CheckBooleanCondition(Expr *&E, SourceLocation Loc) { +ExprResult Sema::CheckBooleanCondition(Expr *E, SourceLocation Loc) { DiagnoseAssignmentAsCondition(E); if (ParenExpr *parenE = dyn_cast(E)) DiagnoseEqualityWithExtraParens(parenE); if (!E->isTypeDependent()) { - if (E->isBoundMemberFunction(Context)) - return Diag(E->getLocStart(), diag::err_invalid_use_of_bound_member_func) + if (E->isBoundMemberFunction(Context)) { + Diag(E->getLocStart(), diag::err_invalid_use_of_bound_member_func) << E->getSourceRange(); + return ExprError(); + } if (getLangOptions().CPlusPlus) return CheckCXXBooleanCondition(E); // C++ 6.4p4 - DefaultFunctionArrayLvalueConversion(E); + ExprResult ERes = DefaultFunctionArrayLvalueConversion(E); + if (ERes.isInvalid()) + return ExprError(); + E = ERes.take(); QualType T = E->getType(); - if (!T->isScalarType()) // C99 6.8.4.1p1 - return Diag(Loc, diag::err_typecheck_statement_requires_scalar) - << T << E->getSourceRange(); + if (!T->isScalarType()) { // C99 6.8.4.1p1 + Diag(Loc, diag::err_typecheck_statement_requires_scalar) + << T << E->getSourceRange(); + return ExprError(); + } } - return false; + return Owned(E); } ExprResult Sema::ActOnBooleanCondition(Scope *S, SourceLocation Loc, Expr *Sub) { if (!Sub) return ExprError(); - - if (CheckBooleanCondition(Sub, Loc)) - return ExprError(); - - return Owned(Sub); + + return CheckBooleanCondition(Sub, Loc); } namespace { @@ -10023,9 +10205,9 @@ namespace { /// Check a cast of an unknown-any type. We intentionally only /// trigger this for C-style casts. -bool Sema::checkUnknownAnyCast(SourceRange typeRange, QualType castType, - Expr *&castExpr, CastKind &castKind, - ExprValueKind &VK, CXXCastPath &path) { +ExprResult Sema::checkUnknownAnyCast(SourceRange typeRange, QualType castType, + Expr *castExpr, CastKind &castKind, + ExprValueKind &VK, CXXCastPath &path) { VK = Expr::getValueKindForType(castType); // Rewrite the casted expression from scratch. diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp index 3d38b511ec..fb4ff7891f 100644 --- a/lib/Sema/SemaExprCXX.cpp +++ b/lib/Sema/SemaExprCXX.cpp @@ -323,7 +323,7 @@ ExprResult Sema::BuildCXXTypeId(QualType TypeInfoType, QualType UnqualT = Context.getUnqualifiedArrayType(T, Quals); if (!Context.hasSameType(T, UnqualT)) { T = UnqualT; - ImpCastExprToType(E, UnqualT, CK_NoOp, CastCategory(E)); + E = ImpCastExprToType(E, UnqualT, CK_NoOp, CastCategory(E)).take(); } } @@ -483,13 +483,17 @@ Sema::ActOnCXXThrow(SourceLocation OpLoc, Expr *Ex) { !getSourceManager().isInSystemHeader(OpLoc)) Diag(OpLoc, diag::err_exceptions_disabled) << "throw"; - if (Ex && !Ex->isTypeDependent() && CheckCXXThrowOperand(OpLoc, Ex)) - return ExprError(); + if (Ex && !Ex->isTypeDependent()) { + ExprResult ExRes = CheckCXXThrowOperand(OpLoc, Ex); + if (ExRes.isInvalid()) + return ExprError(); + Ex = ExRes.take(); + } return Owned(new (Context) CXXThrowExpr(Ex, Context.VoidTy, OpLoc)); } /// CheckCXXThrowOperand - Validate the operand of a throw. -bool Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E) { +ExprResult Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *E) { // C++ [except.throw]p3: // A throw-expression initializes a temporary object, called the exception // object, the type of which is determined by removing any top-level @@ -497,10 +501,13 @@ bool Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E) { // the type from "array of T" or "function returning T" to "pointer to T" // or "pointer to function returning T", [...] if (E->getType().hasQualifiers()) - ImpCastExprToType(E, E->getType().getUnqualifiedType(), CK_NoOp, - CastCategory(E)); + E = ImpCastExprToType(E, E->getType().getUnqualifiedType(), CK_NoOp, + CastCategory(E)).take(); - DefaultFunctionArrayConversion(E); + ExprResult Res = DefaultFunctionArrayConversion(E); + if (Res.isInvalid()) + return ExprError(); + E = Res.take(); // If the type of the exception would be an incomplete type or a pointer // to an incomplete type other than (cv) void the program is ill-formed. @@ -515,12 +522,12 @@ bool Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E) { PDiag(isPointer ? diag::err_throw_incomplete_ptr : diag::err_throw_incomplete) << E->getSourceRange())) - return true; + return ExprError(); if (RequireNonAbstractType(ThrowLoc, E->getType(), PDiag(diag::err_throw_abstract_type) << E->getSourceRange())) - return true; + return ExprError(); } // Initialize the exception result. This implicitly weeds out @@ -531,16 +538,16 @@ bool Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E) { InitializedEntity Entity = InitializedEntity::InitializeException(ThrowLoc, E->getType(), /*NRVO=*/false); - ExprResult Res = PerformMoveOrCopyInitialization(Entity, NRVOVariable, - QualType(), E); + Res = PerformMoveOrCopyInitialization(Entity, NRVOVariable, + QualType(), E); if (Res.isInvalid()) - return true; - E = Res.takeAs(); + return ExprError(); + E = Res.take(); // If the exception has class type, we need additional handling. const RecordType *RecordTy = Ty->getAs(); if (!RecordTy) - return false; + return Owned(E); CXXRecordDecl *RD = cast(RecordTy->getDecl()); // If we are throwing a polymorphic class type or pointer thereof, @@ -549,21 +556,21 @@ bool Sema::CheckCXXThrowOperand(SourceLocation ThrowLoc, Expr *&E) { // If a pointer is thrown, the referenced object will not be destroyed. if (isPointer) - return false; + return Owned(E); // If the class has a non-trivial destructor, we must be able to call it. if (RD->hasTrivialDestructor()) - return false; + return Owned(E); CXXDestructorDecl *Destructor = const_cast(LookupDestructor(RD)); if (!Destructor) - return false; + return Owned(E); MarkDeclarationReferenced(E->getExprLoc(), Destructor); CheckDestructorAccess(E->getExprLoc(), Destructor, PDiag(diag::err_access_dtor_exception) << Ty); - return false; + return Owned(E); } CXXMethodDecl *Sema::tryCaptureCXXThis() { @@ -668,10 +675,13 @@ Sema::BuildCXXTypeConstructExpr(TypeSourceInfo *TInfo, CastKind Kind = CK_Invalid; ExprValueKind VK = VK_RValue; CXXCastPath BasePath; - if (CheckCastTypes(TInfo->getTypeLoc().getSourceRange(), Ty, Exprs[0], - Kind, VK, BasePath, - /*FunctionalStyle=*/true)) + ExprResult CastExpr = + CheckCastTypes(TInfo->getTypeLoc().getSourceRange(), Ty, Exprs[0], + Kind, VK, BasePath, + /*FunctionalStyle=*/true); + if (CastExpr.isInvalid()) return ExprError(); + Exprs[0] = CastExpr.take(); exprs.release(); @@ -939,8 +949,8 @@ Sema::BuildCXXNew(SourceLocation StartLoc, bool UseGlobal, } } - ImpCastExprToType(ArraySize, Context.getSizeType(), - CK_IntegralCast); + ArraySize = ImpCastExprToType(ArraySize, Context.getSizeType(), + CK_IntegralCast).take(); } FunctionDecl *OperatorNew = 0; @@ -1633,19 +1643,20 @@ bool Sema::FindDeallocationFunction(SourceLocation StartLoc, CXXRecordDecl *RD, /// @code delete [] ptr; @endcode ExprResult Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, - bool ArrayForm, Expr *Ex) { + bool ArrayForm, Expr *ExE) { // C++ [expr.delete]p1: // The operand shall have a pointer type, or a class type having a single // conversion function to a pointer type. The result has type void. // // DR599 amends "pointer type" to "pointer to object type" in both cases. + ExprResult Ex = Owned(ExE); FunctionDecl *OperatorDelete = 0; bool ArrayFormAsWritten = ArrayForm; bool UsualArrayDeleteWantsSize = false; - if (!Ex->isTypeDependent()) { - QualType Type = Ex->getType(); + if (!Ex.get()->isTypeDependent()) { + QualType Type = Ex.get()->getType(); if (const RecordType *Record = Type->getAs()) { if (RequireCompleteType(StartLoc, Type, @@ -1677,15 +1688,18 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, // We have a single conversion to a pointer-to-object type. Perform // that conversion. // TODO: don't redo the conversion calculation. - if (!PerformImplicitConversion(Ex, + ExprResult Res = + PerformImplicitConversion(Ex.get(), ObjectPtrConversions.front()->getConversionType(), - AA_Converting)) { - Type = Ex->getType(); + AA_Converting); + if (Res.isUsable()) { + Ex = move(Res); + Type = Ex.get()->getType(); } } else if (ObjectPtrConversions.size() > 1) { Diag(StartLoc, diag::err_ambiguous_delete_operand) - << Type << Ex->getSourceRange(); + << Type << Ex.get()->getSourceRange(); for (unsigned i= 0; i < ObjectPtrConversions.size(); i++) NoteOverloadCandidate(ObjectPtrConversions[i]); return ExprError(); @@ -1694,7 +1708,7 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, if (!Type->isPointerType()) return ExprError(Diag(StartLoc, diag::err_delete_operand) - << Type << Ex->getSourceRange()); + << Type << Ex.get()->getSourceRange()); QualType Pointee = Type->getAs()->getPointeeType(); if (Pointee->isVoidType() && !isSFINAEContext()) { @@ -1702,14 +1716,14 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, // effectively bans deletion of "void*". However, most compilers support // this, so we treat it as a warning unless we're in a SFINAE context. Diag(StartLoc, diag::ext_delete_void_ptr_operand) - << Type << Ex->getSourceRange(); + << Type << Ex.get()->getSourceRange(); } else if (Pointee->isFunctionType() || Pointee->isVoidType()) return ExprError(Diag(StartLoc, diag::err_delete_operand) - << Type << Ex->getSourceRange()); + << Type << Ex.get()->getSourceRange()); else if (!Pointee->isDependentType() && RequireCompleteType(StartLoc, Pointee, PDiag(diag::warn_delete_incomplete) - << Ex->getSourceRange())) + << Ex.get()->getSourceRange())) return ExprError(); // C++ [expr.delete]p2: @@ -1717,12 +1731,12 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, // delete-expression; it is not necessary to cast away the constness // (5.2.11) of the pointer expression before it is used as the operand // of the delete-expression. ] - ImpCastExprToType(Ex, Context.getPointerType(Context.VoidTy), + Ex = ImpCastExprToType(Ex.take(), Context.getPointerType(Context.VoidTy), CK_NoOp); if (Pointee->isArrayType() && !ArrayForm) { Diag(StartLoc, diag::warn_delete_array_type) - << Type << Ex->getSourceRange() + << Type << Ex.get()->getSourceRange() << FixItHint::CreateInsertion(PP.getLocForEndOfToken(StartLoc), "[]"); ArrayForm = true; } @@ -1765,8 +1779,9 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, // Look for a global declaration. DeclareGlobalNewDelete(); DeclContext *TUDecl = Context.getTranslationUnitDecl(); + Expr *Arg = Ex.get(); if (FindAllocationOverload(StartLoc, SourceRange(), DeleteName, - &Ex, 1, TUDecl, /*AllowMissing=*/false, + &Arg, 1, TUDecl, /*AllowMissing=*/false, OperatorDelete)) return ExprError(); } @@ -1777,7 +1792,7 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, if (const RecordType *RT = PointeeElem->getAs()) { CXXRecordDecl *RD = cast(RT->getDecl()); if (CXXDestructorDecl *Dtor = LookupDestructor(RD)) { - CheckDestructorAccess(Ex->getExprLoc(), Dtor, + CheckDestructorAccess(Ex.get()->getExprLoc(), Dtor, PDiag(diag::err_access_dtor) << PointeeElem); } } @@ -1787,7 +1802,7 @@ Sema::ActOnCXXDelete(SourceLocation StartLoc, bool UseGlobal, return Owned(new (Context) CXXDeleteExpr(Context.VoidTy, UseGlobal, ArrayForm, ArrayFormAsWritten, UsualArrayDeleteWantsSize, - OperatorDelete, Ex, StartLoc)); + OperatorDelete, Ex.take(), StartLoc)); } /// \brief Check the use of the given variable as a C++ condition in an if, @@ -1808,19 +1823,23 @@ ExprResult Sema::CheckConditionVariable(VarDecl *ConditionVar, diag::err_invalid_use_of_array_type) << ConditionVar->getSourceRange()); - Expr *Condition = DeclRefExpr::Create(Context, NestedNameSpecifierLoc(), + ExprResult Condition = + Owned(DeclRefExpr::Create(Context, NestedNameSpecifierLoc(), ConditionVar, ConditionVar->getLocation(), ConditionVar->getType().getNonReferenceType(), - VK_LValue); - if (ConvertToBoolean && CheckBooleanCondition(Condition, StmtLoc)) - return ExprError(); + VK_LValue)); + if (ConvertToBoolean) { + Condition = CheckBooleanCondition(Condition.take(), StmtLoc); + if (Condition.isInvalid()) + return ExprError(); + } - return Owned(Condition); + return move(Condition); } /// CheckCXXBooleanCondition - Returns true if a conversion to bool is invalid. -bool Sema::CheckCXXBooleanCondition(Expr *&CondExpr) { +ExprResult Sema::CheckCXXBooleanCondition(Expr *CondExpr) { // C++ 6.4p4: // The value of a condition that is an initialized declaration in a statement // other than a switch statement is the value of the declared variable @@ -1906,20 +1925,22 @@ static ExprResult BuildCXXCastArgument(Sema &S, /// PerformImplicitConversion - Perform an implicit conversion of the /// expression From to the type ToType using the pre-computed implicit -/// conversion sequence ICS. Returns true if there was an error, false -/// otherwise. The expression From is replaced with the converted +/// conversion sequence ICS. Returns the converted /// expression. Action is the kind of conversion we're performing, /// used in the error message. -bool -Sema::PerformImplicitConversion(Expr *&From, QualType ToType, +ExprResult +Sema::PerformImplicitConversion(Expr *From, QualType ToType, const ImplicitConversionSequence &ICS, AssignmentAction Action, bool CStyle) { switch (ICS.getKind()) { - case ImplicitConversionSequence::StandardConversion: - if (PerformImplicitConversion(From, ToType, ICS.Standard, Action, - CStyle)) - return true; + case ImplicitConversionSequence::StandardConversion: { + ExprResult Res = PerformImplicitConversion(From, ToType, ICS.Standard, + Action, CStyle); + if (Res.isInvalid()) + return ExprError(); + From = Res.take(); break; + } case ImplicitConversionSequence::UserDefinedConversion: { @@ -1946,10 +1967,13 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, } // Watch out for elipsis conversion. if (!ICS.UserDefined.EllipsisConversion) { - if (PerformImplicitConversion(From, BeforeToType, - ICS.UserDefined.Before, AA_Converting, - CStyle)) - return true; + ExprResult Res = + PerformImplicitConversion(From, BeforeToType, + ICS.UserDefined.Before, AA_Converting, + CStyle); + if (Res.isInvalid()) + return ExprError(); + From = Res.take(); } ExprResult CastArg @@ -1961,9 +1985,9 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, From); if (CastArg.isInvalid()) - return true; + return ExprError(); - From = CastArg.takeAs(); + From = CastArg.take(); return PerformImplicitConversion(From, ToType, ICS.UserDefined.After, AA_Converting, CStyle); @@ -1973,28 +1997,27 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, ICS.DiagnoseAmbiguousConversion(*this, From->getExprLoc(), PDiag(diag::err_typecheck_ambiguous_condition) << From->getSourceRange()); - return true; + return ExprError(); case ImplicitConversionSequence::EllipsisConversion: assert(false && "Cannot perform an ellipsis conversion"); - return false; + return Owned(From); case ImplicitConversionSequence::BadConversion: - return true; + return ExprError(); } // Everything went well. - return false; + return Owned(From); } /// PerformImplicitConversion - Perform an implicit conversion of the /// expression From to the type ToType by following the standard -/// conversion sequence SCS. Returns true if there was an error, false -/// otherwise. The expression From is replaced with the converted +/// conversion sequence SCS. Returns the converted /// expression. Flavor is the context in which we're performing this /// conversion, for use in error messages. -bool -Sema::PerformImplicitConversion(Expr *&From, QualType ToType, +ExprResult +Sema::PerformImplicitConversion(Expr *From, QualType ToType, const StandardConversionSequence& SCS, AssignmentAction Action, bool CStyle) { // Overall FIXME: we are recomputing too many types here and doing far too @@ -2012,32 +2035,20 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, MultiExprArg(*this, &From, 1), /*FIXME:ConstructLoc*/SourceLocation(), ConstructorArgs)) - return true; - ExprResult FromResult = - BuildCXXConstructExpr(/*FIXME:ConstructLoc*/SourceLocation(), - ToType, SCS.CopyConstructor, - move_arg(ConstructorArgs), - /*ZeroInit*/ false, - CXXConstructExpr::CK_Complete, - SourceRange()); - if (FromResult.isInvalid()) - return true; - From = FromResult.takeAs(); - return false; + return ExprError(); + return BuildCXXConstructExpr(/*FIXME:ConstructLoc*/SourceLocation(), + ToType, SCS.CopyConstructor, + move_arg(ConstructorArgs), + /*ZeroInit*/ false, + CXXConstructExpr::CK_Complete, + SourceRange()); } - ExprResult FromResult = - BuildCXXConstructExpr(/*FIXME:ConstructLoc*/SourceLocation(), - ToType, SCS.CopyConstructor, - MultiExprArg(*this, &From, 1), - /*ZeroInit*/ false, - CXXConstructExpr::CK_Complete, - SourceRange()); - - if (FromResult.isInvalid()) - return true; - - From = FromResult.takeAs(); - return false; + return BuildCXXConstructExpr(/*FIXME:ConstructLoc*/SourceLocation(), + ToType, SCS.CopyConstructor, + MultiExprArg(*this, &From, 1), + /*ZeroInit*/ false, + CXXConstructExpr::CK_Complete, + SourceRange()); } // Resolve overloaded function references. @@ -2046,10 +2057,10 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, FunctionDecl *Fn = ResolveAddressOfOverloadedFunction(From, ToType, true, Found); if (!Fn) - return true; + return ExprError(); if (DiagnoseUseOfDecl(Fn, From->getSourceRange().getBegin())) - return true; + return ExprError(); From = FixOverloadedFunctionReference(From, Found, Fn); FromType = From->getType(); @@ -2064,7 +2075,10 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, case ICK_Lvalue_To_Rvalue: // Should this get its own ICK? if (From->getObjectKind() == OK_ObjCProperty) { - ConvertPropertyForRValue(From); + ExprResult FromRes = ConvertPropertyForRValue(From); + if (FromRes.isInvalid()) + return ExprError(); + From = FromRes.take(); if (!From->isGLValue()) break; } @@ -2078,12 +2092,12 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, case ICK_Array_To_Pointer: FromType = Context.getArrayDecayedType(FromType); - ImpCastExprToType(From, FromType, CK_ArrayToPointerDecay); + From = ImpCastExprToType(From, FromType, CK_ArrayToPointerDecay).take(); break; case ICK_Function_To_Pointer: FromType = Context.getPointerType(FromType); - ImpCastExprToType(From, FromType, CK_FunctionToPointerDecay); + From = ImpCastExprToType(From, FromType, CK_FunctionToPointerDecay).take(); break; default: @@ -2097,7 +2111,7 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, // If both sides are functions (or pointers/references to them), there could // be incompatible exception declarations. if (CheckExceptionSpecCompatibility(From, ToType)) - return true; + return ExprError(); // Nothing else to do. break; @@ -2105,19 +2119,19 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, // If both sides are functions (or pointers/references to them), there could // be incompatible exception declarations. if (CheckExceptionSpecCompatibility(From, ToType)) - return true; + return ExprError(); - ImpCastExprToType(From, ToType, CK_NoOp); + From = ImpCastExprToType(From, ToType, CK_NoOp).take(); break; case ICK_Integral_Promotion: case ICK_Integral_Conversion: - ImpCastExprToType(From, ToType, CK_IntegralCast); + From = ImpCastExprToType(From, ToType, CK_IntegralCast).take(); break; case ICK_Floating_Promotion: case ICK_Floating_Conversion: - ImpCastExprToType(From, ToType, CK_FloatingCast); + From = ImpCastExprToType(From, ToType, CK_FloatingCast).take(); break; case ICK_Complex_Promotion: @@ -2135,19 +2149,19 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, } else { CK = CK_IntegralComplexCast; } - ImpCastExprToType(From, ToType, CK); + From = ImpCastExprToType(From, ToType, CK).take(); break; } case ICK_Floating_Integral: if (ToType->isRealFloatingType()) - ImpCastExprToType(From, ToType, CK_IntegralToFloating); + From = ImpCastExprToType(From, ToType, CK_IntegralToFloating).take(); else - ImpCastExprToType(From, ToType, CK_FloatingToIntegral); + From = ImpCastExprToType(From, ToType, CK_FloatingToIntegral).take(); break; case ICK_Compatible_Conversion: - ImpCastExprToType(From, ToType, CK_NoOp); + From = ImpCastExprToType(From, ToType, CK_NoOp).take(); break; case ICK_Pointer_Conversion: { @@ -2168,8 +2182,8 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, CastKind Kind = CK_Invalid; CXXCastPath BasePath; if (CheckPointerConversion(From, ToType, Kind, BasePath, CStyle)) - return true; - ImpCastExprToType(From, ToType, Kind, VK_RValue, &BasePath); + return ExprError(); + From = ImpCastExprToType(From, ToType, Kind, VK_RValue, &BasePath).take(); break; } @@ -2177,16 +2191,16 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, CastKind Kind = CK_Invalid; CXXCastPath BasePath; if (CheckMemberPointerConversion(From, ToType, Kind, BasePath, CStyle)) - return true; + return ExprError(); if (CheckExceptionSpecCompatibility(From, ToType)) - return true; - ImpCastExprToType(From, ToType, Kind, VK_RValue, &BasePath); + return ExprError(); + From = ImpCastExprToType(From, ToType, Kind, VK_RValue, &BasePath).take(); break; } case ICK_Boolean_Conversion: - ImpCastExprToType(From, Context.BoolTy, - ScalarTypeToBooleanCastKind(FromType)); + From = ImpCastExprToType(From, Context.BoolTy, + ScalarTypeToBooleanCastKind(FromType)).take(); break; case ICK_Derived_To_Base: { @@ -2197,20 +2211,20 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, From->getSourceRange(), &BasePath, CStyle)) - return true; + return ExprError(); - ImpCastExprToType(From, ToType.getNonReferenceType(), + From = ImpCastExprToType(From, ToType.getNonReferenceType(), CK_DerivedToBase, CastCategory(From), - &BasePath); + &BasePath).take(); break; } case ICK_Vector_Conversion: - ImpCastExprToType(From, ToType, CK_BitCast); + From = ImpCastExprToType(From, ToType, CK_BitCast).take(); break; case ICK_Vector_Splat: - ImpCastExprToType(From, ToType, CK_VectorSplat); + From = ImpCastExprToType(From, ToType, CK_VectorSplat).take(); break; case ICK_Complex_Real: @@ -2223,17 +2237,17 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, if (Context.hasSameUnqualifiedType(ElType, From->getType())) { // do nothing } else if (From->getType()->isRealFloatingType()) { - ImpCastExprToType(From, ElType, - isFloatingComplex ? CK_FloatingCast : CK_FloatingToIntegral); + From = ImpCastExprToType(From, ElType, + isFloatingComplex ? CK_FloatingCast : CK_FloatingToIntegral).take(); } else { assert(From->getType()->isIntegerType()); - ImpCastExprToType(From, ElType, - isFloatingComplex ? CK_IntegralToFloating : CK_IntegralCast); + From = ImpCastExprToType(From, ElType, + isFloatingComplex ? CK_IntegralToFloating : CK_IntegralCast).take(); } // y -> _Complex y - ImpCastExprToType(From, ToType, + From = ImpCastExprToType(From, ToType, isFloatingComplex ? CK_FloatingRealToComplex - : CK_IntegralRealToComplex); + : CK_IntegralRealToComplex).take(); // Case 2. _Complex x -> y } else { @@ -2244,32 +2258,37 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, bool isFloatingComplex = ElType->isRealFloatingType(); // _Complex x -> x - ImpCastExprToType(From, ElType, + From = ImpCastExprToType(From, ElType, isFloatingComplex ? CK_FloatingComplexToReal - : CK_IntegralComplexToReal); + : CK_IntegralComplexToReal).take(); // x -> y if (Context.hasSameUnqualifiedType(ElType, ToType)) { // do nothing } else if (ToType->isRealFloatingType()) { - ImpCastExprToType(From, ToType, - isFloatingComplex ? CK_FloatingCast : CK_IntegralToFloating); + From = ImpCastExprToType(From, ToType, + isFloatingComplex ? CK_FloatingCast : CK_IntegralToFloating).take(); } else { assert(ToType->isIntegerType()); - ImpCastExprToType(From, ToType, - isFloatingComplex ? CK_FloatingToIntegral : CK_IntegralCast); + From = ImpCastExprToType(From, ToType, + isFloatingComplex ? CK_FloatingToIntegral : CK_IntegralCast).take(); } } break; case ICK_Block_Pointer_Conversion: { - ImpCastExprToType(From, ToType.getUnqualifiedType(), CK_BitCast, VK_RValue); + From = ImpCastExprToType(From, ToType.getUnqualifiedType(), CK_BitCast, + VK_RValue).take(); break; } case ICK_TransparentUnionConversion: { + ExprResult FromRes = Owned(From); Sema::AssignConvertType ConvTy = - CheckTransparentUnionArgumentConstraints(ToType, From); + CheckTransparentUnionArgumentConstraints(ToType, FromRes); + if (FromRes.isInvalid()) + return ExprError(); + From = FromRes.take(); assert ((ConvTy == Sema::Compatible) && "Improper transparent union conversion"); (void)ConvTy; @@ -2295,8 +2314,8 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, // target type isn't a reference. ExprValueKind VK = ToType->isReferenceType() ? CastCategory(From) : VK_RValue; - ImpCastExprToType(From, ToType.getNonLValueExprType(Context), - CK_NoOp, VK); + From = ImpCastExprToType(From, ToType.getNonLValueExprType(Context), + CK_NoOp, VK).take(); if (SCS.DeprecatedStringLiteralToCharPtr && !getLangOptions().WritableStrings) @@ -2311,7 +2330,7 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, break; } - return false; + return Owned(From); } ExprResult Sema::ActOnUnaryTypeTrait(UnaryTypeTrait UTT, @@ -2713,7 +2732,7 @@ ExprResult Sema::BuildBinaryTypeTrait(BinaryTypeTrait BTT, ResultType)); } -QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, +QualType Sema::CheckPointerToMemberOperands(ExprResult &lex, ExprResult &rex, ExprValueKind &VK, SourceLocation Loc, bool isIndirect) { @@ -2722,11 +2741,11 @@ QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, // The binary operator .* [p3: ->*] binds its second operand, which shall // be of type "pointer to member of T" (where T is a completely-defined // class type) [...] - QualType RType = rex->getType(); + QualType RType = rex.get()->getType(); const MemberPointerType *MemPtr = RType->getAs(); if (!MemPtr) { Diag(Loc, diag::err_bad_memptr_rhs) - << OpSpelling << RType << rex->getSourceRange(); + << OpSpelling << RType << rex.get()->getSourceRange(); return QualType(); } @@ -2742,7 +2761,7 @@ QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, // [...] to its first operand, which shall be of class T or of a class of // which T is an unambiguous and accessible base class. [p3: a pointer to // such a class] - QualType LType = lex->getType(); + QualType LType = lex.get()->getType(); if (isIndirect) { if (const PointerType *Ptr = LType->getAs()) LType = Ptr->getPointeeType(); @@ -2767,20 +2786,20 @@ QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, if (!IsDerivedFrom(LType, Class, Paths) || Paths.isAmbiguous(Context.getCanonicalType(Class))) { Diag(Loc, diag::err_bad_memptr_lhs) << OpSpelling - << (int)isIndirect << lex->getType(); + << (int)isIndirect << lex.get()->getType(); return QualType(); } // Cast LHS to type of use. QualType UseType = isIndirect ? Context.getPointerType(Class) : Class; ExprValueKind VK = - isIndirect ? VK_RValue : CastCategory(lex); + isIndirect ? VK_RValue : CastCategory(lex.get()); CXXCastPath BasePath; BuildBasePathArray(Paths, BasePath); - ImpCastExprToType(lex, UseType, CK_DerivedToBase, VK, &BasePath); + lex = ImpCastExprToType(lex.take(), UseType, CK_DerivedToBase, VK, &BasePath); } - if (isa(rex->IgnoreParens())) { + if (isa(rex.get()->IgnoreParens())) { // Diagnose use of pointer-to-member type which when used as // the functional cast in a pointer-to-member expression. Diag(Loc, diag::err_pointer_to_member_type) << isIndirect; @@ -2815,15 +2834,15 @@ QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, break; case RQ_LValue: - if (!isIndirect && !lex->Classify(Context).isLValue()) + if (!isIndirect && !lex.get()->Classify(Context).isLValue()) Diag(Loc, diag::err_pointer_to_member_oper_value_classify) - << RType << 1 << lex->getSourceRange(); + << RType << 1 << lex.get()->getSourceRange(); break; case RQ_RValue: - if (isIndirect || !lex->Classify(Context).isRValue()) + if (isIndirect || !lex.get()->Classify(Context).isRValue()) Diag(Loc, diag::err_pointer_to_member_oper_value_classify) - << RType << 0 << lex->getSourceRange(); + << RType << 0 << lex.get()->getSourceRange(); break; } } @@ -2840,7 +2859,7 @@ QualType Sema::CheckPointerToMemberOperands(Expr *&lex, Expr *&rex, else if (isIndirect) VK = VK_LValue; else - VK = lex->getValueKind(); + VK = lex.get()->getValueKind(); return Result; } @@ -2941,43 +2960,52 @@ static bool TryClassUnification(Sema &Self, Expr *From, Expr *To, /// This is part of the parameter validation for the ? operator. If either /// value operand is a class type, overload resolution is used to find a /// conversion to a common type. -static bool FindConditionalOverload(Sema &Self, Expr *&LHS, Expr *&RHS, +static bool FindConditionalOverload(Sema &Self, ExprResult &LHS, ExprResult &RHS, SourceLocation QuestionLoc) { - Expr *Args[2] = { LHS, RHS }; + Expr *Args[2] = { LHS.get(), RHS.get() }; OverloadCandidateSet CandidateSet(QuestionLoc); Self.AddBuiltinOperatorCandidates(OO_Conditional, QuestionLoc, Args, 2, CandidateSet); OverloadCandidateSet::iterator Best; switch (CandidateSet.BestViableFunction(Self, QuestionLoc, Best)) { - case OR_Success: + case OR_Success: { // We found a match. Perform the conversions on the arguments and move on. - if (Self.PerformImplicitConversion(LHS, Best->BuiltinTypes.ParamTypes[0], - Best->Conversions[0], Sema::AA_Converting) || - Self.PerformImplicitConversion(RHS, Best->BuiltinTypes.ParamTypes[1], - Best->Conversions[1], Sema::AA_Converting)) + ExprResult LHSRes = + Self.PerformImplicitConversion(LHS.get(), Best->BuiltinTypes.ParamTypes[0], + Best->Conversions[0], Sema::AA_Converting); + if (LHSRes.isInvalid()) break; + LHS = move(LHSRes); + + ExprResult RHSRes = + Self.PerformImplicitConversion(RHS.get(), Best->BuiltinTypes.ParamTypes[1], + Best->Conversions[1], Sema::AA_Converting); + if (RHSRes.isInvalid()) + break; + RHS = move(RHSRes); if (Best->Function) Self.MarkDeclarationReferenced(QuestionLoc, Best->Function); return false; - + } + case OR_No_Viable_Function: // Emit a better diagnostic if one of the expressions is a null pointer // constant and the other is a pointer type. In this case, the user most // likely forgot to take the address of the other expression. - if (Self.DiagnoseConditionalForNull(LHS, RHS, QuestionLoc)) + if (Self.DiagnoseConditionalForNull(LHS.get(), RHS.get(), QuestionLoc)) return true; Self.Diag(QuestionLoc, diag::err_typecheck_cond_incompatible_operands) - << LHS->getType() << RHS->getType() - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getType() << RHS.get()->getType() + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return true; case OR_Ambiguous: Self.Diag(QuestionLoc, diag::err_conditional_ambiguous_ovl) - << LHS->getType() << RHS->getType() - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getType() << RHS.get()->getType() + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); // FIXME: Print the possible common types by printing the return types of // the viable candidates. break; @@ -2991,16 +3019,17 @@ static bool FindConditionalOverload(Sema &Self, Expr *&LHS, Expr *&RHS, /// \brief Perform an "extended" implicit conversion as returned by /// TryClassUnification. -static bool ConvertForConditional(Sema &Self, Expr *&E, QualType T) { +static bool ConvertForConditional(Sema &Self, ExprResult &E, QualType T) { InitializedEntity Entity = InitializedEntity::InitializeTemporary(T); - InitializationKind Kind = InitializationKind::CreateCopy(E->getLocStart(), + InitializationKind Kind = InitializationKind::CreateCopy(E.get()->getLocStart(), SourceLocation()); - InitializationSequence InitSeq(Self, Entity, Kind, &E, 1); - ExprResult Result = InitSeq.Perform(Self, Entity, Kind, MultiExprArg(&E, 1)); + Expr *Arg = E.take(); + InitializationSequence InitSeq(Self, Entity, Kind, &Arg, 1); + ExprResult Result = InitSeq.Perform(Self, Entity, Kind, MultiExprArg(&Arg, 1)); if (Result.isInvalid()) return true; - E = Result.takeAs(); + E = Result; return false; } @@ -3008,7 +3037,7 @@ static bool ConvertForConditional(Sema &Self, Expr *&E, QualType T) { /// /// See C++ [expr.cond]. Note that LHS is never null, even for the GNU x ?: y /// extension. In this case, LHS == Cond. (But they're not aliases.) -QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, +QualType Sema::CXXCheckConditionalOperands(ExprResult &Cond, ExprResult &LHS, ExprResult &RHS, ExprValueKind &VK, ExprObjectKind &OK, SourceLocation QuestionLoc) { // FIXME: Handle C99's complex types, vector types, block pointers and Obj-C++ @@ -3016,9 +3045,11 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // C++0x 5.16p1 // The first expression is contextually converted to bool. - if (!Cond->isTypeDependent()) { - if (CheckCXXBooleanCondition(Cond)) + if (!Cond.get()->isTypeDependent()) { + ExprResult CondRes = CheckCXXBooleanCondition(Cond.take()); + if (CondRes.isInvalid()) return QualType(); + Cond = move(CondRes); } // Assume r-value. @@ -3026,28 +3057,30 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, OK = OK_Ordinary; // Either of the arguments dependent? - if (LHS->isTypeDependent() || RHS->isTypeDependent()) + if (LHS.get()->isTypeDependent() || RHS.get()->isTypeDependent()) return Context.DependentTy; // C++0x 5.16p2 // If either the second or the third operand has type (cv) void, ... - QualType LTy = LHS->getType(); - QualType RTy = RHS->getType(); + QualType LTy = LHS.get()->getType(); + QualType RTy = RHS.get()->getType(); bool LVoid = LTy->isVoidType(); bool RVoid = RTy->isVoidType(); if (LVoid || RVoid) { // ... then the [l2r] conversions are performed on the second and third // operands ... - DefaultFunctionArrayLvalueConversion(LHS); - DefaultFunctionArrayLvalueConversion(RHS); - LTy = LHS->getType(); - RTy = RHS->getType(); + LHS = DefaultFunctionArrayLvalueConversion(LHS.take()); + RHS = DefaultFunctionArrayLvalueConversion(RHS.take()); + if (LHS.isInvalid() || RHS.isInvalid()) + return QualType(); + LTy = LHS.get()->getType(); + RTy = RHS.get()->getType(); // ... and one of the following shall hold: // -- The second or the third operand (but not both) is a throw- // expression; the result is of the type of the other and is an rvalue. - bool LThrow = isa(LHS); - bool RThrow = isa(RHS); + bool LThrow = isa(LHS.get()); + bool RThrow = isa(RHS.get()); if (LThrow && !RThrow) return RTy; if (RThrow && !LThrow) @@ -3061,7 +3094,7 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // Neither holds, error. Diag(QuestionLoc, diag::err_conditional_void_nonvoid) << (LVoid ? RTy : LTy) << (LVoid ? 0 : 1) - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return QualType(); } @@ -3077,15 +3110,15 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // These return true if a single direction is already ambiguous. QualType L2RType, R2LType; bool HaveL2R, HaveR2L; - if (TryClassUnification(*this, LHS, RHS, QuestionLoc, HaveL2R, L2RType)) + if (TryClassUnification(*this, LHS.get(), RHS.get(), QuestionLoc, HaveL2R, L2RType)) return QualType(); - if (TryClassUnification(*this, RHS, LHS, QuestionLoc, HaveR2L, R2LType)) + if (TryClassUnification(*this, RHS.get(), LHS.get(), QuestionLoc, HaveR2L, R2LType)) return QualType(); // If both can be converted, [...] the program is ill-formed. if (HaveL2R && HaveR2L) { Diag(QuestionLoc, diag::err_conditional_ambiguous) - << LTy << RTy << LHS->getSourceRange() << RHS->getSourceRange(); + << LTy << RTy << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return QualType(); } @@ -3093,13 +3126,13 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // the chosen operand and the converted operands are used in place of the // original operands for the remainder of this section. if (HaveL2R) { - if (ConvertForConditional(*this, LHS, L2RType)) + if (ConvertForConditional(*this, LHS, L2RType) || LHS.isInvalid()) return QualType(); - LTy = LHS->getType(); + LTy = LHS.get()->getType(); } else if (HaveR2L) { - if (ConvertForConditional(*this, RHS, R2LType)) + if (ConvertForConditional(*this, RHS, R2LType) || RHS.isInvalid()) return QualType(); - RTy = RHS->getType(); + RTy = RHS.get()->getType(); } } @@ -3112,13 +3145,13 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // l-values. bool Same = Context.hasSameType(LTy, RTy); if (Same && - LHS->isGLValue() && - LHS->getValueKind() == RHS->getValueKind() && - LHS->isOrdinaryOrBitFieldObject() && - RHS->isOrdinaryOrBitFieldObject()) { - VK = LHS->getValueKind(); - if (LHS->getObjectKind() == OK_BitField || - RHS->getObjectKind() == OK_BitField) + LHS.get()->isGLValue() && + LHS.get()->getValueKind() == RHS.get()->getValueKind() && + LHS.get()->isOrdinaryOrBitFieldObject() && + RHS.get()->isOrdinaryOrBitFieldObject()) { + VK = LHS.get()->getValueKind(); + if (LHS.get()->getObjectKind() == OK_BitField || + RHS.get()->getObjectKind() == OK_BitField) OK = OK_BitField; return LTy; } @@ -3137,10 +3170,12 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // C++0x 5.16p6 // LValue-to-rvalue, array-to-pointer, and function-to-pointer standard // conversions are performed on the second and third operands. - DefaultFunctionArrayLvalueConversion(LHS); - DefaultFunctionArrayLvalueConversion(RHS); - LTy = LHS->getType(); - RTy = RHS->getType(); + LHS = DefaultFunctionArrayLvalueConversion(LHS.take()); + RHS = DefaultFunctionArrayLvalueConversion(RHS.take()); + if (LHS.isInvalid() || RHS.isInvalid()) + return QualType(); + LTy = LHS.get()->getType(); + RTy = RHS.get()->getType(); // After those conversions, one of the following shall hold: // -- The second and third operands have the same type; the result @@ -3154,18 +3189,18 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, InitializedEntity Entity = InitializedEntity::InitializeTemporary(LTy); ExprResult LHSCopy = PerformCopyInitialization(Entity, SourceLocation(), - Owned(LHS)); + LHS); if (LHSCopy.isInvalid()) return QualType(); ExprResult RHSCopy = PerformCopyInitialization(Entity, SourceLocation(), - Owned(RHS)); + RHS); if (RHSCopy.isInvalid()) return QualType(); - LHS = LHSCopy.takeAs(); - RHS = RHSCopy.takeAs(); + LHS = LHSCopy; + RHS = RHSCopy; } return LTy; @@ -3180,7 +3215,9 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, // common type, and the result is of that type. if (LTy->isArithmeticType() && RTy->isArithmeticType()) { UsualArithmeticConversions(LHS, RHS); - return LHS->getType(); + if (LHS.isInvalid() || RHS.isInvalid()) + return QualType(); + return LHS.get()->getType(); } // -- The second and third operands have pointer type, or one has pointer @@ -3201,7 +3238,7 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, Diag(QuestionLoc, diag::ext_typecheck_cond_incompatible_operands_nonstandard) << LTy << RTy << Composite - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return Composite; } @@ -3212,12 +3249,12 @@ QualType Sema::CXXCheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS, return Composite; // Check if we are using a null with a non-pointer type. - if (DiagnoseConditionalForNull(LHS, RHS, QuestionLoc)) + if (DiagnoseConditionalForNull(LHS.get(), RHS.get(), QuestionLoc)) return QualType(); Diag(QuestionLoc, diag::err_typecheck_cond_incompatible_operands) - << LHS->getType() << RHS->getType() - << LHS->getSourceRange() << RHS->getSourceRange(); + << LHS.get()->getType() << RHS.get()->getType() + << LHS.get()->getSourceRange() << RHS.get()->getSourceRange(); return QualType(); } @@ -3255,16 +3292,16 @@ QualType Sema::FindCompositePointerType(SourceLocation Loc, // the type of the other operand. if (E1->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { if (T2->isMemberPointerType()) - ImpCastExprToType(E1, T2, CK_NullToMemberPointer); + E1 = ImpCastExprToType(E1, T2, CK_NullToMemberPointer).take(); else - ImpCastExprToType(E1, T2, CK_NullToPointer); + E1 = ImpCastExprToType(E1, T2, CK_NullToPointer).take(); return T2; } if (E2->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull)) { if (T1->isMemberPointerType()) - ImpCastExprToType(E2, T1, CK_NullToMemberPointer); + E2 = ImpCastExprToType(E2, T1, CK_NullToMemberPointer).take(); else - ImpCastExprToType(E2, T1, CK_NullToPointer); + E2 = ImpCastExprToType(E2, T1, CK_NullToPointer).take(); return T1; } @@ -3867,24 +3904,25 @@ ExprResult Sema::ActOnPseudoDestructorExpr(Scope *S, Expr *Base, Destructed, HasTrailingLParen); } -ExprResult Sema::BuildCXXMemberCallExpr(Expr *Exp, NamedDecl *FoundDecl, +ExprResult Sema::BuildCXXMemberCallExpr(Expr *E, NamedDecl *FoundDecl, CXXMethodDecl *Method) { - if (PerformObjectArgumentInitialization(Exp, /*Qualifier=*/0, - FoundDecl, Method)) + ExprResult Exp = PerformObjectArgumentInitialization(E, /*Qualifier=*/0, + FoundDecl, Method); + if (Exp.isInvalid()) return true; MemberExpr *ME = - new (Context) MemberExpr(Exp, /*IsArrow=*/false, Method, + new (Context) MemberExpr(Exp.take(), /*IsArrow=*/false, Method, SourceLocation(), Method->getType(), VK_RValue, OK_Ordinary); QualType ResultType = Method->getResultType(); ExprValueKind VK = Expr::getValueKindForType(ResultType); ResultType = ResultType.getNonLValueExprType(Context); - MarkDeclarationReferenced(Exp->getLocStart(), Method); + MarkDeclarationReferenced(Exp.get()->getLocStart(), Method); CXXMemberCallExpr *CE = new (Context) CXXMemberCallExpr(Context, ME, 0, 0, ResultType, VK, - Exp->getLocEnd()); + Exp.get()->getLocEnd()); return CE; } @@ -3902,42 +3940,51 @@ ExprResult Sema::ActOnNoexceptExpr(SourceLocation KeyLoc, SourceLocation, /// Perform the conversions required for an expression used in a /// context that ignores the result. -void Sema::IgnoredValueConversions(Expr *&E) { +ExprResult Sema::IgnoredValueConversions(Expr *E) { // C99 6.3.2.1: // [Except in specific positions,] an lvalue that does not have // array type is converted to the value stored in the // designated object (and is no longer an lvalue). - if (E->isRValue()) return; + if (E->isRValue()) return Owned(E); // We always want to do this on ObjC property references. if (E->getObjectKind() == OK_ObjCProperty) { - ConvertPropertyForRValue(E); - if (E->isRValue()) return; + ExprResult Res = ConvertPropertyForRValue(E); + if (Res.isInvalid()) return Owned(E); + E = Res.take(); + if (E->isRValue()) return Owned(E); } // Otherwise, this rule does not apply in C++, at least not for the moment. - if (getLangOptions().CPlusPlus) return; + if (getLangOptions().CPlusPlus) return Owned(E); // GCC seems to also exclude expressions of incomplete enum type. if (const EnumType *T = E->getType()->getAs()) { if (!T->getDecl()->isComplete()) { // FIXME: stupid workaround for a codegen bug! - ImpCastExprToType(E, Context.VoidTy, CK_ToVoid); - return; + E = ImpCastExprToType(E, Context.VoidTy, CK_ToVoid).take(); + return Owned(E); } } - DefaultFunctionArrayLvalueConversion(E); + ExprResult Res = DefaultFunctionArrayLvalueConversion(E); + if (Res.isInvalid()) + return Owned(E); + E = Res.take(); + if (!E->getType()->isVoidType()) RequireCompleteType(E->getExprLoc(), E->getType(), diag::err_incomplete_type); + return Owned(E); } -ExprResult Sema::ActOnFinishFullExpr(Expr *FullExpr) { - if (!FullExpr) +ExprResult Sema::ActOnFinishFullExpr(Expr *FE) { + ExprResult FullExpr = Owned(FE); + + if (!FullExpr.get()) return ExprError(); - if (DiagnoseUnexpandedParameterPack(FullExpr)) + if (DiagnoseUnexpandedParameterPack(FullExpr.get())) return ExprError(); // 13.4.1 ... An overloaded function name shall not be used without arguments @@ -3950,12 +3997,12 @@ ExprResult Sema::ActOnFinishFullExpr(Expr *FullExpr) { // foo; // fooT; - if (FullExpr->getType() == Context.OverloadTy) { + if (FullExpr.get()->getType() == Context.OverloadTy) { ExprResult Fixed - = ResolveAndFixSingleFunctionTemplateSpecialization(FullExpr, + = ResolveAndFixSingleFunctionTemplateSpecialization(FullExpr.get(), /*DoFunctionPointerConversion=*/false, /*Complain=*/true, - FullExpr->getSourceRange(), + FullExpr.get()->getSourceRange(), QualType(), diag::err_addr_ovl_ambiguous); if (Fixed.isInvalid()) @@ -3965,9 +4012,11 @@ ExprResult Sema::ActOnFinishFullExpr(Expr *FullExpr) { } - IgnoredValueConversions(FullExpr); - CheckImplicitConversions(FullExpr); - + FullExpr = IgnoredValueConversions(FullExpr.take()); + if (FullExpr.isInvalid()) + return ExprError(); + + CheckImplicitConversions(FullExpr.get()); return MaybeCreateExprWithCleanups(FullExpr); } diff --git a/lib/Sema/SemaExprObjC.cpp b/lib/Sema/SemaExprObjC.cpp index c5c991f22c..3cc9754b06 100644 --- a/lib/Sema/SemaExprObjC.cpp +++ b/lib/Sema/SemaExprObjC.cpp @@ -246,7 +246,10 @@ bool Sema::CheckMessageArgumentTypes(Expr **Args, unsigned NumArgs, if (Args[i]->isTypeDependent()) continue; - DefaultArgumentPromotion(Args[i]); + ExprResult Result = DefaultArgumentPromotion(Args[i]); + if (Result.isInvalid()) + return true; + Args[i] = Result.take(); } unsigned DiagID = isClassMessage ? diag::warn_class_method_not_found : @@ -305,7 +308,9 @@ bool Sema::CheckMessageArgumentTypes(Expr **Args, unsigned NumArgs, if (Args[i]->isTypeDependent()) continue; - IsError |= DefaultVariadicArgumentPromotion(Args[i], VariadicMethod, 0); + ExprResult Arg = DefaultVariadicArgumentPromotion(Args[i], VariadicMethod, 0); + IsError |= Arg.isInvalid(); + Args[i] = Arg.take(); } } else { // Check for extra arguments to non-variadic methods. @@ -1040,7 +1045,10 @@ ExprResult Sema::BuildInstanceMessage(Expr *Receiver, // If necessary, apply function/array conversion to the receiver. // C99 6.7.5.3p[7,8]. - DefaultFunctionArrayLvalueConversion(Receiver); + ExprResult Result = DefaultFunctionArrayLvalueConversion(Receiver); + if (Result.isInvalid()) + return ExprError(); + Receiver = Result.take(); ReceiverType = Receiver->getType(); } @@ -1162,37 +1170,42 @@ ExprResult Sema::BuildInstanceMessage(Expr *Receiver, << ReceiverType << Receiver->getSourceRange(); if (ReceiverType->isPointerType()) - ImpCastExprToType(Receiver, Context.getObjCIdType(), - CK_BitCast); + Receiver = ImpCastExprToType(Receiver, Context.getObjCIdType(), + CK_BitCast).take(); else { // TODO: specialized warning on null receivers? bool IsNull = Receiver->isNullPointerConstant(Context, Expr::NPC_ValueDependentIsNull); - ImpCastExprToType(Receiver, Context.getObjCIdType(), - IsNull ? CK_NullToPointer : CK_IntegralToPointer); + Receiver = ImpCastExprToType(Receiver, Context.getObjCIdType(), + IsNull ? CK_NullToPointer : CK_IntegralToPointer).take(); } ReceiverType = Receiver->getType(); } - else if (getLangOptions().CPlusPlus && - !PerformContextuallyConvertToObjCId(Receiver)) { - if (ImplicitCastExpr *ICE = dyn_cast(Receiver)) { - Receiver = ICE->getSubExpr(); - ReceiverType = Receiver->getType(); + else { + ExprResult ReceiverRes; + if (getLangOptions().CPlusPlus) + ReceiverRes = PerformContextuallyConvertToObjCId(Receiver); + if (ReceiverRes.isUsable()) { + Receiver = ReceiverRes.take(); + if (ImplicitCastExpr *ICE = dyn_cast(Receiver)) { + Receiver = ICE->getSubExpr(); + ReceiverType = Receiver->getType(); + } + return BuildInstanceMessage(Receiver, + ReceiverType, + SuperLoc, + Sel, + Method, + LBracLoc, + SelectorLoc, + RBracLoc, + move(ArgsIn)); + } else { + // Reject other random receiver types (e.g. structs). + Diag(Loc, diag::err_bad_receiver_type) + << ReceiverType << Receiver->getSourceRange(); + return ExprError(); } - return BuildInstanceMessage(Receiver, - ReceiverType, - SuperLoc, - Sel, - Method, - LBracLoc, - SelectorLoc, - RBracLoc, - move(ArgsIn)); - } else { - // Reject other random receiver types (e.g. structs). - Diag(Loc, diag::err_bad_receiver_type) - << ReceiverType << Receiver->getSourceRange(); - return ExprError(); } } } diff --git a/lib/Sema/SemaInit.cpp b/lib/Sema/SemaInit.cpp index 358e5fb501..0f8d4ddc33 100644 --- a/lib/Sema/SemaInit.cpp +++ b/lib/Sema/SemaInit.cpp @@ -713,15 +713,23 @@ void InitListChecker::CheckSubElementType(const InitializedEntity &Entity, // compatible structure or union type. In the latter case, the // initial value of the object, including unnamed members, is // that of the expression. + ExprResult ExprRes = SemaRef.Owned(expr); if ((ElemType->isRecordType() || ElemType->isVectorType()) && - SemaRef.CheckSingleAssignmentConstraints(ElemType, expr) + SemaRef.CheckSingleAssignmentConstraints(ElemType, ExprRes) == Sema::Compatible) { - SemaRef.DefaultFunctionArrayLvalueConversion(expr); - UpdateStructuredListElement(StructuredList, StructuredIndex, expr); + if (ExprRes.isInvalid()) + hadError = true; + else { + ExprRes = SemaRef.DefaultFunctionArrayLvalueConversion(ExprRes.take()); + if (ExprRes.isInvalid()) + hadError = true; + } + UpdateStructuredListElement(StructuredList, StructuredIndex, + ExprRes.takeAs()); ++Index; return; } - + ExprRes.release(); // Fall through for subaggregate initialization } @@ -2104,6 +2112,7 @@ bool InitializationSequence::isAmbiguous() const { case FK_ReferenceInitDropsQualifiers: case FK_ReferenceInitFailed: case FK_ConversionFailed: + case FK_ConversionFromPropertyFailed: case FK_TooManyInitsForScalar: case FK_ReferenceBindingToInitList: case FK_InitListBadDestinationType: @@ -3129,8 +3138,14 @@ InitializationSequence::InitializationSequence(Sema &S, } for (unsigned I = 0; I != NumArgs; ++I) - if (Args[I]->getObjectKind() == OK_ObjCProperty) - S.ConvertPropertyForRValue(Args[I]); + if (Args[I]->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = S.ConvertPropertyForRValue(Args[I]); + if (Result.isInvalid()) { + SetFailed(FK_ConversionFromPropertyFailed); + return; + } + Args[I] = Result.take(); + } QualType SourceType; Expr *Initializer = 0; @@ -3693,14 +3708,15 @@ InitializationSequence::Perform(Sema &S, case SK_ObjCObjectConversion: case SK_ArrayInit: { assert(Args.size() == 1); - Expr *CurInitExpr = Args.get()[0]; - if (!CurInitExpr) return ExprError(); + CurInit = Args.get()[0]; + if (!CurInit.get()) return ExprError(); // Read from a property when initializing something with it. - if (CurInitExpr->getObjectKind() == OK_ObjCProperty) - S.ConvertPropertyForRValue(CurInitExpr); - - CurInit = ExprResult(CurInitExpr); + if (CurInit.get()->getObjectKind() == OK_ObjCProperty) { + CurInit = S.ConvertPropertyForRValue(CurInit.take()); + if (CurInit.isInvalid()) + return ExprError(); + } break; } @@ -3717,14 +3733,13 @@ InitializationSequence::Perform(Sema &S, if (CurInit.isInvalid()) return ExprError(); - Expr *CurInitExpr = CurInit.get(); - QualType SourceType = CurInitExpr? CurInitExpr->getType() : QualType(); + QualType SourceType = CurInit.get() ? CurInit.get()->getType() : QualType(); switch (Step->Kind) { case SK_ResolveAddressOfOverloadedFunction: // Overload resolution determined which function invoke; update the // initializer to reflect that choice. - S.CheckAddressOfMemberAccess(CurInitExpr, Step->Function.FoundDecl); + S.CheckAddressOfMemberAccess(CurInit.get(), Step->Function.FoundDecl); S.DiagnoseUseOfDecl(Step->Function.FoundDecl, Kind.getLocation()); CurInit = S.FixOverloadedFunctionReference(move(CurInit), Step->Function.FoundDecl, @@ -3742,8 +3757,8 @@ InitializationSequence::Perform(Sema &S, // Casts to inaccessible base classes are allowed with C-style casts. bool IgnoreBaseAccess = Kind.isCStyleOrFunctionalCast(); if (S.CheckDerivedToBaseConversion(SourceType, Step->Type, - CurInitExpr->getLocStart(), - CurInitExpr->getSourceRange(), + CurInit.get()->getLocStart(), + CurInit.get()->getSourceRange(), &BasePath, IgnoreBaseAccess)) return ExprError(); @@ -3752,7 +3767,7 @@ InitializationSequence::Perform(Sema &S, if (const PointerType *Pointer = T->getAs()) T = Pointer->getPointeeType(); if (const RecordType *RecordTy = T->getAs()) - S.MarkVTableUsed(CurInitExpr->getLocStart(), + S.MarkVTableUsed(CurInit.get()->getLocStart(), cast(RecordTy->getDecl())); } @@ -3771,21 +3786,21 @@ InitializationSequence::Perform(Sema &S, } case SK_BindReference: - if (FieldDecl *BitField = CurInitExpr->getBitField()) { + if (FieldDecl *BitField = CurInit.get()->getBitField()) { // References cannot bind to bit fields (C++ [dcl.init.ref]p5). S.Diag(Kind.getLocation(), diag::err_reference_bind_to_bitfield) << Entity.getType().isVolatileQualified() << BitField->getDeclName() - << CurInitExpr->getSourceRange(); + << CurInit.get()->getSourceRange(); S.Diag(BitField->getLocation(), diag::note_bitfield_decl); return ExprError(); } - if (CurInitExpr->refersToVectorElement()) { + if (CurInit.get()->refersToVectorElement()) { // References cannot bind to vector elements. S.Diag(Kind.getLocation(), diag::err_reference_bind_to_vector_element) << Entity.getType().isVolatileQualified() - << CurInitExpr->getSourceRange(); + << CurInit.get()->getSourceRange(); PrintInitLocationNote(S, Entity); return ExprError(); } @@ -3793,7 +3808,7 @@ InitializationSequence::Perform(Sema &S, // Reference binding does not have any corresponding ASTs. // Check exception specifications - if (S.CheckExceptionSpecCompatibility(CurInitExpr, DestType)) + if (S.CheckExceptionSpecCompatibility(CurInit.get(), DestType)) return ExprError(); break; @@ -3802,7 +3817,7 @@ InitializationSequence::Perform(Sema &S, // Reference binding does not have any corresponding ASTs. // Check exception specifications - if (S.CheckExceptionSpecCompatibility(CurInitExpr, DestType)) + if (S.CheckExceptionSpecCompatibility(CurInit.get(), DestType)) return ExprError(); break; @@ -3824,13 +3839,14 @@ InitializationSequence::Perform(Sema &S, if (CXXConstructorDecl *Constructor = dyn_cast(Fn)) { // Build a call to the selected constructor. ASTOwningVector ConstructorArgs(S); - SourceLocation Loc = CurInitExpr->getLocStart(); + SourceLocation Loc = CurInit.get()->getLocStart(); CurInit.release(); // Ownership transferred into MultiExprArg, below. // Determine the arguments required to actually perform the constructor // call. + Expr *Arg = CurInit.get(); if (S.CompleteConstructorCall(Constructor, - MultiExprArg(&CurInitExpr, 1), + MultiExprArg(&Arg, 1), Loc, ConstructorArgs)) return ExprError(); @@ -3858,23 +3874,22 @@ InitializationSequence::Perform(Sema &S, // Build a call to the conversion function. CXXConversionDecl *Conversion = cast(Fn); IsLvalue = Conversion->getResultType()->isLValueReferenceType(); - S.CheckMemberOperatorAccess(Kind.getLocation(), CurInitExpr, 0, + S.CheckMemberOperatorAccess(Kind.getLocation(), CurInit.get(), 0, FoundFn); S.DiagnoseUseOfDecl(FoundFn, Kind.getLocation()); // FIXME: Should we move this initialization into a separate // derived-to-base conversion? I believe the answer is "no", because // we don't want to turn off access control here for c-style casts. - if (S.PerformObjectArgumentInitialization(CurInitExpr, /*Qualifier=*/0, - FoundFn, Conversion)) + ExprResult CurInitExprRes = + S.PerformObjectArgumentInitialization(CurInit.take(), /*Qualifier=*/0, + FoundFn, Conversion); + if(CurInitExprRes.isInvalid()) return ExprError(); - - // Do a little dance to make sure that CurInit has the proper - // pointer. - CurInit.release(); + CurInit = move(CurInitExprRes); // Build the actual call to the conversion function. - CurInit = S.BuildCXXMemberCallExpr(CurInitExpr, FoundFn, Conversion); + CurInit = S.BuildCXXMemberCallExpr(CurInit.get(), FoundFn, Conversion); if (CurInit.isInvalid() || !CurInit.get()) return ExprError(); @@ -3888,23 +3903,21 @@ InitializationSequence::Perform(Sema &S, if (RequiresCopy || shouldBindAsTemporary(Entity)) CurInit = S.MaybeBindToTemporary(CurInit.takeAs()); else if (CreatedObject && shouldDestroyTemporary(Entity)) { - CurInitExpr = static_cast(CurInit.get()); - QualType T = CurInitExpr->getType(); + QualType T = CurInit.get()->getType(); if (const RecordType *Record = T->getAs()) { CXXDestructorDecl *Destructor = S.LookupDestructor(cast(Record->getDecl())); - S.CheckDestructorAccess(CurInitExpr->getLocStart(), Destructor, + S.CheckDestructorAccess(CurInit.get()->getLocStart(), Destructor, S.PDiag(diag::err_access_dtor_temp) << T); - S.MarkDeclarationReferenced(CurInitExpr->getLocStart(), Destructor); - S.DiagnoseUseOfDecl(Destructor, CurInitExpr->getLocStart()); + S.MarkDeclarationReferenced(CurInit.get()->getLocStart(), Destructor); + S.DiagnoseUseOfDecl(Destructor, CurInit.get()->getLocStart()); } } - CurInitExpr = CurInit.takeAs(); // FIXME: xvalues CurInit = S.Owned(ImplicitCastExpr::Create(S.Context, - CurInitExpr->getType(), - CastKind, CurInitExpr, 0, + CurInit.get()->getType(), + CastKind, CurInit.get(), 0, IsLvalue ? VK_LValue : VK_RValue)); if (RequiresCopy) @@ -3924,25 +3937,23 @@ InitializationSequence::Perform(Sema &S, (Step->Kind == SK_QualificationConversionXValue ? VK_XValue : VK_RValue); - S.ImpCastExprToType(CurInitExpr, Step->Type, CK_NoOp, VK); - CurInit.release(); - CurInit = S.Owned(CurInitExpr); + CurInit = S.ImpCastExprToType(CurInit.take(), Step->Type, CK_NoOp, VK); break; } case SK_ConversionSequence: { - if (S.PerformImplicitConversion(CurInitExpr, Step->Type, *Step->ICS, - getAssignmentAction(Entity), - Kind.isCStyleOrFunctionalCast())) + ExprResult CurInitExprRes = + S.PerformImplicitConversion(CurInit.get(), Step->Type, *Step->ICS, + getAssignmentAction(Entity), + Kind.isCStyleOrFunctionalCast()); + if (CurInitExprRes.isInvalid()) return ExprError(); - - CurInit.release(); - CurInit = S.Owned(CurInitExpr); + CurInit = move(CurInitExprRes); break; } case SK_ListInitialization: { - InitListExpr *InitList = cast(CurInitExpr); + InitListExpr *InitList = cast(CurInit.get()); QualType Ty = Step->Type; if (S.CheckInitList(Entity, InitList, ResultType? *ResultType : Ty)) return ExprError(); @@ -4075,54 +4086,57 @@ InitializationSequence::Perform(Sema &S, } case SK_CAssignment: { - QualType SourceType = CurInitExpr->getType(); + QualType SourceType = CurInit.get()->getType(); + ExprResult Result = move(CurInit); Sema::AssignConvertType ConvTy = - S.CheckSingleAssignmentConstraints(Step->Type, CurInitExpr); + S.CheckSingleAssignmentConstraints(Step->Type, Result); + if (Result.isInvalid()) + return ExprError(); + CurInit = move(Result); // If this is a call, allow conversion to a transparent union. + ExprResult CurInitExprRes = move(CurInit); if (ConvTy != Sema::Compatible && Entity.getKind() == InitializedEntity::EK_Parameter && - S.CheckTransparentUnionArgumentConstraints(Step->Type, CurInitExpr) + S.CheckTransparentUnionArgumentConstraints(Step->Type, CurInitExprRes) == Sema::Compatible) ConvTy = Sema::Compatible; + if (CurInitExprRes.isInvalid()) + return ExprError(); + CurInit = move(CurInitExprRes); bool Complained; if (S.DiagnoseAssignmentResult(ConvTy, Kind.getLocation(), Step->Type, SourceType, - CurInitExpr, + CurInit.get(), getAssignmentAction(Entity), &Complained)) { PrintInitLocationNote(S, Entity); return ExprError(); } else if (Complained) PrintInitLocationNote(S, Entity); - - CurInit.release(); - CurInit = S.Owned(CurInitExpr); break; } case SK_StringInit: { QualType Ty = Step->Type; - CheckStringInit(CurInitExpr, ResultType ? *ResultType : Ty, + CheckStringInit(CurInit.get(), ResultType ? *ResultType : Ty, S.Context.getAsArrayType(Ty), S); break; } case SK_ObjCObjectConversion: - S.ImpCastExprToType(CurInitExpr, Step->Type, + CurInit = S.ImpCastExprToType(CurInit.take(), Step->Type, CK_ObjCObjectLValueCast, - S.CastCategory(CurInitExpr)); - CurInit.release(); - CurInit = S.Owned(CurInitExpr); + S.CastCategory(CurInit.get())); break; case SK_ArrayInit: // Okay: we checked everything before creating this step. Note that // this is a GNU extension. S.Diag(Kind.getLocation(), diag::ext_array_init_copy) - << Step->Type << CurInitExpr->getType() - << CurInitExpr->getSourceRange(); + << Step->Type << CurInit.get()->getType() + << CurInit.get()->getSourceRange(); // If the destination type is an incomplete array type, update the // type accordingly. @@ -4130,7 +4144,7 @@ InitializationSequence::Perform(Sema &S, if (const IncompleteArrayType *IncompleteDest = S.Context.getAsIncompleteArrayType(Step->Type)) { if (const ConstantArrayType *ConstantSource - = S.Context.getAsConstantArrayType(CurInitExpr->getType())) { + = S.Context.getAsConstantArrayType(CurInit.get()->getType())) { *ResultType = S.Context.getConstantArrayType( IncompleteDest->getElementType(), ConstantSource->getSize(), @@ -4290,6 +4304,11 @@ bool InitializationSequence::Diagnose(Sema &S, << Args[0]->getSourceRange(); break; } + + case FK_ConversionFromPropertyFailed: + // No-op. This error has already been reported. + break; + case FK_TooManyInitsForScalar: { SourceRange R; @@ -4489,6 +4508,10 @@ void InitializationSequence::dump(llvm::raw_ostream &OS) const { OS << "conversion failed"; break; + case FK_ConversionFromPropertyFailed: + OS << "conversion from property failed"; + break; + case FK_TooManyInitsForScalar: OS << "too many initializers for scalar"; break; diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp index 5b444c14d6..3212c36b9a 100644 --- a/lib/Sema/SemaOverload.cpp +++ b/lib/Sema/SemaOverload.cpp @@ -36,12 +36,14 @@ using namespace sema; /// A convenience routine for creating a decayed reference to a /// function. -static Expr * +static ExprResult CreateFunctionRefExpr(Sema &S, FunctionDecl *Fn, SourceLocation Loc = SourceLocation()) { - Expr *E = new (S.Context) DeclRefExpr(Fn, Fn->getType(), VK_LValue, Loc); - S.DefaultFunctionArrayConversion(E); - return E; + ExprResult E = S.Owned(new (S.Context) DeclRefExpr(Fn, Fn->getType(), VK_LValue, Loc)); + E = S.DefaultFunctionArrayConversion(E.take()); + if (E.isInvalid()) + return ExprError(); + return move(E); } static bool IsStandardConversion(Sema &S, Expr* From, QualType ToType, @@ -886,20 +888,19 @@ bool Sema::TryImplicitConversion(InitializationSequence &Sequence, } /// PerformImplicitConversion - Perform an implicit conversion of the -/// expression From to the type ToType. Returns true if there was an -/// error, false otherwise. The expression From is replaced with the +/// expression From to the type ToType. Returns the /// converted expression. Flavor is the kind of conversion we're /// performing, used in the error message. If @p AllowExplicit, /// explicit user-defined conversions are permitted. -bool -Sema::PerformImplicitConversion(Expr *&From, QualType ToType, +ExprResult +Sema::PerformImplicitConversion(Expr *From, QualType ToType, AssignmentAction Action, bool AllowExplicit) { ImplicitConversionSequence ICS; return PerformImplicitConversion(From, ToType, Action, AllowExplicit, ICS); } -bool -Sema::PerformImplicitConversion(Expr *&From, QualType ToType, +ExprResult +Sema::PerformImplicitConversion(Expr *From, QualType ToType, AssignmentAction Action, bool AllowExplicit, ImplicitConversionSequence& ICS) { ICS = clang::TryImplicitConversion(*this, From, ToType, @@ -3525,8 +3526,8 @@ TryObjectArgumentInitialization(Sema &S, QualType OrigFromType, /// PerformObjectArgumentInitialization - Perform initialization of /// the implicit object parameter for the given Method with the given /// expression. -bool -Sema::PerformObjectArgumentInitialization(Expr *&From, +ExprResult +Sema::PerformObjectArgumentInitialization(Expr *From, NestedNameSpecifier *Qualifier, NamedDecl *FoundDecl, CXXMethodDecl *Method) { @@ -3562,7 +3563,7 @@ Sema::PerformObjectArgumentInitialization(Expr *&From, << From->getSourceRange(); Diag(Method->getLocation(), diag::note_previous_decl) << Method->getDeclName(); - return true; + return ExprError(); } } @@ -3571,13 +3572,18 @@ Sema::PerformObjectArgumentInitialization(Expr *&From, << ImplicitParamRecordType << FromRecordType << From->getSourceRange(); } - if (ICS.Standard.Second == ICK_Derived_To_Base) - return PerformObjectMemberConversion(From, Qualifier, FoundDecl, Method); + if (ICS.Standard.Second == ICK_Derived_To_Base) { + ExprResult FromRes = + PerformObjectMemberConversion(From, Qualifier, FoundDecl, Method); + if (FromRes.isInvalid()) + return ExprError(); + From = FromRes.take(); + } if (!Context.hasSameType(From->getType(), DestType)) - ImpCastExprToType(From, DestType, CK_NoOp, - From->getType()->isPointerType() ? VK_RValue : VK_LValue); - return false; + From = ImpCastExprToType(From, DestType, CK_NoOp, + From->getType()->isPointerType() ? VK_RValue : VK_LValue).take(); + return Owned(From); } /// TryContextuallyConvertToBool - Attempt to contextually convert the @@ -3595,7 +3601,7 @@ TryContextuallyConvertToBool(Sema &S, Expr *From) { /// PerformContextuallyConvertToBool - Perform a contextual conversion /// of the expression From to bool (C++0x [conv]p3). -bool Sema::PerformContextuallyConvertToBool(Expr *&From) { +ExprResult Sema::PerformContextuallyConvertToBool(Expr *From) { ImplicitConversionSequence ICS = TryContextuallyConvertToBool(*this, From); if (!ICS.isBad()) return PerformImplicitConversion(From, Context.BoolTy, ICS, AA_Converting); @@ -3604,7 +3610,7 @@ bool Sema::PerformContextuallyConvertToBool(Expr *&From) { return Diag(From->getSourceRange().getBegin(), diag::err_typecheck_bool_condition) << From->getType() << From->getSourceRange(); - return true; + return ExprError(); } /// TryContextuallyConvertToObjCId - Attempt to contextually convert the @@ -3622,12 +3628,12 @@ TryContextuallyConvertToObjCId(Sema &S, Expr *From) { /// PerformContextuallyConvertToObjCId - Perform a contextual conversion /// of the expression From to 'id'. -bool Sema::PerformContextuallyConvertToObjCId(Expr *&From) { +ExprResult Sema::PerformContextuallyConvertToObjCId(Expr *From) { QualType Ty = Context.getObjCIdType(); ImplicitConversionSequence ICS = TryContextuallyConvertToObjCId(*this, From); if (!ICS.isBad()) return PerformImplicitConversion(From, Ty, ICS, AA_Converting); - return true; + return ExprError(); } /// \brief Attempt to convert the given expression to an integral or @@ -7565,19 +7571,20 @@ ExprResult Sema::ResolveAndFixSingleFunctionTemplateSpecialization( assert(SrcExpr->getType() == Context.OverloadTy); DeclAccessPair Found; - Expr* SingleFunctionExpression = 0; + ExprResult SingleFunctionExpression; if (FunctionDecl* Fn = ResolveSingleFunctionTemplateSpecialization( SrcExpr, false, // false -> Complain &Found)) { if (!DiagnoseUseOfDecl(Fn, SrcExpr->getSourceRange().getBegin())) { // mark the expression as resolved to Fn - SingleFunctionExpression = FixOverloadedFunctionReference(SrcExpr, - Found, Fn); + SingleFunctionExpression = Owned(FixOverloadedFunctionReference(SrcExpr, + Found, Fn)); if (DoFunctionPointerConverion) - DefaultFunctionArrayLvalueConversion(SingleFunctionExpression); + SingleFunctionExpression = + DefaultFunctionArrayLvalueConversion(SingleFunctionExpression.take()); } } - if (!SingleFunctionExpression) { + if (!SingleFunctionExpression.isUsable()) { if (Complain) { OverloadExpr* oe = OverloadExpr::find(SrcExpr).Expression; Diag(OpRangeForComplaining.getBegin(), DiagIDForComplaining) @@ -7847,8 +7854,12 @@ Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc, unsigned OpcIn, // TODO: provide better source location info. DeclarationNameInfo OpNameInfo(OpName, OpLoc); - if (Input->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Input); + if (Input->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(Input); + if (Result.isInvalid()) + return ExprError(); + Input = Result.take(); + } Expr *Args[2] = { Input, 0 }; unsigned NumArgs = 1; @@ -7919,9 +7930,12 @@ Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc, unsigned OpcIn, if (CXXMethodDecl *Method = dyn_cast(FnDecl)) { CheckMemberOperatorAccess(OpLoc, Args[0], 0, Best->FoundDecl); - if (PerformObjectArgumentInitialization(Input, /*Qualifier=*/0, - Best->FoundDecl, Method)) + ExprResult InputRes = + PerformObjectArgumentInitialization(Input, /*Qualifier=*/0, + Best->FoundDecl, Method); + if (InputRes.isInvalid()) return ExprError(); + Input = InputRes.take(); } else { // Convert the arguments. ExprResult InputInit @@ -7943,11 +7957,13 @@ Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc, unsigned OpcIn, ResultTy = ResultTy.getNonLValueExprType(Context); // Build the actual expression node. - Expr *FnExpr = CreateFunctionRefExpr(*this, FnDecl); + ExprResult FnExpr = CreateFunctionRefExpr(*this, FnDecl); + if (FnExpr.isInvalid()) + return ExprError(); Args[0] = Input; CallExpr *TheCall = - new (Context) CXXOperatorCallExpr(Context, Op, FnExpr, + new (Context) CXXOperatorCallExpr(Context, Op, FnExpr.take(), Args, NumArgs, ResultTy, VK, OpLoc); if (CheckCallReturnType(FnDecl->getResultType(), OpLoc, TheCall, @@ -7959,38 +7975,40 @@ Sema::CreateOverloadedUnaryOp(SourceLocation OpLoc, unsigned OpcIn, // We matched a built-in operator. Convert the arguments, then // break out so that we will build the appropriate built-in // operator node. - if (PerformImplicitConversion(Input, Best->BuiltinTypes.ParamTypes[0], - Best->Conversions[0], AA_Passing)) - return ExprError(); - - break; - } - } - - case OR_No_Viable_Function: - // No viable function; fall through to handling this as a - // built-in operator, which will produce an error message for us. + ExprResult InputRes = + PerformImplicitConversion(Input, Best->BuiltinTypes.ParamTypes[0], + Best->Conversions[0], AA_Passing); + if (InputRes.isInvalid()) + return ExprError(); + Input = InputRes.take(); break; + } + } - case OR_Ambiguous: - Diag(OpLoc, diag::err_ovl_ambiguous_oper_unary) - << UnaryOperator::getOpcodeStr(Opc) - << Input->getType() - << Input->getSourceRange(); - CandidateSet.NoteCandidates(*this, OCD_ViableCandidates, - Args, NumArgs, - UnaryOperator::getOpcodeStr(Opc), OpLoc); - return ExprError(); + case OR_No_Viable_Function: + // No viable function; fall through to handling this as a + // built-in operator, which will produce an error message for us. + break; - case OR_Deleted: - Diag(OpLoc, diag::err_ovl_deleted_oper) - << Best->Function->isDeleted() + case OR_Ambiguous: + Diag(OpLoc, diag::err_ovl_ambiguous_oper_unary) << UnaryOperator::getOpcodeStr(Opc) - << getDeletedOrUnavailableSuffix(Best->Function) + << Input->getType() << Input->getSourceRange(); - CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs); - return ExprError(); - } + CandidateSet.NoteCandidates(*this, OCD_ViableCandidates, + Args, NumArgs, + UnaryOperator::getOpcodeStr(Opc), OpLoc); + return ExprError(); + + case OR_Deleted: + Diag(OpLoc, diag::err_ovl_deleted_oper) + << Best->Function->isDeleted() + << UnaryOperator::getOpcodeStr(Opc) + << getDeletedOrUnavailableSuffix(Best->Function) + << Input->getSourceRange(); + CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs); + return ExprError(); + } // Either we found no viable overloaded operator or we matched a // built-in operator. In either case, fall through to trying to @@ -8065,8 +8083,12 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc, } // Always do property rvalue conversions on the RHS. - if (Args[1]->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Args[1]); + if (Args[1]->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(Args[1]); + if (Result.isInvalid()) + return ExprError(); + Args[1] = Result.take(); + } // The LHS is more complicated. if (Args[0]->getObjectKind() == OK_ObjCProperty) { @@ -8094,7 +8116,10 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc, return CreateBuiltinBinOp(OpLoc, Opc, Args[0], Args[1]); } - ConvertPropertyForRValue(Args[0]); + ExprResult Result = ConvertPropertyForRValue(Args[0]); + if (Result.isInvalid()) + return ExprError(); + Args[0] = Result.take(); } // If this is the assignment operator, we only perform overload resolution @@ -8155,10 +8180,12 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc, if (Arg1.isInvalid()) return ExprError(); - if (PerformObjectArgumentInitialization(Args[0], /*Qualifier=*/0, - Best->FoundDecl, Method)) + ExprResult Arg0 = + PerformObjectArgumentInitialization(Args[0], /*Qualifier=*/0, + Best->FoundDecl, Method); + if (Arg0.isInvalid()) return ExprError(); - + Args[0] = Arg0.takeAs(); Args[1] = RHS = Arg1.takeAs(); } else { // Convert the arguments. @@ -8188,10 +8215,12 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc, ResultTy = ResultTy.getNonLValueExprType(Context); // Build the actual expression node. - Expr *FnExpr = CreateFunctionRefExpr(*this, FnDecl, OpLoc); + ExprResult FnExpr = CreateFunctionRefExpr(*this, FnDecl, OpLoc); + if (FnExpr.isInvalid()) + return ExprError(); CXXOperatorCallExpr *TheCall = - new (Context) CXXOperatorCallExpr(Context, Op, FnExpr, + new (Context) CXXOperatorCallExpr(Context, Op, FnExpr.take(), Args, 2, ResultTy, VK, OpLoc); if (CheckCallReturnType(FnDecl->getResultType(), OpLoc, TheCall, @@ -8203,12 +8232,19 @@ Sema::CreateOverloadedBinOp(SourceLocation OpLoc, // We matched a built-in operator. Convert the arguments, then // break out so that we will build the appropriate built-in // operator node. - if (PerformImplicitConversion(Args[0], Best->BuiltinTypes.ParamTypes[0], - Best->Conversions[0], AA_Passing) || - PerformImplicitConversion(Args[1], Best->BuiltinTypes.ParamTypes[1], - Best->Conversions[1], AA_Passing)) + ExprResult ArgsRes0 = + PerformImplicitConversion(Args[0], Best->BuiltinTypes.ParamTypes[0], + Best->Conversions[0], AA_Passing); + if (ArgsRes0.isInvalid()) return ExprError(); + Args[0] = ArgsRes0.take(); + ExprResult ArgsRes1 = + PerformImplicitConversion(Args[1], Best->BuiltinTypes.ParamTypes[1], + Best->Conversions[1], AA_Passing); + if (ArgsRes1.isInvalid()) + return ExprError(); + Args[1] = ArgsRes1.take(); break; } } @@ -8297,10 +8333,18 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc, RLoc)); } - if (Args[0]->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Args[0]); - if (Args[1]->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Args[1]); + if (Args[0]->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(Args[0]); + if (Result.isInvalid()) + return ExprError(); + Args[0] = Result.take(); + } + if (Args[1]->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(Args[1]); + if (Result.isInvalid()) + return ExprError(); + Args[1] = Result.take(); + } // Build an empty overload set. OverloadCandidateSet CandidateSet(LLoc); @@ -8331,9 +8375,12 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc, // Convert the arguments. CXXMethodDecl *Method = cast(FnDecl); - if (PerformObjectArgumentInitialization(Args[0], /*Qualifier=*/0, - Best->FoundDecl, Method)) + ExprResult Arg0 = + PerformObjectArgumentInitialization(Args[0], /*Qualifier=*/0, + Best->FoundDecl, Method); + if (Arg0.isInvalid()) return ExprError(); + Args[0] = Arg0.take(); // Convert the arguments. ExprResult InputInit @@ -8353,11 +8400,13 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc, ResultTy = ResultTy.getNonLValueExprType(Context); // Build the actual expression node. - Expr *FnExpr = CreateFunctionRefExpr(*this, FnDecl, LLoc); + ExprResult FnExpr = CreateFunctionRefExpr(*this, FnDecl, LLoc); + if (FnExpr.isInvalid()) + return ExprError(); CXXOperatorCallExpr *TheCall = new (Context) CXXOperatorCallExpr(Context, OO_Subscript, - FnExpr, Args, 2, + FnExpr.take(), Args, 2, ResultTy, VK, RLoc); if (CheckCallReturnType(FnDecl->getResultType(), LLoc, TheCall, @@ -8369,11 +8418,19 @@ Sema::CreateOverloadedArraySubscriptExpr(SourceLocation LLoc, // We matched a built-in operator. Convert the arguments, then // break out so that we will build the appropriate built-in // operator node. - if (PerformImplicitConversion(Args[0], Best->BuiltinTypes.ParamTypes[0], - Best->Conversions[0], AA_Passing) || - PerformImplicitConversion(Args[1], Best->BuiltinTypes.ParamTypes[1], - Best->Conversions[1], AA_Passing)) + ExprResult ArgsRes0 = + PerformImplicitConversion(Args[0], Best->BuiltinTypes.ParamTypes[0], + Best->Conversions[0], AA_Passing); + if (ArgsRes0.isInvalid()) return ExprError(); + Args[0] = ArgsRes0.take(); + + ExprResult ArgsRes1 = + PerformImplicitConversion(Args[1], Best->BuiltinTypes.ParamTypes[1], + Best->Conversions[1], AA_Passing); + if (ArgsRes1.isInvalid()) + return ExprError(); + Args[1] = ArgsRes1.take(); break; } @@ -8559,12 +8616,14 @@ Sema::BuildCallToMemberFunction(Scope *S, Expr *MemExprE, // Convert the object argument (for a non-static member function call). // We only need to do this if there was actually an overload; otherwise // it was done at lookup. - Expr *ObjectArg = MemExpr->getBase(); - if (!Method->isStatic() && - PerformObjectArgumentInitialization(ObjectArg, Qualifier, - FoundDecl, Method)) - return ExprError(); - MemExpr->setBase(ObjectArg); + if (!Method->isStatic()) { + ExprResult ObjectArg = + PerformObjectArgumentInitialization(MemExpr->getBase(), Qualifier, + FoundDecl, Method); + if (ObjectArg.isInvalid()) + return ExprError(); + MemExpr->setBase(ObjectArg.take()); + } // Convert the rest of the arguments const FunctionProtoType *Proto = @@ -8584,15 +8643,19 @@ Sema::BuildCallToMemberFunction(Scope *S, Expr *MemExprE, /// overloaded function call operator (@c operator()) or performing a /// user-defined conversion on the object argument. ExprResult -Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, +Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Obj, SourceLocation LParenLoc, Expr **Args, unsigned NumArgs, SourceLocation RParenLoc) { - if (Object->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Object); + ExprResult Object = Owned(Obj); + if (Object.get()->getObjectKind() == OK_ObjCProperty) { + Object = ConvertPropertyForRValue(Object.take()); + if (Object.isInvalid()) + return ExprError(); + } - assert(Object->getType()->isRecordType() && "Requires object type argument"); - const RecordType *Record = Object->getType()->getAs(); + assert(Object.get()->getType()->isRecordType() && "Requires object type argument"); + const RecordType *Record = Object.get()->getType()->getAs(); // C++ [over.call.object]p1: // If the primary-expression E in the function call syntax @@ -8604,9 +8667,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, OverloadCandidateSet CandidateSet(LParenLoc); DeclarationName OpName = Context.DeclarationNames.getCXXOperatorName(OO_Call); - if (RequireCompleteType(LParenLoc, Object->getType(), + if (RequireCompleteType(LParenLoc, Object.get()->getType(), PDiag(diag::err_incomplete_object_call) - << Object->getSourceRange())) + << Object.get()->getSourceRange())) return true; LookupResult R(*this, OpName, LParenLoc, LookupOrdinaryName); @@ -8615,8 +8678,8 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, for (LookupResult::iterator Oper = R.begin(), OperEnd = R.end(); Oper != OperEnd; ++Oper) { - AddMethodCandidate(Oper.getPair(), Object->getType(), - Object->Classify(Context), Args, NumArgs, CandidateSet, + AddMethodCandidate(Oper.getPair(), Object.get()->getType(), + Object.get()->Classify(Context), Args, NumArgs, CandidateSet, /*SuppressUserConversions=*/ false); } @@ -8661,12 +8724,12 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, if (const FunctionProtoType *Proto = ConvType->getAs()) AddSurrogateCandidate(Conv, I.getPair(), ActingContext, Proto, - Object, Args, NumArgs, CandidateSet); + Object.get(), Args, NumArgs, CandidateSet); } // Perform overload resolution. OverloadCandidateSet::iterator Best; - switch (CandidateSet.BestViableFunction(*this, Object->getLocStart(), + switch (CandidateSet.BestViableFunction(*this, Object.get()->getLocStart(), Best)) { case OR_Success: // Overload resolution succeeded; we'll build the appropriate call @@ -8675,30 +8738,30 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, case OR_No_Viable_Function: if (CandidateSet.empty()) - Diag(Object->getSourceRange().getBegin(), diag::err_ovl_no_oper) - << Object->getType() << /*call*/ 1 - << Object->getSourceRange(); + Diag(Object.get()->getSourceRange().getBegin(), diag::err_ovl_no_oper) + << Object.get()->getType() << /*call*/ 1 + << Object.get()->getSourceRange(); else - Diag(Object->getSourceRange().getBegin(), + Diag(Object.get()->getSourceRange().getBegin(), diag::err_ovl_no_viable_object_call) - << Object->getType() << Object->getSourceRange(); + << Object.get()->getType() << Object.get()->getSourceRange(); CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs); break; case OR_Ambiguous: - Diag(Object->getSourceRange().getBegin(), + Diag(Object.get()->getSourceRange().getBegin(), diag::err_ovl_ambiguous_object_call) - << Object->getType() << Object->getSourceRange(); + << Object.get()->getType() << Object.get()->getSourceRange(); CandidateSet.NoteCandidates(*this, OCD_ViableCandidates, Args, NumArgs); break; case OR_Deleted: - Diag(Object->getSourceRange().getBegin(), + Diag(Object.get()->getSourceRange().getBegin(), diag::err_ovl_deleted_object_call) << Best->Function->isDeleted() - << Object->getType() + << Object.get()->getType() << getDeletedOrUnavailableSuffix(Best->Function) - << Object->getSourceRange(); + << Object.get()->getSourceRange(); CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs); break; } @@ -8713,7 +8776,7 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, = cast( Best->Conversions[0].UserDefined.ConversionFunction); - CheckMemberOperatorAccess(LParenLoc, Object, 0, Best->FoundDecl); + CheckMemberOperatorAccess(LParenLoc, Object.get(), 0, Best->FoundDecl); DiagnoseUseOfDecl(Best->FoundDecl, LParenLoc); // We selected one of the surrogate functions that converts the @@ -8722,7 +8785,7 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, // Create an implicit member expr to refer to the conversion operator. // and then call it. - ExprResult Call = BuildCXXMemberCallExpr(Object, Best->FoundDecl, Conv); + ExprResult Call = BuildCXXMemberCallExpr(Object.get(), Best->FoundDecl, Conv); if (Call.isInvalid()) return ExprError(); @@ -8731,7 +8794,7 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, } MarkDeclarationReferenced(LParenLoc, Best->Function); - CheckMemberOperatorAccess(LParenLoc, Object, 0, Best->FoundDecl); + CheckMemberOperatorAccess(LParenLoc, Object.get(), 0, Best->FoundDecl); DiagnoseUseOfDecl(Best->FoundDecl, LParenLoc); // We found an overloaded operator(). Build a CXXOperatorCallExpr @@ -8754,11 +8817,13 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, } else { MethodArgs = new Expr*[NumArgs + 1]; } - MethodArgs[0] = Object; + MethodArgs[0] = Object.get(); for (unsigned ArgIdx = 0; ArgIdx < NumArgs; ++ArgIdx) MethodArgs[ArgIdx + 1] = Args[ArgIdx]; - Expr *NewFn = CreateFunctionRefExpr(*this, Method); + ExprResult NewFn = CreateFunctionRefExpr(*this, Method); + if (NewFn.isInvalid()) + return true; // Once we've built TheCall, all of the expressions are properly // owned. @@ -8767,7 +8832,7 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, ResultTy = ResultTy.getNonLValueExprType(Context); CXXOperatorCallExpr *TheCall = - new (Context) CXXOperatorCallExpr(Context, OO_Call, NewFn, + new (Context) CXXOperatorCallExpr(Context, OO_Call, NewFn.take(), MethodArgs, NumArgs + 1, ResultTy, VK, RParenLoc); delete [] MethodArgs; @@ -8786,10 +8851,14 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, bool IsError = false; // Initialize the implicit object parameter. - IsError |= PerformObjectArgumentInitialization(Object, /*Qualifier=*/0, - Best->FoundDecl, Method); - TheCall->setArg(0, Object); - + ExprResult ObjRes = + PerformObjectArgumentInitialization(Object.get(), /*Qualifier=*/0, + Best->FoundDecl, Method); + if (ObjRes.isInvalid()) + IsError = true; + else + Object = move(ObjRes); + TheCall->setArg(0, Object.take()); // Check the argument types. for (unsigned i = 0; i != NumArgsToCheck; i++) { @@ -8825,9 +8894,9 @@ Sema::BuildCallToObjectOfClassType(Scope *S, Expr *Object, if (Proto->isVariadic()) { // Promote the arguments (C99 6.5.2.2p7). for (unsigned i = NumArgsInProto; i != NumArgs; i++) { - Expr *Arg = Args[i]; - IsError |= DefaultVariadicArgumentPromotion(Arg, VariadicMethod, 0); - TheCall->setArg(i + 1, Arg); + ExprResult Arg = DefaultVariadicArgumentPromotion(Args[i], VariadicMethod, 0); + IsError |= Arg.isInvalid(); + TheCall->setArg(i + 1, Arg.take()); } } @@ -8847,8 +8916,12 @@ Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc) { assert(Base->getType()->isRecordType() && "left-hand side must have class type"); - if (Base->getObjectKind() == OK_ObjCProperty) - ConvertPropertyForRValue(Base); + if (Base->getObjectKind() == OK_ObjCProperty) { + ExprResult Result = ConvertPropertyForRValue(Base); + if (Result.isInvalid()) + return ExprError(); + Base = Result.take(); + } SourceLocation Loc = Base->getExprLoc(); @@ -8917,18 +8990,23 @@ Sema::BuildOverloadedArrowExpr(Scope *S, Expr *Base, SourceLocation OpLoc) { // Convert the object parameter. CXXMethodDecl *Method = cast(Best->Function); - if (PerformObjectArgumentInitialization(Base, /*Qualifier=*/0, - Best->FoundDecl, Method)) + ExprResult BaseResult = + PerformObjectArgumentInitialization(Base, /*Qualifier=*/0, + Best->FoundDecl, Method); + if (BaseResult.isInvalid()) return ExprError(); + Base = BaseResult.take(); // Build the operator call. - Expr *FnExpr = CreateFunctionRefExpr(*this, Method); + ExprResult FnExpr = CreateFunctionRefExpr(*this, Method); + if (FnExpr.isInvalid()) + return ExprError(); QualType ResultTy = Method->getResultType(); ExprValueKind VK = Expr::getValueKindForType(ResultTy); ResultTy = ResultTy.getNonLValueExprType(Context); CXXOperatorCallExpr *TheCall = - new (Context) CXXOperatorCallExpr(Context, OO_Arrow, FnExpr, + new (Context) CXXOperatorCallExpr(Context, OO_Arrow, FnExpr.take(), &Base, 1, ResultTy, VK, OpLoc); if (CheckCallReturnType(Method->getResultType(), OpLoc, TheCall, diff --git a/lib/Sema/SemaStmt.cpp b/lib/Sema/SemaStmt.cpp index dae6bce626..e957a4b93f 100644 --- a/lib/Sema/SemaStmt.cpp +++ b/lib/Sema/SemaStmt.cpp @@ -469,7 +469,10 @@ Sema::ActOnFinishSwitchStmt(SourceLocation SwitchLoc, Stmt *Switch, GetTypeBeforeIntegralPromotion(CondExpr); // C99 6.8.4.2p5 - Integer promotions are performed on the controlling expr. - UsualUnaryConversions(CondExpr); + ExprResult CondResult = UsualUnaryConversions(CondExpr); + if (CondResult.isInvalid()) + return StmtError(); + CondExpr = CondResult.take(); QualType CondType = CondExpr->getType(); SS->setCond(CondExpr); @@ -555,7 +558,7 @@ Sema::ActOnFinishSwitchStmt(SourceLocation SwitchLoc, Stmt *Switch, // If the LHS is not the same type as the condition, insert an implicit // cast. - ImpCastExprToType(Lo, CondType, CK_IntegralCast); + Lo = ImpCastExprToType(Lo, CondType, CK_IntegralCast).take(); CS->setLHS(Lo); // If this is a case range, remember it in CaseRanges, otherwise CaseVals. @@ -634,7 +637,7 @@ Sema::ActOnFinishSwitchStmt(SourceLocation SwitchLoc, Stmt *Switch, // If the LHS is not the same type as the condition, insert an implicit // cast. - ImpCastExprToType(Hi, CondType, CK_IntegralCast); + Hi = ImpCastExprToType(Hi, CondType, CK_IntegralCast).take(); CR->setRHS(Hi); // If the low value is bigger than the high value, the case is empty. @@ -868,11 +871,13 @@ Sema::ActOnDoStmt(SourceLocation DoLoc, Stmt *Body, Expr *Cond, SourceLocation CondRParen) { assert(Cond && "ActOnDoStmt(): missing expression"); - if (CheckBooleanCondition(Cond, DoLoc)) + ExprResult CondResult = CheckBooleanCondition(Cond, DoLoc); + if (CondResult.isInvalid() || CondResult.isInvalid()) return StmtError(); + Cond = CondResult.take(); CheckImplicitConversions(Cond, DoLoc); - ExprResult CondResult = MaybeCreateExprWithCleanups(Cond); + CondResult = MaybeCreateExprWithCleanups(Cond); if (CondResult.isInvalid()) return StmtError(); Cond = CondResult.take(); @@ -973,7 +978,10 @@ Sema::ActOnObjCForCollectionStmt(SourceLocation ForLoc, << FirstType << First->getSourceRange(); } if (Second && !Second->isTypeDependent()) { - DefaultFunctionArrayLvalueConversion(Second); + ExprResult Result = DefaultFunctionArrayLvalueConversion(Second); + if (Result.isInvalid()) + return StmtError(); + Second = Result.take(); QualType SecondType = Second->getType(); if (!SecondType->isObjCObjectPointerType()) Diag(ForLoc, diag::err_collection_expr_type) @@ -1020,8 +1028,12 @@ Sema::ActOnIndirectGotoStmt(SourceLocation GotoLoc, SourceLocation StarLoc, if (!E->isTypeDependent()) { QualType ETy = E->getType(); QualType DestTy = Context.getPointerType(Context.VoidTy.withConst()); + ExprResult ExprRes = Owned(E); AssignConvertType ConvTy = - CheckSingleAssignmentConstraints(DestTy, E); + CheckSingleAssignmentConstraints(DestTy, ExprRes); + if (ExprRes.isInvalid()) + return StmtError(); + E = ExprRes.take(); if (DiagnoseAssignmentResult(ConvTy, StarLoc, DestTy, ETy, E, AA_Passing)) return StmtError(); } @@ -1188,7 +1200,10 @@ Sema::ActOnBlockReturnStmt(SourceLocation ReturnLoc, Expr *RetValExp) { if (RetValExp) { // Don't call UsualUnaryConversions(), since we don't want to do // integer promotions here. - DefaultFunctionArrayLvalueConversion(RetValExp); + ExprResult Result = DefaultFunctionArrayLvalueConversion(RetValExp); + if (Result.isInvalid()) + return StmtError(); + RetValExp = Result.take(); CurBlock->ReturnType = RetValExp->getType(); if (BlockDeclRefExpr *CDRE = dyn_cast(RetValExp)) { // We have to remove a 'const' added to copied-in variable which was @@ -1290,8 +1305,12 @@ Sema::ActOnReturnStmt(SourceLocation ReturnLoc, Expr *RetValExp) { if (RetValExp->getType()->isVoidType()) D = diag::ext_return_has_void_expr; else { - IgnoredValueConversions(RetValExp); - ImpCastExprToType(RetValExp, Context.VoidTy, CK_ToVoid); + ExprResult Result = Owned(RetValExp); + Result = IgnoredValueConversions(Result.take()); + if (Result.isInvalid()) + return StmtError(); + RetValExp = Result.take(); + RetValExp = ImpCastExprToType(RetValExp, Context.VoidTy, CK_ToVoid).take(); } // return (some void expression); is legal in C++. @@ -1498,8 +1517,11 @@ StmtResult Sema::ActOnAsmStmt(SourceLocation AsmLoc, bool IsSimple, } } - DefaultFunctionArrayLvalueConversion(Exprs[i]); + ExprResult Result = DefaultFunctionArrayLvalueConversion(Exprs[i]); + if (Result.isInvalid()) + return StmtError(); + Exprs[i] = Result.take(); InputConstraintInfos.push_back(Info); } @@ -1614,7 +1636,7 @@ StmtResult Sema::ActOnAsmStmt(SourceLocation AsmLoc, bool IsSimple, if (InputDomain == AD_Int && OutputDomain == AD_Int && !isOperandMentioned(InputOpNo, Pieces) && InputExpr->isEvaluatable(Context)) { - ImpCastExprToType(InputExpr, OutTy, CK_IntegralCast); + InputExpr = ImpCastExprToType(InputExpr, OutTy, CK_IntegralCast).take(); Exprs[InputOpNo] = InputExpr; NS->setInputExpr(i, InputExpr); continue; @@ -1663,8 +1685,11 @@ Sema::ActOnObjCAtTryStmt(SourceLocation AtLoc, Stmt *Try, StmtResult Sema::BuildObjCAtThrowStmt(SourceLocation AtLoc, Expr *Throw) { if (Throw) { - DefaultLvalueConversion(Throw); + ExprResult Result = DefaultLvalueConversion(Throw); + if (Result.isInvalid()) + return StmtError(); + Throw = Result.take(); QualType ThrowType = Throw->getType(); // Make sure the expression type is an ObjC pointer or "void *". if (!ThrowType->isDependentType() && @@ -1703,8 +1728,11 @@ Sema::ActOnObjCAtSynchronizedStmt(SourceLocation AtLoc, Expr *SyncExpr, Stmt *SyncBody) { getCurFunction()->setHasBranchProtectedScope(); - DefaultLvalueConversion(SyncExpr); + ExprResult Result = DefaultLvalueConversion(SyncExpr); + if (Result.isInvalid()) + return StmtError(); + SyncExpr = Result.take(); // Make sure the expression type is an ObjC pointer or "void *". if (!SyncExpr->getType()->isDependentType() && !SyncExpr->getType()->isObjCObjectPointerType()) { diff --git a/lib/Sema/SemaTemplate.cpp b/lib/Sema/SemaTemplate.cpp index 68cb6f4dfe..7bc5904e9a 100644 --- a/lib/Sema/SemaTemplate.cpp +++ b/lib/Sema/SemaTemplate.cpp @@ -680,10 +680,12 @@ Decl *Sema::ActOnNonTypeTemplateParameter(Scope *S, Declarator &D, return Param; TemplateArgument Converted; - if (CheckTemplateArgument(Param, Param->getType(), Default, Converted)) { + ExprResult DefaultRes = CheckTemplateArgument(Param, Param->getType(), Default, Converted); + if (DefaultRes.isInvalid()) { Param->setInvalidDecl(); return Param; } + Default = DefaultRes.take(); Param->setDefaultArgument(Default, false); } @@ -2418,9 +2420,11 @@ bool Sema::CheckTemplateArgument(NamedDecl *Param, return true; case TemplateArgument::Expression: { - Expr *E = Arg.getArgument().getAsExpr(); TemplateArgument Result; - if (CheckTemplateArgument(NTTP, NTTPType, E, Result, CTAK)) + ExprResult Res = + CheckTemplateArgument(NTTP, NTTPType, Arg.getArgument().getAsExpr(), + Result, CTAK); + if (Res.isInvalid()) return true; Converted.push_back(Result); @@ -2451,23 +2455,21 @@ bool Sema::CheckTemplateArgument(NamedDecl *Param, CXXScopeSpec SS; SS.Adopt(Arg.getTemplateQualifierLoc()); - Expr *E = DependentScopeDeclRefExpr::Create(Context, + ExprResult E = Owned(DependentScopeDeclRefExpr::Create(Context, SS.getWithLocInContext(Context), - NameInfo); + NameInfo)); // If we parsed the template argument as a pack expansion, create a // pack expansion expression. if (Arg.getArgument().getKind() == TemplateArgument::TemplateExpansion){ - ExprResult Expansion = ActOnPackExpansion(E, - Arg.getTemplateEllipsisLoc()); - if (Expansion.isInvalid()) + E = ActOnPackExpansion(E.take(), Arg.getTemplateEllipsisLoc()); + if (E.isInvalid()) return true; - - E = Expansion.get(); } TemplateArgument Result; - if (CheckTemplateArgument(NTTP, NTTPType, E, Result)) + E = CheckTemplateArgument(NTTP, NTTPType, E.take(), Result); + if (E.isInvalid()) return true; Converted.push_back(Result); @@ -3389,15 +3391,14 @@ bool Sema::CheckTemplateArgumentPointerToMember(Expr *Arg, /// non-type template parameter. /// /// This routine implements the semantics of C++ [temp.arg.nontype]. -/// It returns true if an error occurred, and false otherwise. \p +/// If an error occurred, it returns ExprError(); otherwise, it +/// returns the converted template argument. \p /// InstantiatedParamType is the type of the non-type template /// parameter after it has been instantiated. -/// -/// If no error was detected, Converted receives the converted template argument. -bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, - QualType InstantiatedParamType, Expr *&Arg, - TemplateArgument &Converted, - CheckTemplateArgumentKind CTAK) { +ExprResult Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, + QualType InstantiatedParamType, Expr *Arg, + TemplateArgument &Converted, + CheckTemplateArgumentKind CTAK) { SourceLocation StartLoc = Arg->getSourceRange().getBegin(); // If either the parameter has a dependent type or the argument is @@ -3405,7 +3406,7 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, if (InstantiatedParamType->isDependentType() || Arg->isTypeDependent()) { // FIXME: Produce a cloned, canonical expression? Converted = TemplateArgument(Arg); - return false; + return Owned(Arg); } // C++ [temp.arg.nontype]p5: @@ -3435,12 +3436,12 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, diag::err_template_arg_not_integral_or_enumeral) << ArgType << Arg->getSourceRange(); Diag(Param->getLocation(), diag::note_template_param_here); - return true; + return ExprError(); } else if (!Arg->isValueDependent() && !Arg->isIntegerConstantExpr(Value, Context, &NonConstantLoc)) { Diag(NonConstantLoc, diag::err_template_arg_not_ice) << ArgType << Arg->getSourceRange(); - return true; + return ExprError(); } // From here on out, all we care about are the unqualified forms @@ -3463,21 +3464,21 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, Diag(StartLoc, diag::err_deduced_non_type_template_arg_type_mismatch) << ArgType << ParamType; Diag(Param->getLocation(), diag::note_template_param_here); - return true; + return ExprError(); } else if (ParamType->isBooleanType()) { // This is an integral-to-boolean conversion. - ImpCastExprToType(Arg, ParamType, CK_IntegralToBoolean); + Arg = ImpCastExprToType(Arg, ParamType, CK_IntegralToBoolean).take(); } else if (IsIntegralPromotion(Arg, ArgType, ParamType) || !ParamType->isEnumeralType()) { // This is an integral promotion or conversion. - ImpCastExprToType(Arg, ParamType, CK_IntegralCast); + Arg = ImpCastExprToType(Arg, ParamType, CK_IntegralCast).take(); } else { // We can't perform this conversion. Diag(Arg->getSourceRange().getBegin(), diag::err_template_arg_not_convertible) << Arg->getType() << InstantiatedParamType << Arg->getSourceRange(); Diag(Param->getLocation(), diag::note_template_param_here); - return true; + return ExprError(); } QualType IntegerType = Context.getCanonicalType(ParamType); @@ -3527,13 +3528,13 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, // The argument is value-dependent. Create a new // TemplateArgument with the converted expression. Converted = TemplateArgument(Arg); - return false; + return Owned(Arg); } Converted = TemplateArgument(Value, ParamType->isEnumeralType() ? ParamType : IntegerType); - return false; + return Owned(Arg); } DeclAccessPair FoundResult; // temporary for ResolveOverloadedFunction @@ -3545,7 +3546,7 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, if (ArgType->isNullPtrType() && (ParamType->isPointerType() || ParamType->isMemberPointerType())) { Converted = TemplateArgument((NamedDecl *)0); - return false; + return Owned(Arg); } // Handle pointer-to-function, reference-to-function, and @@ -3577,22 +3578,25 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, true, FoundResult)) { if (DiagnoseUseOfDecl(Fn, Arg->getSourceRange().getBegin())) - return true; + return ExprError(); Arg = FixOverloadedFunctionReference(Arg, FoundResult, Fn); ArgType = Arg->getType(); } else - return true; + return ExprError(); } - if (!ParamType->isMemberPointerType()) - return CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, - ParamType, - Arg, Converted); + if (!ParamType->isMemberPointerType()) { + if (CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, + ParamType, + Arg, Converted)) + return ExprError(); + return Owned(Arg); + } if (IsQualificationConversion(ArgType, ParamType.getNonReferenceType(), false)) { - ImpCastExprToType(Arg, ParamType, CK_NoOp, CastCategory(Arg)); + Arg = ImpCastExprToType(Arg, ParamType, CK_NoOp, CastCategory(Arg)).take(); } else if (!Context.hasSameUnqualifiedType(ArgType, ParamType.getNonReferenceType())) { // We can't perform this conversion. @@ -3600,10 +3604,12 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, diag::err_template_arg_not_convertible) << Arg->getType() << InstantiatedParamType << Arg->getSourceRange(); Diag(Param->getLocation(), diag::note_template_param_here); - return true; + return ExprError(); } - return CheckTemplateArgumentPointerToMember(Arg, Converted); + if (CheckTemplateArgumentPointerToMember(Arg, Converted)) + return ExprError(); + return Owned(Arg); } if (ParamType->isPointerType()) { @@ -3614,9 +3620,11 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, assert(ParamType->getPointeeType()->isIncompleteOrObjectType() && "Only object pointers allowed here"); - return CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, - ParamType, - Arg, Converted); + if (CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, + ParamType, + Arg, Converted)) + return ExprError(); + return Owned(Arg); } if (const ReferenceType *ParamRefType = ParamType->getAs()) { @@ -3635,17 +3643,19 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, true, FoundResult)) { if (DiagnoseUseOfDecl(Fn, Arg->getSourceRange().getBegin())) - return true; + return ExprError(); Arg = FixOverloadedFunctionReference(Arg, FoundResult, Fn); ArgType = Arg->getType(); } else - return true; + return ExprError(); } - return CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, - ParamType, - Arg, Converted); + if (CheckTemplateArgumentAddressOfObjectOrFunction(*this, Param, + ParamType, + Arg, Converted)) + return ExprError(); + return Owned(Arg); } // -- For a non-type template-parameter of type pointer to data @@ -3655,17 +3665,19 @@ bool Sema::CheckTemplateArgument(NonTypeTemplateParmDecl *Param, if (Context.hasSameUnqualifiedType(ParamType, ArgType)) { // Types match exactly: nothing more to do here. } else if (IsQualificationConversion(ArgType, ParamType, false)) { - ImpCastExprToType(Arg, ParamType, CK_NoOp, CastCategory(Arg)); + Arg = ImpCastExprToType(Arg, ParamType, CK_NoOp, CastCategory(Arg)).take(); } else { // We can't perform this conversion. Diag(Arg->getSourceRange().getBegin(), diag::err_template_arg_not_convertible) << Arg->getType() << InstantiatedParamType << Arg->getSourceRange(); Diag(Param->getLocation(), diag::note_template_param_here); - return true; + return ExprError(); } - return CheckTemplateArgumentPointerToMember(Arg, Converted); + if (CheckTemplateArgumentPointerToMember(Arg, Converted)) + return ExprError(); + return Owned(Arg); } /// \brief Check a template argument against its corresponding @@ -3759,11 +3771,8 @@ Sema::BuildExpressionFromDeclTemplateArgument(const TemplateArgument &Arg, // the element type on the parameter could be more qualified than the // element type in the expression we constructed. if (IsQualificationConversion(((Expr*) RefExpr.get())->getType(), - ParamType.getUnqualifiedType(), false)) { - Expr *RefE = RefExpr.takeAs(); - ImpCastExprToType(RefE, ParamType.getUnqualifiedType(), CK_NoOp); - RefExpr = Owned(RefE); - } + ParamType.getUnqualifiedType(), false)) + RefExpr = ImpCastExprToType(RefExpr.take(), ParamType.getUnqualifiedType(), CK_NoOp); assert(!RefExpr.isInvalid() && Context.hasSameType(((Expr*) RefExpr.get())->getType(), @@ -3782,12 +3791,9 @@ Sema::BuildExpressionFromDeclTemplateArgument(const TemplateArgument &Arg, if (T->isFunctionType() || T->isArrayType()) { // Decay functions and arrays. - Expr *RefE = (Expr *)RefExpr.get(); - DefaultFunctionArrayConversion(RefE); - if (RefE != RefExpr.get()) { - RefExpr.release(); - RefExpr = Owned(RefE); - } + RefExpr = DefaultFunctionArrayConversion(RefExpr.take()); + if (RefExpr.isInvalid()) + return ExprError(); return move(RefExpr); } diff --git a/lib/Sema/SemaType.cpp b/lib/Sema/SemaType.cpp index d0b3fe70a2..0ec2986ba5 100644 --- a/lib/Sema/SemaType.cpp +++ b/lib/Sema/SemaType.cpp @@ -1154,8 +1154,13 @@ QualType Sema::BuildArrayType(QualType T, ArrayType::ArraySizeModifier ASM, } // Do lvalue-to-rvalue conversions on the array size expression. - if (ArraySize && !ArraySize->isRValue()) - DefaultLvalueConversion(ArraySize); + if (ArraySize && !ArraySize->isRValue()) { + ExprResult Result = DefaultLvalueConversion(ArraySize); + if (Result.isInvalid()) + return QualType(); + + ArraySize = Result.take(); + } // C99 6.7.5.2p1: The size expression shall have integer type. // TODO: in theory, if we were insane, we could allow contextual diff --git a/lib/Sema/TreeTransform.h b/lib/Sema/TreeTransform.h index 74e918bf86..a7dc920f84 100644 --- a/lib/Sema/TreeTransform.h +++ b/lib/Sema/TreeTransform.h @@ -1373,11 +1373,13 @@ public: assert(Member->getType()->isRecordType() && "unnamed member not of record type?"); - if (getSema().PerformObjectMemberConversion(Base, - QualifierLoc.getNestedNameSpecifier(), - FoundDecl, Member)) + ExprResult BaseResult = + getSema().PerformObjectMemberConversion(Base, + QualifierLoc.getNestedNameSpecifier(), + FoundDecl, Member); + if (BaseResult.isInvalid()) return ExprError(); - + Base = BaseResult.take(); ExprValueKind VK = isArrow ? VK_LValue : Base->getValueKind(); MemberExpr *ME = new (getSema().Context) MemberExpr(Base, isArrow, @@ -1390,7 +1392,10 @@ public: CXXScopeSpec SS; SS.Adopt(QualifierLoc); - getSema().DefaultFunctionArrayConversion(Base); + ExprResult BaseResult = getSema().DefaultFunctionArrayConversion(Base); + if (BaseResult.isInvalid()) + return ExprError(); + Base = BaseResult.take(); QualType BaseType = Base->getType(); // FIXME: this involves duplicating earlier analysis in a lot of @@ -2060,20 +2065,20 @@ public: bool IsArrow, bool IsFreeIvar) { // FIXME: We lose track of the IsFreeIvar bit. CXXScopeSpec SS; - Expr *Base = BaseArg; + ExprResult Base = getSema().Owned(BaseArg); LookupResult R(getSema(), Ivar->getDeclName(), IvarLoc, Sema::LookupMemberName); ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, /*FIME:*/IvarLoc, SS, 0, false); - if (Result.isInvalid()) + if (Result.isInvalid() || Base.isInvalid()) return ExprError(); if (Result.get()) return move(Result); - return getSema().BuildMemberReferenceExpr(Base, Base->getType(), + return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), /*FIXME:*/IvarLoc, IsArrow, SS, /*FirstQualifierInScope=*/0, R, @@ -2088,20 +2093,20 @@ public: ObjCPropertyDecl *Property, SourceLocation PropertyLoc) { CXXScopeSpec SS; - Expr *Base = BaseArg; + ExprResult Base = getSema().Owned(BaseArg); LookupResult R(getSema(), Property->getDeclName(), PropertyLoc, Sema::LookupMemberName); bool IsArrow = false; ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, /*FIME:*/PropertyLoc, SS, 0, false); - if (Result.isInvalid()) + if (Result.isInvalid() || Base.isInvalid()) return ExprError(); if (Result.get()) return move(Result); - return getSema().BuildMemberReferenceExpr(Base, Base->getType(), + return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), /*FIXME:*/PropertyLoc, IsArrow, SS, /*FirstQualifierInScope=*/0, @@ -2132,19 +2137,19 @@ public: ExprResult RebuildObjCIsaExpr(Expr *BaseArg, SourceLocation IsaLoc, bool IsArrow) { CXXScopeSpec SS; - Expr *Base = BaseArg; + ExprResult Base = getSema().Owned(BaseArg); LookupResult R(getSema(), &getSema().Context.Idents.get("isa"), IsaLoc, Sema::LookupMemberName); ExprResult Result = getSema().LookupMemberExpr(R, Base, IsArrow, /*FIME:*/IsaLoc, SS, 0, false); - if (Result.isInvalid()) + if (Result.isInvalid() || Base.isInvalid()) return ExprError(); if (Result.get()) return move(Result); - return getSema().BuildMemberReferenceExpr(Base, Base->getType(), + return getSema().BuildMemberReferenceExpr(Base.get(), Base.get()->getType(), /*FIXME:*/IsaLoc, IsArrow, SS, /*FirstQualifierInScope=*/0, R, @@ -2167,28 +2172,25 @@ public: // Build a reference to the __builtin_shufflevector builtin FunctionDecl *Builtin = cast(*Lookup.first); - Expr *Callee - = new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(), - VK_LValue, BuiltinLoc); - SemaRef.UsualUnaryConversions(Callee); + ExprResult Callee + = SemaRef.Owned(new (SemaRef.Context) DeclRefExpr(Builtin, Builtin->getType(), + VK_LValue, BuiltinLoc)); + Callee = SemaRef.UsualUnaryConversions(Callee.take()); + if (Callee.isInvalid()) + return ExprError(); // Build the CallExpr unsigned NumSubExprs = SubExprs.size(); Expr **Subs = (Expr **)SubExprs.release(); - CallExpr *TheCall = new (SemaRef.Context) CallExpr(SemaRef.Context, Callee, + ExprResult TheCall = SemaRef.Owned( + new (SemaRef.Context) CallExpr(SemaRef.Context, Callee.take(), Subs, NumSubExprs, Builtin->getCallResultType(), Expr::getValueKindForType(Builtin->getResultType()), - RParenLoc); - ExprResult OwnedCall(SemaRef.Owned(TheCall)); + RParenLoc)); // Type-check the __builtin_shufflevector expression. - ExprResult Result = SemaRef.SemaBuiltinShuffleVector(TheCall); - if (Result.isInvalid()) - return ExprError(); - - OwnedCall.release(); - return move(Result); + return SemaRef.SemaBuiltinShuffleVector(cast(TheCall.take())); } /// \brief Build a new template argument pack expansion. -- 2.50.1