Fix an Obj-C++ miscompile when calling an Obj-C method that returns a C++ reference.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@106477 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp
index 8655a66..cfb5af7 100644
--- a/lib/CodeGen/CGExpr.cpp
+++ b/lib/CodeGen/CGExpr.cpp
@@ -1981,10 +1981,17 @@
 }
 
 LValue CodeGenFunction::EmitObjCMessageExprLValue(const ObjCMessageExpr *E) {
-  // Can only get l-value for message expression returning aggregate type
   RValue RV = EmitObjCMessageExpr(E);
-  // FIXME: can this be volatile?
-  return LValue::MakeAddr(RV.getAggregateAddr(), MakeQualifiers(E->getType()));
+  
+  if (!RV.isScalar())
+    return LValue::MakeAddr(RV.getAggregateAddr(),
+                            MakeQualifiers(E->getType()));
+  
+  assert(E->getMethodDecl()->getResultType()->isReferenceType() &&
+         "Can't have a scalar return unless the return type is a "
+         "reference type!");
+  
+  return LValue::MakeAddr(RV.getScalarVal(), MakeQualifiers(E->getType()));
 }
 
 LValue CodeGenFunction::EmitObjCSelectorLValue(const ObjCSelectorExpr *E) {
diff --git a/lib/CodeGen/CGObjC.cpp b/lib/CodeGen/CGObjC.cpp
index 95be0dd..30f7ab5 100644
--- a/lib/CodeGen/CGObjC.cpp
+++ b/lib/CodeGen/CGObjC.cpp
@@ -90,11 +90,14 @@
   CallArgList Args;
   EmitCallArgs(Args, E->getMethodDecl(), E->arg_begin(), E->arg_end());
 
+  QualType ResultType =
+    E->getMethodDecl() ? E->getMethodDecl()->getResultType() : E->getType();
+
   if (isSuperMessage) {
     // super is only valid in an Objective-C method
     const ObjCMethodDecl *OMD = cast<ObjCMethodDecl>(CurFuncDecl);
     bool isCategoryImpl = isa<ObjCCategoryImplDecl>(OMD->getDeclContext());
-    return Runtime.GenerateMessageSendSuper(*this, Return, E->getType(),
+    return Runtime.GenerateMessageSendSuper(*this, Return, ResultType,
                                             E->getSelector(),
                                             OMD->getClassInterface(),
                                             isCategoryImpl,
@@ -104,7 +107,7 @@
                                             E->getMethodDecl());
   }
 
-  return Runtime.GenerateMessageSend(*this, Return, E->getType(),
+  return Runtime.GenerateMessageSend(*this, Return, ResultType,
                                      E->getSelector(),
                                      Receiver, Args, OID,
                                      E->getMethodDecl());
diff --git a/lib/CodeGen/CGObjCMac.cpp b/lib/CodeGen/CGObjCMac.cpp
index 8374aa8..cd27dce 100644
--- a/lib/CodeGen/CGObjCMac.cpp
+++ b/lib/CodeGen/CGObjCMac.cpp
@@ -1634,6 +1634,11 @@
   const llvm::FunctionType *FTy =
     Types.GetFunctionType(FnInfo, Method ? Method->isVariadic() : false);
 
+  if (Method)
+    assert(CGM.getContext().getCanonicalType(Method->getResultType()) ==
+           CGM.getContext().getCanonicalType(ResultType) &&
+           "Result type mismatch!");
+
   llvm::Constant *Fn = NULL;
   if (CGM.ReturnTypeUsesSret(FnInfo)) {
     Fn = (ObjCABI == 2) ?  ObjCTypes.getSendStretFn2(IsSuper)