Fix a crash bug when comparing overload quality of conversion operators with conversion constructors.
Remove an atrocious amount of trailing whitespace in the overloaded operator mangler. Sorry, couldn't help myself.
Change the DeclType parameter of Sema::CheckReferenceInit to be passed by value instead of reference. It wasn't changed anywhere.
Let the parser handle C++'s irregular grammar around assignment-expression and conditional-expression.
And finally, the reason for all this stuff: implement C++ semantics for the conditional operator. The implementation is complete except for determining lvalueness.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@69299 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/Mangle.cpp b/lib/CodeGen/Mangle.cpp
index c8d9de2..e42b6fd 100644
--- a/lib/CodeGen/Mangle.cpp
+++ b/lib/CodeGen/Mangle.cpp
@@ -283,97 +283,98 @@
 void 
 CXXNameMangler::mangleOperatorName(OverloadedOperatorKind OO, unsigned Arity) {
   switch (OO) {
-  // <operator-name> ::= nw     # new           
+  // <operator-name> ::= nw     # new
   case OO_New: Out << "nw"; break;
   //              ::= na        # new[]
   case OO_Array_New: Out << "na"; break;
-  //              ::= dl        # delete     
+  //              ::= dl        # delete
   case OO_Delete: Out << "dl"; break;
-  //              ::= da        # delete[]      
+  //              ::= da        # delete[]
   case OO_Array_Delete: Out << "da"; break;
   //              ::= ps        # + (unary)
   //              ::= pl        # +
   case OO_Plus: Out << (Arity == 1? "ps" : "pl"); break;
-  //              ::= ng        # - (unary)     
-  //              ::= mi        # -             
+  //              ::= ng        # - (unary)
+  //              ::= mi        # -
   case OO_Minus: Out << (Arity == 1? "ng" : "mi"); break;
-  //              ::= ad        # & (unary)     
-  //              ::= an        # &             
+  //              ::= ad        # & (unary)
+  //              ::= an        # &
   case OO_Amp: Out << (Arity == 1? "ad" : "an"); break;
-  //              ::= de        # * (unary)     
-  //              ::= ml        # *             
+  //              ::= de        # * (unary)
+  //              ::= ml        # *
   case OO_Star: Out << (Arity == 1? "de" : "ml"); break;
-  //              ::= co        # ~             
+  //              ::= co        # ~
   case OO_Tilde: Out << "co"; break;
-  //              ::= dv        # /             
+  //              ::= dv        # /
   case OO_Slash: Out << "dv"; break;
-  //              ::= rm        # %             
+  //              ::= rm        # %
   case OO_Percent: Out << "rm"; break;
-  //              ::= or        # |   
-  case OO_Pipe: Out << "or"; break;          
-  //              ::= eo        # ^             
+  //              ::= or        # |
+  case OO_Pipe: Out << "or"; break;
+  //              ::= eo        # ^
   case OO_Caret: Out << "eo"; break;
-  //              ::= aS        # = 
+  //              ::= aS        # =
   case OO_Equal: Out << "aS"; break;
-  //              ::= pL        # +=            
+  //              ::= pL        # +=
   case OO_PlusEqual: Out << "pL"; break;
-  //              ::= mI        # -=   
+  //              ::= mI        # -=
   case OO_MinusEqual: Out << "mI"; break;
-  //              ::= mL        # *=     
+  //              ::= mL        # *=
   case OO_StarEqual: Out << "mL"; break;
-  //              ::= dV        # /=    
+  //              ::= dV        # /=
   case OO_SlashEqual: Out << "dV"; break;
-  //              ::= rM        # %=     
-  case OO_PercentEqual: Out << "rM"; break;       
-  //              ::= aN        # &=       
-  case OO_AmpEqual: Out << "aN"; break;     
-  //              ::= oR        # |=   
-  case OO_PipeEqual: Out << "oR"; break;         
-  //              ::= eO        # ^=      
-  case OO_CaretEqual: Out << "eO"; break;      
-  //              ::= ls        # <<     
+  //              ::= rM        # %=
+  case OO_PercentEqual: Out << "rM"; break;
+  //              ::= aN        # &=
+  case OO_AmpEqual: Out << "aN"; break;
+  //              ::= oR        # |=
+  case OO_PipeEqual: Out << "oR"; break;
+  //              ::= eO        # ^=
+  case OO_CaretEqual: Out << "eO"; break;
+  //              ::= ls        # <<
   case OO_LessLess: Out << "ls"; break;
-  //              ::= rs        # >>   
-  case OO_GreaterGreater: Out << "rs"; break;         
-  //              ::= lS        # <<=        
-  case OO_LessLessEqual: Out << "lS"; break;   
-  //              ::= rS        # >>=       
-  case OO_GreaterGreaterEqual: Out << "rS"; break;    
+  //              ::= rs        # >>
+  case OO_GreaterGreater: Out << "rs"; break;
+  //              ::= lS        # <<=
+  case OO_LessLessEqual: Out << "lS"; break;
+  //              ::= rS        # >>=
+  case OO_GreaterGreaterEqual: Out << "rS"; break;
   //              ::= eq        # ==
   case OO_EqualEqual: Out << "eq"; break;
-  //              ::= ne        # !=     
-  case OO_ExclaimEqual: Out << "ne"; break;       
-  //              ::= lt        # <        
+  //              ::= ne        # !=
+  case OO_ExclaimEqual: Out << "ne"; break;
+  //              ::= lt        # <
   case OO_Less: Out << "lt"; break;
-  //              ::= gt        # >             
+  //              ::= gt        # >
   case OO_Greater: Out << "gt"; break;
-  //              ::= le        # <=  
+  //              ::= le        # <=
   case OO_LessEqual: Out << "le"; break;
-  //              ::= ge        # >=    
+  //              ::= ge        # >=
   case OO_GreaterEqual: Out << "ge"; break;
-  //              ::= nt        # !        
+  //              ::= nt        # !
   case OO_Exclaim: Out << "nt"; break;
-  //              ::= aa        # &&  
+  //              ::= aa        # &&
   case OO_AmpAmp: Out << "aa"; break;
-  //              ::= oo        # || 
-  case OO_PipePipe: Out << "oo"; break;           
-  //              ::= pp        # ++   
-  case OO_PlusPlus: Out << "pp"; break;         
-  //              ::= mm        # --   
+  //              ::= oo        # ||
+  case OO_PipePipe: Out << "oo"; break;
+  //              ::= pp        # ++
+  case OO_PlusPlus: Out << "pp"; break;
+  //              ::= mm        # --
   case OO_MinusMinus: Out << "mm"; break;
-  //              ::= cm        # ,      
-  case OO_Comma: Out << "cm"; break;       
-  //              ::= pm        # ->*      
+  //              ::= cm        # ,
+  case OO_Comma: Out << "cm"; break;
+  //              ::= pm        # ->*
   case OO_ArrowStar: Out << "pm"; break;
-  //              ::= pt        # ->    
+  //              ::= pt        # ->
   case OO_Arrow: Out << "pt"; break;
-  //              ::= cl        # ()            
+  //              ::= cl        # ()
   case OO_Call: Out << "cl"; break;
-  //              ::= ix        # []            
+  //              ::= ix        # []
   case OO_Subscript: Out << "ix"; break;
   // UNSUPPORTED: ::= qu        # ?
 
-  case OO_None: 
+  case OO_None:
+  case OO_Conditional:
   case NUM_OVERLOADED_OPERATORS:
     assert(false && "Not an overloaded operator"); 
     break;
diff --git a/lib/Parse/ParseExpr.cpp b/lib/Parse/ParseExpr.cpp
index d41586c..3280730 100644
--- a/lib/Parse/ParseExpr.cpp
+++ b/lib/Parse/ParseExpr.cpp
@@ -186,6 +186,7 @@
 ///         logical-OR-expression
 ///         logical-OR-expression '?' expression ':' conditional-expression
 /// [GNU]   logical-OR-expression '?' ':' conditional-expression
+/// [C++] the third operand is an assignment-expression
 ///
 ///       assignment-expression: [C99 6.5.16]
 ///         conditional-expression
@@ -332,7 +333,17 @@
     }
 
     // Parse another leaf here for the RHS of the operator.
-    OwningExprResult RHS(ParseCastExpression(false));
+    // ParseCastExpression works here because all RHS expressions in C have it
+    // as a prefix, at least. However, in C++, an assignment-expression could
+    // be a throw-expression, which is not a valid cast-expression.
+    // Therefore we need some special-casing here.
+    // Also note that the third operand of the conditional operator is
+    // an assignment-expression in C++.
+    OwningExprResult RHS(Actions);
+    if (getLang().CPlusPlus && NextTokPrec <= prec::Conditional)
+      RHS = ParseAssignmentExpression();
+    else
+      RHS = ParseCastExpression(false);
     if (RHS.isInvalid())
       return move(RHS);
 
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h
index dc80bd9..fd70851 100644
--- a/lib/Sema/Sema.h
+++ b/lib/Sema/Sema.h
@@ -2382,6 +2382,8 @@
     Expr *lex, Expr *&rex, SourceLocation OpLoc);
   QualType CheckConditionalOperands( // C99 6.5.15
     Expr *&cond, Expr *&lhs, Expr *&rhs, SourceLocation questionLoc);
