Index: lib/Sema/SemaExprCXX.cpp =================================================================== --- lib/Sema/SemaExprCXX.cpp +++ lib/Sema/SemaExprCXX.cpp @@ -4828,11 +4828,9 @@ /// TryClassUnification. static bool ConvertForConditional(Sema &Self, ExprResult &E, QualType T) { InitializedEntity Entity = InitializedEntity::InitializeTemporary(T); - InitializationKind Kind = InitializationKind::CreateCopy(E.get()->getLocStart(), - SourceLocation()); - Expr *Arg = E.get(); - InitializationSequence InitSeq(Self, Entity, Kind, Arg); - ExprResult Result = InitSeq.Perform(Self, Entity, Kind, Arg); + ExprResult Result = Self.PerformCopyInitialization(Entity, + SourceLocation(), + E); if (Result.isInvalid()) return true; @@ -4908,6 +4906,8 @@ // Otherwise, if the second and third operand have different types, and // either has (cv) class type [...] an attempt is made to convert each of // those operands to the type of the other. + bool LHSConverted = false; + bool RHSConverted = false; if (!Context.hasSameType(LTy, RTy) && (LTy->isRecordType() || RTy->isRecordType())) { // These return true if a single direction is already ambiguous. @@ -4932,10 +4932,12 @@ if (ConvertForConditional(*this, LHS, L2RType) || LHS.isInvalid()) return QualType(); LTy = LHS.get()->getType(); + LHSConverted = true; } else if (HaveR2L) { if (ConvertForConditional(*this, RHS, R2LType) || RHS.isInvalid()) return QualType(); RTy = RHS.get()->getType(); + RHSConverted = true; } } @@ -5016,13 +5018,13 @@ return QualType(); InitializedEntity Entity = InitializedEntity::InitializeTemporary(LTy); - ExprResult LHSCopy = PerformCopyInitialization(Entity, + ExprResult LHSCopy = LHSConverted ? LHS : PerformCopyInitialization(Entity, SourceLocation(), LHS); if (LHSCopy.isInvalid()) return QualType(); - ExprResult RHSCopy = PerformCopyInitialization(Entity, + ExprResult RHSCopy = RHSConverted ? RHS : PerformCopyInitialization(Entity, SourceLocation(), RHS); if (RHSCopy.isInvalid()) Index: test/SemaCXX/conditional-expr.cpp =================================================================== --- test/SemaCXX/conditional-expr.cpp +++ test/SemaCXX/conditional-expr.cpp @@ -67,6 +67,13 @@ struct Derived2: Abstract { }; +struct M { + M(); + M(const M&); + M(M&&); + M(const M&&) = delete; +}; + void test() { // This function tests C++0x 5.16 @@ -132,6 +139,9 @@ // should fail: const lost (void)(i1 ? Base() : constder()); // expected-error {{incompatible operand types ('Base' and 'const Derived')}} (void)(i1 ? constder() : Base()); // expected-error {{incompatible operand types ('const Derived' and 'Base')}} + // should succeed: const applied after copy initialization + const M constM; + (void)(i1 ? constM : M()); Priv priv; Fin fin;