+  QualType CXXCheckConditionalOperands( // C++ 5.16
+    Expr *&cond, Expr *&lhs, Expr *&rhs, SourceLocation questionLoc);
 
   /// type checking for vector binary operators.
   inline QualType CheckVectorOperands(SourceLocation l, Expr *&lex, Expr *&rex);
@@ -2435,7 +2437,7 @@
   ReferenceCompareResult CompareReferenceRelationship(QualType T1, QualType T2,
                                                       bool& DerivedToBase);
 
-  bool CheckReferenceInit(Expr *&simpleInit_or_initList, QualType &declType,
+  bool CheckReferenceInit(Expr *&simpleInit_or_initList, QualType declType,
                           ImplicitConversionSequence *ICS = 0,
                           bool SuppressUserConversions = false,
                           bool AllowExplicit = false,
diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp
index 3cfa8ae..8e2302e 100644
--- a/lib/Sema/SemaDeclCXX.cpp
+++ b/lib/Sema/SemaDeclCXX.cpp
@@ -2018,7 +2018,7 @@
 /// conversion functions.
 /// When @p ForceRValue, we unconditionally treat the initializer as an rvalue.
 bool 
-Sema::CheckReferenceInit(Expr *&Init, QualType &DeclType, 
+Sema::CheckReferenceInit(Expr *&Init, QualType DeclType,
                          ImplicitConversionSequence *ICS,
                          bool SuppressUserConversions,
                          bool AllowExplicit, bool ForceRValue) {
diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp
index ef2bf91..f903e8f 100644
--- a/lib/Sema/SemaExpr.cpp
+++ b/lib/Sema/SemaExpr.cpp
@@ -2588,6 +2588,10 @@
 /// C99 6.5.15
 QualType Sema::CheckConditionalOperands(Expr *&Cond, Expr *&LHS, Expr *&RHS,
                                         SourceLocation QuestionLoc) {
+  // C++ is sufficiently different to merit its own checker.
+  if (getLangOptions().CPlusPlus)
+    return CXXCheckConditionalOperands(Cond, LHS, RHS, QuestionLoc);
+
   UsualUnaryConversions(Cond);
   UsualUnaryConversions(LHS);
   UsualUnaryConversions(RHS);
@@ -2596,17 +2600,13 @@
   QualType RHSTy = RHS->getType();
 
   // first, check the condition.
-  if (!Cond->isTypeDependent()) {
-    if (!CondTy->isScalarType()) { // C99 6.5.15p2
-      Diag(Cond->getLocStart(), diag::err_typecheck_cond_expect_scalar)
-        << CondTy;
-      return QualType();
-    }
+  if (!CondTy->isScalarType()) { // C99 6.5.15p2
+    Diag(Cond->getLocStart(), diag::err_typecheck_cond_expect_scalar)
+      << CondTy;
+    return QualType();
   }
 
   // Now check the two expressions.
-  if ((LHS && LHS->isTypeDependent()) || (RHS && RHS->isTypeDependent()))
-    return Context.DependentTy;
 
   // If both operands have arithmetic type, do the usual arithmetic conversions
   // to find a common type: C99 6.5.15p3,5.
diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp
index e2a21f8..8f41c00 100644
--- a/lib/Sema/SemaExprCXX.cpp
+++ b/lib/Sema/SemaExprCXX.cpp
@@ -1008,3 +1008,293 @@
     Result.addVolatile();
   return Result;
 }
+
+/// \brief Get the target type of a standard or user-defined conversion.
+static QualType TargetType(const ImplicitConversionSequence &ICS) {
+  assert((ICS.ConversionKind ==
+              ImplicitConversionSequence::StandardConversion ||
+          ICS.ConversionKind ==
+              ImplicitConversionSequence::UserDefinedConversion) &&
+         "function only valid for standard or user-defined conversions");
+  if (ICS.ConversionKind == ImplicitConversionSequence::StandardConversion)
+    return QualType::getFromOpaquePtr(ICS.Standard.ToTypePtr);
+  return QualType::getFromOpaquePtr(ICS.UserDefined.After.ToTypePtr);
+}
+
+/// \brief Try to convert a type to another according to C++0x 5.16p3.
+///
+/// This is part of the parameter validation for the ? operator. If either
+/// value operand is a class type, the two operands are attempted to be
+/// converted to each other. This function does the conversion in one direction.
+/// It emits a diagnostic and returns true only if it finds an ambiguous
+/// conversion.
+static bool TryClassUnification(Sema &Self, Expr *From, Expr *To,
+                                SourceLocation QuestionLoc,
+                                ImplicitConversionSequence &ICS)
+{
+  // C++0x 5.16p3
+  //   The process for determining whether an operand expression E1 of type T1
+  //   can be converted to match an operand expression E2 of type T2 is defined
+  //   as follows:
+  //   -- If E2 is an lvalue:
+  if (To->isLvalue(Self.Context) == Expr::LV_Valid) {
+    //   E1 can be converted to match E2 if E1 can be implicitly converted to
+    //   type "lvalue reference to T2", subject to the constraint that in the
+    //   conversion the reference must bind directly to E1.
+    if (!Self.CheckReferenceInit(From,
+                            Self.Context.getLValueReferenceType(To->getType()),
+                            &ICS))
+    {
+      assert((ICS.ConversionKind ==
+                  ImplicitConversionSequence::StandardConversion ||
+              ICS.ConversionKind ==
+                  ImplicitConversionSequence::UserDefinedConversion) &&
+             "expected a definite conversion");
+      bool DirectBinding =
+        ICS.ConversionKind == ImplicitConversionSequence::StandardConversion ?
+        ICS.Standard.DirectBinding : ICS.UserDefined.After.DirectBinding;
+      if (DirectBinding)
+        return false;
+    }
+  }
+  ICS.ConversionKind = ImplicitConversionSequence::BadConversion;
+  //   -- If E2 is an rvalue, or if the conversion above cannot be done:
+  //      -- if E1 and E2 have class type, and the underlying class types are
+  //         the same or one is a base class of the other:
+  QualType FTy = From->getType();
+  QualType TTy = To->getType();
+  const RecordType *FRec = FTy->getAsRecordType();
+  const RecordType *TRec = TTy->getAsRecordType();
+  bool FDerivedFromT = FRec && TRec && Self.IsDerivedFrom(FTy, TTy);
+  if (FRec && TRec && (FRec == TRec ||
+        FDerivedFromT || Self.IsDerivedFrom(TTy, FTy))) {
+    //         E1 can be converted to match E2 if the class of T2 is the
+    //         same type as, or a base class of, the class of T1, and
+    //         [cv2 > cv1].
+    if ((FRec == TRec || FDerivedFromT) && TTy.isAtLeastAsQualifiedAs(FTy)) {
+      // Could still fail if there's no copy constructor.
+      // FIXME: Is this a hard error then, or just a conversion failure? The
+      // standard doesn't say.
+      ICS = Self.TryCopyInitialization(From, TTy);
+    }
+  } else {
+    //     -- Otherwise: E1 can be converted to match E2 if E1 can be
+    //        implicitly converted to the type that expression E2 would have
+    //        if E2 were converted to an rvalue.
+    // First find the decayed type.
+    if (TTy->isFunctionType())
+      TTy = Self.Context.getPointerType(TTy);
+    else if(TTy->isArrayType())
+      TTy = Self.Context.getArrayDecayedType(TTy);
+
+    // Now try the implicit conversion.
+    // FIXME: This doesn't detect ambiguities.
+    ICS = Self.TryImplicitConversion(From, TTy);
+  }
+  return false;
+}
+
+/// \brief Try to find a common type for two according to C++0x 5.16p5.
+///
+/// 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,
+                                    SourceLocation Loc) {
+  Expr *Args[2] = { LHS, RHS };
+  OverloadCandidateSet CandidateSet;
+  Self.AddBuiltinOperatorCandidates(OO_Conditional, Args, 2, CandidateSet);
+
+  OverloadCandidateSet::iterator Best;
+  switch (Self.BestViableFunction(CandidateSet, Best)) {
+    case Sema::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], "converting") ||
+          Self.PerformImplicitConversion(RHS, Best->BuiltinTypes.ParamTypes[1],
+                                         Best->Conversions[1], "converting"))
+        break;
+      return false;
+
+    case Sema::OR_No_Viable_Function:
+      Self.Diag(Loc, diag::err_typecheck_cond_incompatible_operands)
+        << LHS->getType() << RHS->getType()
+        << LHS->getSourceRange() << RHS->getSourceRange();
+      return true;
+
+    case Sema::OR_Ambiguous:
+      Self.Diag(Loc, diag::err_conditional_ambiguous_ovl)
+        << LHS->getType() << RHS->getType()
+        << LHS->getSourceRange() << RHS->getSourceRange();
+      // FIXME: Print the possible common types by printing the return types
+      // of the viable candidates.
+      break;
+
+    case Sema::OR_Deleted:
+      assert(false && "Conditional operator has only built-in overloads");
+      break;
+  }
+  return true;
+}
+
+/// \brief Check the operands of ?: under C++ semantics.
+///
+/// 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,
+                                           SourceLocation QuestionLoc) {
+  // FIXME: Handle C99's complex types, vector types, block pointers and
+  // Obj-C++ interface pointers.
+
+  // C++0x 5.16p1
+  //   The first expression is contextually converted to bool.
+  if (!Cond->isTypeDependent()) {
+    if (CheckCXXBooleanCondition(Cond))
+      return QualType();
+  }
+
+  // Either of the arguments dependent?
+  if (LHS->isTypeDependent() || RHS->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();
+  bool LVoid = LTy->isVoidType();
+  bool RVoid = RTy->isVoidType();
+  if (LVoid || RVoid) {
+    //   ... then the [l2r] conversions are performed on the second and third
+    //   operands ...
+    DefaultFunctionArrayConversion(LHS);
+    DefaultFunctionArrayConversion(RHS);
+    LTy = LHS->getType();
+    RTy = RHS->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<CXXThrowExpr>(LHS);
+    bool RThrow = isa<CXXThrowExpr>(RHS);
+    if (LThrow && !RThrow)
+      return RTy;
+    if (RThrow && !LThrow)
+      return LTy;
+
+    //   -- Both the second and third operands have type void; the result is of
+    //      type void and is an rvalue.
+    if (LVoid && RVoid)
+      return Context.VoidTy;
+
+    // Neither holds, error.
+    Diag(QuestionLoc, diag::err_conditional_void_nonvoid)
+      << (LVoid ? RTy : LTy) << (LVoid ? 0 : 1)
+      << LHS->getSourceRange() << RHS->getSourceRange();
+    return QualType();
+  }
+
+  // Neither is void.
+
+  // C++0x 5.16p3
+  //   Otherwise, if the second and third operand have different types, and
+  //   either has (cv) class type, and attempt is made to convert each of those
+  //   operands to the other.
+  if (Context.getCanonicalType(LTy) != Context.getCanonicalType(RTy) &&
+      (LTy->isRecordType() || RTy->isRecordType())) {
+    ImplicitConversionSequence ICSLeftToRight, ICSRightToLeft;
+    // These return true if a single direction is already ambiguous.
+    if (TryClassUnification(*this, LHS, RHS, QuestionLoc, ICSLeftToRight))
+      return QualType();
+    if (TryClassUnification(*this, RHS, LHS, QuestionLoc, ICSRightToLeft))
+      return QualType();
+
+    bool HaveL2R = ICSLeftToRight.ConversionKind !=
+      ImplicitConversionSequence::BadConversion;
+    bool HaveR2L = ICSRightToLeft.ConversionKind !=
+      ImplicitConversionSequence::BadConversion;
+    //   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();
+      return QualType();
+    }
+
+    //   If exactly one conversion is possible, that conversion is applied to
+    //   the chosen operand and the converted operands are used in place of the
+    //   original operands for the remainder of this section.
+    if (HaveL2R) {
+      if (PerformImplicitConversion(LHS, TargetType(ICSLeftToRight),
+                                    ICSLeftToRight, "converting"))
+        return QualType();
+      LTy = LHS->getType();
+    } else if (HaveR2L) {
+      if (PerformImplicitConversion(RHS, TargetType(ICSRightToLeft),
+                                    ICSRightToLeft, "converting"))
+        return QualType();
+      RTy = RHS->getType();
+    }
+  }
+
+  // C++0x 5.16p4
+  //   If the second and third operands are lvalues and have the same type,
+  //   the result is of that type [...]
+  bool Same = Context.getCanonicalType(LTy) == Context.getCanonicalType(RTy);
+  if (Same && LHS->isLvalue(Context) == Expr::LV_Valid &&
+      RHS->isLvalue(Context) == Expr::LV_Valid)
+    return LTy;
+
+  // C++0x 5.16p5
+  //   Otherwise, the result is an rvalue. If the second and third operands
+  //   do not have the same type, and either has (cv) class type, ...
+  if (!Same && (LTy->isRecordType() || RTy->isRecordType())) {
+    //   ... overload resolution is used to determine the conversions (if any)
+    //   to be applied to the operands. If the overload resolution fails, the
+    //   program is ill-formed.
+    if (FindConditionalOverload(*this, LHS, RHS, QuestionLoc))
+      return QualType();
+  }
+
+  // C++0x 5.16p6
+  //   LValue-to-rvalue, array-to-pointer, and function-to-pointer standard
+  //   conversions are performed on the second and third operands.
+  DefaultFunctionArrayConversion(LHS);
+  DefaultFunctionArrayConversion(RHS);
+  LTy = LHS->getType();
+  RTy = RHS->getType();
+
+  //   After those conversions, one of the following shall hold:
+  //   -- The second and third operands have the same type; the result
+  //      is of that type.
+  if (Context.getCanonicalType(LTy) == Context.getCanonicalType(RTy))
+    return LTy;
+
+  //   -- The second and third operands have arithmetic or enumeration type;
+  //      the usual arithmetic conversions are performed to bring them to a
+  //      common type, and the result is of that type.
+  if (LTy->isArithmeticType() && RTy->isArithmeticType()) {
+    UsualArithmeticConversions(LHS, RHS);
+    return LHS->getType();
+  }
+
+  //   -- The second and third operands have pointer type, or one has pointer
+  //      type and the other is a null pointer constant; pointer conversions
+  //      and qualification conversions are performed to bring them to their
+  //      composite pointer type. The result is of the composite pointer type.
+  // Fourth bullet is same for pointers-to-member.
+  if ((LTy->isPointerType() || LTy->isMemberPointerType()) &&
+      RHS->isNullPointerConstant(Context)) {
+    ImpCastExprToType(RHS, LTy); // promote the null to a pointer.
+    return LTy;
+  }
+  if ((RTy->isPointerType() || RTy->isMemberPointerType()) &&
+      LHS->isNullPointerConstant(Context)) {
+    ImpCastExprToType(LHS, RTy); // promote the null to a pointer.
+    return RTy;
+  }
+
+  // FIXME: Handle the case where both are pointers.
+  Diag(QuestionLoc, diag::err_typecheck_cond_incompatible_operands)
+    << LHS->getType() << RHS->getType()
+    << LHS->getSourceRange() << RHS->getSourceRange();
+  return QualType();
+}
diff --git a/lib/Sema/SemaOverload.cpp b/lib/Sema/SemaOverload.cpp
index 70c9ee7..6e2e720 100644
--- a/lib/Sema/SemaOverload.cpp
+++ b/lib/Sema/SemaOverload.cpp
@@ -2026,15 +2026,19 @@
          "Use AddConversionCandidate for conversion functions");
 
   if (CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(Function)) {
-    // If we get here, it's because we're calling a member function
-    // that is named without a member access expression (e.g.,
-    // "this->f") that was either written explicitly or created
-    // implicitly. This can happen with a qualified call to a member
-    // function, e.g., X::f(). We use a NULL object as the implied
-    // object argument (C++ [over.call.func]p3).
-    AddMethodCandidate(Method, 0, Args, NumArgs, CandidateSet, 
-                       SuppressUserConversions, ForceRValue);
-    return;
+    if (!isa<CXXConstructorDecl>(Method)) {
+      // If we get here, it's because we're calling a member function
+      // that is named without a member access expression (e.g.,
+      // "this->f") that was either written explicitly or created
+      // implicitly. This can happen with a qualified call to a member
+      // function, e.g., X::f(). We use a NULL object as the implied
+      // object argument (C++ [over.call.func]p3).
+      AddMethodCandidate(Method, 0, Args, NumArgs, CandidateSet, 
+                         SuppressUserConversions, ForceRValue);
+      return;
+    }
+    // We treat a constructor like a non-member function, since its object
+    // argument doesn't participate in overload resolution.
   }
 
 
@@ -2127,8 +2131,10 @@
   const FunctionProtoType* Proto 
     = dyn_cast<FunctionProtoType>(Method->getType()->getAsFunctionType());
   assert(Proto && "Methods without a prototype cannot be overloaded");
-  assert(!isa<CXXConversionDecl>(Method) && 
+  assert(!isa<CXXConversionDecl>(Method) &&
          "Use AddConversionCandidate for conversion functions");
+  assert(!isa<CXXConstructorDecl>(Method) &&
+         "Use AddOverloadCandidate for constructors");
 
   // Add this candidate
   CandidateSet.push_back(OverloadCandidate());
@@ -2664,7 +2670,7 @@
       Op == OO_Plus || (Op == OO_Minus && NumArgs == 2) || Op == OO_Equal ||
       Op == OO_PlusEqual || Op == OO_MinusEqual || Op == OO_Subscript ||
       Op == OO_ArrowStar || Op == OO_PlusPlus || Op == OO_MinusMinus ||
-      (Op == OO_Star && NumArgs == 1)) {
+      (Op == OO_Star && NumArgs == 1) || Op == OO_Conditional) {
     for (unsigned ArgIdx = 0; ArgIdx < NumArgs; ++ArgIdx)
       CandidateTypes.AddTypesConvertedFrom(Args[ArgIdx]->getType(),
                                            true,
@@ -2939,6 +2945,7 @@
 
   case OO_Slash:
   BinaryStar:
+  Conditional:
     // C++ [over.built]p12:
     //
     //   For every pair of promoted arithmetic types L and R, there
@@ -2957,6 +2964,17 @@
     //
     //   where LR is the result of the usual arithmetic conversions
     //   between types L and R.
+    //
+    // C++ [over.built]p24:
+    //
+    //   For every pair of promoted arithmetic types L and R, there exist
+    //   candidate operator functions of the form
+    //
+    //        LR       operator?(bool, L, R);
+    //
+    //   where LR is the result of the usual arithmetic conversions
+    //   between types L and R.
+    // Our candidates ignore the first parameter.
     for (unsigned Left = FirstPromotedArithmeticType; 
          Left < LastPromotedArithmeticType; ++Left) {
       for (unsigned Right = FirstPromotedArithmeticType; 
@@ -3201,6 +3219,25 @@
   case OO_ArrowStar:
     // FIXME: No support for pointer-to-members yet.
     break;
+
+  case OO_Conditional:
+    // Note that we don't consider the first argument, since it has been
+    // contextually converted to bool long ago. The candidates below are
+    // therefore added as binary.
+    //
+    // C++ [over.built]p24:
+    //   For every type T, where T is a pointer or pointer-to-member type,
+    //   there exist candidate operator functions of the form
+    //
+    //        T        operator?(bool, T, T);
+    //
+    // FIXME: pointer-to-member
+    for (BuiltinCandidateTypeSet::iterator Ptr = CandidateTypes.pointer_begin(),
+         E = CandidateTypes.pointer_end(); Ptr != E; ++Ptr) {
+      QualType ParamTypes[2] = { *Ptr, *Ptr };
+      AddBuiltinCandidate(*Ptr, ParamTypes, Args, 2, CandidateSet);
+    }
+    goto Conditional;
   }
 }
 
@@ -3852,7 +3889,7 @@
   // Perform overload resolution.
   OverloadCandidateSet::iterator Best;
   switch (BestViableFunction(CandidateSet, Best)) {
-  case OR_Success: {
+    case OR_Success: {
       // We found a built-in operator or an overloaded operator.
       FunctionDecl *FnDecl = Best->Function;
 
diff --git a/lib/Sema/SemaOverload.h b/lib/Sema/SemaOverload.h
index e8fad6f..9de3806 100644
--- a/lib/Sema/SemaOverload.h
+++ b/lib/Sema/SemaOverload.h
@@ -169,7 +169,7 @@
 
   /// ImplicitConversionSequence - Represents an implicit conversion
   /// sequence, which may be a standard conversion sequence 
-  // (C++ 13.3.3.1.1), user-defined conversion sequence (C++ 13.3.3.1.2),
+  /// (C++ 13.3.3.1.1), user-defined conversion sequence (C++ 13.3.3.1.2),
   /// or an ellipsis conversion sequence (C++ 13.3.3.1.3).
   struct ImplicitConversionSequence {
     /// Kind - The kind of implicit conversion sequence. BadConversion