diff --git a/include/clang/Parse/Ownership.h b/include/clang/Parse/Ownership.h
index 8c7324f..e6cf4a2 100644
--- a/include/clang/Parse/Ownership.h
+++ b/include/clang/Parse/Ownership.h
@@ -400,6 +400,18 @@
   ASTMultiPtr<Destroyer> move(ASTMultiPtr<Destroyer> &ptr) {
     return ASTMultiPtr<Destroyer>(moving::ASTMultiMover<Destroyer>(ptr));
   }
+
+  // A shortcoming of the move emulation is that Ptr = move(Result) doesn't work
+
+  template <ASTDestroyer Destroyer> inline
+  ASTOwningResult<Destroyer> move_convert(ASTOwningPtr<Destroyer> &ptr) {
+    return ASTOwningResult<Destroyer>(moving::ASTPtrMover<Destroyer>(ptr));
+  }
+
+  template <ASTDestroyer Destroyer> inline
+  ASTOwningPtr<Destroyer> move_convert(ASTOwningResult<Destroyer> &ptr) {
+    return ASTOwningPtr<Destroyer>(moving::ASTResultMover<Destroyer>(ptr));
+  }
 }
 
 #endif
diff --git a/include/clang/Parse/Parser.h b/include/clang/Parse/Parser.h
index fafaac5..d6a3efd 100644
--- a/include/clang/Parse/Parser.h
+++ b/include/clang/Parse/Parser.h
@@ -87,6 +87,8 @@
   typedef Action::OwningExprResult OwningExprResult;
   typedef Action::OwningStmtResult OwningStmtResult;
 
+  typedef Action::ExprArg ExprArg;
+
   /// Adorns a ExprResult with Actions to make it an OwningExprResult
   OwningExprResult Owned(ExprResult res) {
     return OwningExprResult(Actions, res);
@@ -594,11 +596,11 @@
   OwningExprResult ParseBraceInitializer();
   OwningExprResult ParseInitializerWithPotentialDesignator(
                        InitListDesignations &D, unsigned InitNum);
-  
+
   //===--------------------------------------------------------------------===//
   // clang Expressions
-  
-  ExprResult ParseBlockLiteralExpression();  // ^{...}
+
+  OwningExprResult ParseBlockLiteralExpression();  // ^{...}
 
   //===--------------------------------------------------------------------===//
   // Objective-C Expressions
@@ -612,21 +614,20 @@
     
     return Tok.getIdentifierInfo() == Ident_super;
   }
-  
-  ExprResult ParseObjCAtExpression(SourceLocation AtLocation);
-  ExprResult ParseObjCStringLiteral(SourceLocation AtLoc);
-  ExprResult ParseObjCEncodeExpression(SourceLocation AtLoc);
-  ExprResult ParseObjCSelectorExpression(SourceLocation AtLoc);
-  ExprResult ParseObjCProtocolExpression(SourceLocation AtLoc);
-  ExprResult ParseObjCMessageExpression();
-  ExprResult ParseObjCMessageExpressionBody(SourceLocation LBracloc,
-                                            SourceLocation NameLoc,
-                                            IdentifierInfo *ReceiverName,
-                                            ExprTy *ReceiverExpr);
-  ExprResult ParseAssignmentExprWithObjCMessageExprStart(SourceLocation LBracloc,
-                                                         SourceLocation NameLoc,
-                                                         IdentifierInfo *ReceiverName,
-                                                         ExprTy *ReceiverExpr);
+
+  OwningExprResult ParseObjCAtExpression(SourceLocation AtLocation);
+  OwningExprResult ParseObjCStringLiteral(SourceLocation AtLoc);
+  OwningExprResult ParseObjCEncodeExpression(SourceLocation AtLoc);
+  OwningExprResult ParseObjCSelectorExpression(SourceLocation AtLoc);
+  OwningExprResult ParseObjCProtocolExpression(SourceLocation AtLoc);
+  OwningExprResult ParseObjCMessageExpression();
+  OwningExprResult ParseObjCMessageExpressionBody(SourceLocation LBracloc,
+                                                  SourceLocation NameLoc,
+                                                  IdentifierInfo *ReceiverName,
+                                                  ExprArg ReceiverExpr);
+  OwningExprResult ParseAssignmentExprWithObjCMessageExprStart(
+      SourceLocation LBracloc, SourceLocation NameLoc,
+      IdentifierInfo *ReceiverName, ExprArg ReceiverExpr);
 
   //===--------------------------------------------------------------------===//
   // C99 6.8: Statements and Blocks.
diff --git a/lib/Parse/ParseExpr.cpp b/lib/Parse/ParseExpr.cpp
index 0d324ec..127ddf4 100644
--- a/lib/Parse/ParseExpr.cpp
+++ b/lib/Parse/ParseExpr.cpp
@@ -186,7 +186,7 @@
 ///
 Parser::OwningExprResult
 Parser::ParseExpressionWithLeadingAt(SourceLocation AtLoc) {
-  OwningExprResult LHS(Actions, ParseObjCAtExpression(AtLoc));
+  OwningExprResult LHS(ParseObjCAtExpression(AtLoc));
   if (LHS.isInvalid()) return move(LHS);
 
   return ParseRHSOfBinaryExpression(move(LHS), prec::Comma);
@@ -212,18 +212,18 @@
 ///
 /// Since this handles full assignment-expression's, it handles postfix
 /// expressions and other binary operators for these expressions as well.
-Parser::ExprResult
+Parser::OwningExprResult
 Parser::ParseAssignmentExprWithObjCMessageExprStart(SourceLocation LBracLoc,
                                                     SourceLocation NameLoc,
                                                    IdentifierInfo *ReceiverName,
-                                                    ExprTy *ReceiverExpr) {
-  OwningExprResult R(Actions, ParseObjCMessageExpressionBody(LBracLoc, NameLoc,
-                                                             ReceiverName,
-                                                             ReceiverExpr));
-  if (R.isInvalid()) return R.result();
+                                                    ExprArg ReceiverExpr) {
+  OwningExprResult R(ParseObjCMessageExpressionBody(LBracLoc, NameLoc,
+                                                    ReceiverName,
+                                                    move(ReceiverExpr)));
+  if (R.isInvalid()) return move(R);
   R = ParsePostfixExpressionSuffix(move(R));
-  if (R.isInvalid()) return R.result();
-  return ParseRHSOfBinaryExpression(move(R), prec::Assignment).result();
+  if (R.isInvalid()) return move(R);
+  return ParseRHSOfBinaryExpression(move(R), prec::Assignment);
 }
 
 
@@ -642,17 +642,17 @@
 
   case tok::at: {
     SourceLocation AtLoc = ConsumeToken();
-    return Owned(ParseObjCAtExpression(AtLoc));
+    return ParseObjCAtExpression(AtLoc);
   }
   case tok::caret:
     if (getLang().Blocks)
-      return ParsePostfixExpressionSuffix(Owned(ParseBlockLiteralExpression()));
+      return ParsePostfixExpressionSuffix(ParseBlockLiteralExpression());
     Diag(Tok, diag::err_expected_expression);
     return ExprError();
   case tok::l_square:
     // These can be followed by postfix-expr pieces.
     if (getLang().ObjC1)
-      return ParsePostfixExpressionSuffix(Owned(ParseObjCMessageExpression()));
+      return ParsePostfixExpressionSuffix(ParseObjCMessageExpression());
     // FALL THROUGH.
   default:
   UnhandledToken:
@@ -1152,10 +1152,10 @@
 /// [clang] block-args:
 /// [clang]   '(' parameter-list ')'
 ///
-Parser::ExprResult Parser::ParseBlockLiteralExpression() {
+Parser::OwningExprResult Parser::ParseBlockLiteralExpression() {
   assert(Tok.is(tok::caret) && "block literal starts with ^");
   SourceLocation CaretLoc = ConsumeToken();
-  
+
   // Enter a scope to hold everything within the block.  This includes the 
   // argument decls, decls within the compound expression, etc.  This also
   // allows determining whether a variable reference inside the block is
@@ -1165,11 +1165,11 @@
 
   // Inform sema that we are starting a block.
   Actions.ActOnBlockStart(CaretLoc, CurScope);
-  
+
   // Parse the return type if present.
   DeclSpec DS;
   Declarator ParamInfo(DS, Declarator::PrototypeContext);
-  
+
   // If this block has arguments, parse them.  There is no ambiguity here with
   // the expression case, because the expression case requires a parameter list.
   if (Tok.is(tok::l_paren)) {
@@ -1180,7 +1180,7 @@
       // If there was an error parsing the arguments, they may have tried to use
       // ^(x+y) which requires an argument list.  Just skip the whole block
       // literal.
-      return true;
+      return ExprError();
     }
   } else {
     // Otherwise, pretend we saw (void).
@@ -1190,7 +1190,7 @@
 
   // Inform sema that we are starting a block.
   Actions.ActOnBlockArguments(ParamInfo);
-  
+
   OwningExprResult Result(Actions, true);
   if (Tok.is(tok::l_brace)) {
     OwningStmtResult Stmt(ParseCompoundStatementBody());
@@ -1200,6 +1200,6 @@
       Actions.ActOnBlockError(CaretLoc, CurScope);
     }
   }
-  return Result.result();
+  return move(Result);
 }
 
diff --git a/lib/Parse/ParseInit.cpp b/lib/Parse/ParseInit.cpp
index 26c40a7..ac13902 100644
--- a/lib/Parse/ParseInit.cpp
+++ b/lib/Parse/ParseInit.cpp
@@ -133,13 +133,13 @@
         else
           Diag(Tok, diag::err_expected_equal_designator);
       }
-      
+
       IdentifierInfo *Name = Tok.getIdentifierInfo();
       SourceLocation NameLoc = ConsumeToken();
-      return Owned(ParseAssignmentExprWithObjCMessageExprStart(
-                       StartLoc, NameLoc, Name, 0));
+      return ParseAssignmentExprWithObjCMessageExprStart(
+                       StartLoc, NameLoc, Name, ExprArg(Actions));
     }
-    
+
     // Note that we parse this as an assignment expression, not a constant
     // expression (allowing *=, =, etc) to handle the objc case.  Sema needs
     // to validate that the expression is a constant.
@@ -168,9 +168,9 @@
           Diag(Tok, diag::err_expected_equal_designator);
       }
 
-      return Owned(ParseAssignmentExprWithObjCMessageExprStart(StartLoc,
-                                                               SourceLocation(),
-                                                             0, Idx.release()));
+      return ParseAssignmentExprWithObjCMessageExprStart(StartLoc,
+                                                         SourceLocation(),
+                                                         0, move_convert(Idx));
     }
 
     // Create designation if we haven't already.
diff --git a/lib/Parse/ParseObjc.cpp b/lib/Parse/ParseObjc.cpp
index 1966512..994e783 100644
--- a/lib/Parse/ParseObjc.cpp
+++ b/lib/Parse/ParseObjc.cpp
@@ -1393,28 +1393,24 @@
   return Owned(Actions.ActOnExprStmt(Res.release()));
 }
 
-Parser::ExprResult Parser::ParseObjCAtExpression(SourceLocation AtLoc) {
+Parser::OwningExprResult Parser::ParseObjCAtExpression(SourceLocation AtLoc) {
   switch (Tok.getKind()) {
   case tok::string_literal:    // primary-expression: string-literal
   case tok::wide_string_literal:
-    return ParsePostfixExpressionSuffix(
-      Owned(ParseObjCStringLiteral(AtLoc))).result();
+    return ParsePostfixExpressionSuffix(ParseObjCStringLiteral(AtLoc));
   default:
     if (Tok.getIdentifierInfo() == 0)
-      return Diag(AtLoc, diag::err_unexpected_at);
+      return ExprError(Diag(AtLoc, diag::err_unexpected_at));
 
     switch (Tok.getIdentifierInfo()->getObjCKeywordID()) {
     case tok::objc_encode:
-      return ParsePostfixExpressionSuffix(
-        Owned(ParseObjCEncodeExpression(AtLoc))).result();
+      return ParsePostfixExpressionSuffix(ParseObjCEncodeExpression(AtLoc));
     case tok::objc_protocol:
-      return ParsePostfixExpressionSuffix(
-        Owned(ParseObjCProtocolExpression(AtLoc))).result();
+      return ParsePostfixExpressionSuffix(ParseObjCProtocolExpression(AtLoc));
     case tok::objc_selector:
-      return ParsePostfixExpressionSuffix(
-        Owned(ParseObjCSelectorExpression(AtLoc))).result();
+      return ParsePostfixExpressionSuffix(ParseObjCSelectorExpression(AtLoc));
     default:
-        return Diag(AtLoc, diag::err_unexpected_at);
+      return ExprError(Diag(AtLoc, diag::err_unexpected_at));
     }
   }
 }
@@ -1426,7 +1422,7 @@
 ///     expression
 ///     class-name
 ///     type-name
-Parser::ExprResult Parser::ParseObjCMessageExpression() {
+Parser::OwningExprResult Parser::ParseObjCMessageExpression() {
   assert(Tok.is(tok::l_square) && "'[' expected");
   SourceLocation LBracLoc = ConsumeBracket(); // consume '['
 
@@ -1434,22 +1430,23 @@
   if (isTokObjCMessageIdentifierReceiver()) {
     IdentifierInfo *ReceiverName = Tok.getIdentifierInfo();
     SourceLocation NameLoc = ConsumeToken();
-    return ParseObjCMessageExpressionBody(LBracLoc, NameLoc, ReceiverName, 0);
+    return ParseObjCMessageExpressionBody(LBracLoc, NameLoc, ReceiverName,
+                                          ExprArg(Actions));
   }
 
   OwningExprResult Res(ParseExpression());
   if (Res.isInvalid()) {
     SkipUntil(tok::r_square);
-    return Res.result();
+    return move(Res);
   }
-  
+
   return ParseObjCMessageExpressionBody(LBracLoc, SourceLocation(),
-                                        0, Res.release());
+                                        0, move_convert(Res));
 }
-  
+
 /// ParseObjCMessageExpressionBody - Having parsed "'[' objc-receiver", parse
 /// the rest of a message expression.
-///  
+/// 
 ///   objc-message-args:
 ///     objc-selector
 ///     objc-keywordarg-list
@@ -1467,12 +1464,12 @@
 ///   nonempty-expr-list:
 ///     assignment-expression
 ///     nonempty-expr-list , assignment-expression
-///   
-Parser::ExprResult
+///
+Parser::OwningExprResult
 Parser::ParseObjCMessageExpressionBody(SourceLocation LBracLoc,
                                        SourceLocation NameLoc,
                                        IdentifierInfo *ReceiverName,
-                                       ExprTy *ReceiverExpr) {
+                                       ExprArg ReceiverExpr) {
   // Parse objc-selector
   SourceLocation Loc;
   IdentifierInfo *selIdent = ParseObjCSelector(Loc);
@@ -1491,9 +1488,9 @@
         // stop at the ']' when it skips to the ';'.  We want it to skip beyond
         // the enclosing expression.
         SkipUntil(tok::r_square);
-        return true;
+        return ExprError();
       }
-      
+
       ConsumeToken(); // Eat the ':'.
       ///  Parse the expression after ':' 
       OwningExprResult Res(ParseAssignmentExpression());
@@ -1502,12 +1499,12 @@
         // stop at the ']' when it skips to the ';'.  We want it to skip beyond
         // the enclosing expression.
         SkipUntil(tok::r_square);
-        return Res.result();
+        return move(Res);
       }
-      
+
       // We have a valid expression.
       KeyExprs.push_back(Res.release());
-      
+
       // Check for another keyword selector.
       selIdent = ParseObjCSelector(Loc);
       if (!selIdent && Tok.isNot(tok::colon))
@@ -1524,7 +1521,7 @@
         // stop at the ']' when it skips to the ';'.  We want it to skip beyond
         // the enclosing expression.
         SkipUntil(tok::r_square);
-        return Res.result();
+        return move(Res);
       }
 
       // We have a valid expression.
@@ -1532,44 +1529,44 @@
     }
   } else if (!selIdent) {
     Diag(Tok, diag::err_expected_ident); // missing selector name.
-    
+
     // We must manually skip to a ']', otherwise the expression skipper will
     // stop at the ']' when it skips to the ';'.  We want it to skip beyond
     // the enclosing expression.
     SkipUntil(tok::r_square);
-    return true;
+    return ExprError();
   }
-  
+
   if (Tok.isNot(tok::r_square)) {
     Diag(Tok, diag::err_expected_rsquare);
     // We must manually skip to a ']', otherwise the expression skipper will
     // stop at the ']' when it skips to the ';'.  We want it to skip beyond
     // the enclosing expression.
     SkipUntil(tok::r_square);
-    return true;
+    return ExprError();
   }
-  
+
   SourceLocation RBracLoc = ConsumeBracket(); // consume ']'
-  
+
   unsigned nKeys = KeyIdents.size();
   if (nKeys == 0)
     KeyIdents.push_back(selIdent);
   Selector Sel = PP.getSelectorTable().getSelector(nKeys, &KeyIdents[0]);
-  
+
   // We've just parsed a keyword message.
-  if (ReceiverName) 
-    return Actions.ActOnClassMessage(CurScope,
-                                     ReceiverName, Sel, 
-                                     LBracLoc, NameLoc, RBracLoc,
-                                     KeyExprs.take(), KeyExprs.size());
-  return Actions.ActOnInstanceMessage(ReceiverExpr, Sel, LBracLoc, RBracLoc,
-                                      KeyExprs.take(), KeyExprs.size());
+  if (ReceiverName)
+    return Owned(Actions.ActOnClassMessage(CurScope, ReceiverName, Sel,
+                                           LBracLoc, NameLoc, RBracLoc,
+                                           KeyExprs.take(), KeyExprs.size()));
+  return Owned(Actions.ActOnInstanceMessage(ReceiverExpr.release(), Sel,
+                                            LBracLoc, RBracLoc,
+                                            KeyExprs.take(), KeyExprs.size()));
 }
 
-Parser::ExprResult Parser::ParseObjCStringLiteral(SourceLocation AtLoc) {
+Parser::OwningExprResult Parser::ParseObjCStringLiteral(SourceLocation AtLoc) {
   OwningExprResult Res(ParseStringLiteralExpression());
-  if (Res.isInvalid()) return Res.result();
-  
+  if (Res.isInvalid()) return move(Res);
+
   // @"foo" @"bar" is a valid concatenated string.  Eat any subsequent string
   // expressions.  At this point, we know that the only valid thing that starts
   // with '@' is an @"".
@@ -1589,79 +1586,82 @@
       Diag(Tok, diag::err_objc_concat_string);
 
     if (Lit.isInvalid())
-      return Lit.result();
+      return move(Lit);
 
     AtStrings.push_back(Lit.release());
   }
-  
-  return Actions.ParseObjCStringLiteral(&AtLocs[0], AtStrings.take(),
-                                        AtStrings.size());
+
+  return Owned(Actions.ParseObjCStringLiteral(&AtLocs[0], AtStrings.take(),
+                                              AtStrings.size()));
 }
 
 ///    objc-encode-expression:
 ///      @encode ( type-name )
-Parser::ExprResult Parser::ParseObjCEncodeExpression(SourceLocation AtLoc) {
+Parser::OwningExprResult
+Parser::ParseObjCEncodeExpression(SourceLocation AtLoc) {
   assert(Tok.isObjCAtKeyword(tok::objc_encode) && "Not an @encode expression!");
-  
+
   SourceLocation EncLoc = ConsumeToken();
-  
+
   if (Tok.isNot(tok::l_paren))
-    return Diag(Tok, diag::err_expected_lparen_after) << "@encode";
-   
+    return ExprError(Diag(Tok, diag::err_expected_lparen_after) << "@encode");
+
   SourceLocation LParenLoc = ConsumeParen();
-  
+
   TypeTy *Ty = ParseTypeName();
-  
+
   SourceLocation RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
-   
-  return Actions.ParseObjCEncodeExpression(AtLoc, EncLoc, LParenLoc, Ty, 
-                                           RParenLoc);
+
+  return Owned(Actions.ParseObjCEncodeExpression(AtLoc, EncLoc, LParenLoc, Ty,
+                                                 RParenLoc));
 }
 
 ///     objc-protocol-expression
 ///       @protocol ( protocol-name )
-Parser::ExprResult Parser::ParseObjCProtocolExpression(SourceLocation AtLoc) {
+Parser::OwningExprResult
+Parser::ParseObjCProtocolExpression(SourceLocation AtLoc) {
   SourceLocation ProtoLoc = ConsumeToken();
-  
+
   if (Tok.isNot(tok::l_paren))
-    return Diag(Tok, diag::err_expected_lparen_after) << "@protocol";
-  
+    return ExprError(Diag(Tok, diag::err_expected_lparen_after) << "@protocol");
+
   SourceLocation LParenLoc = ConsumeParen();
-  
+
   if (Tok.isNot(tok::identifier))
-    return Diag(Tok, diag::err_expected_ident);
-  
+    return ExprError(Diag(Tok, diag::err_expected_ident));
+
   IdentifierInfo *protocolId = Tok.getIdentifierInfo();
   ConsumeToken();
-  
+
   SourceLocation RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
 
-  return Actions.ParseObjCProtocolExpression(protocolId, AtLoc, ProtoLoc, 
-                                             LParenLoc, RParenLoc);
+  return Owned(Actions.ParseObjCProtocolExpression(protocolId, AtLoc, ProtoLoc,
+                                                   LParenLoc, RParenLoc));
 }
 
 ///     objc-selector-expression
 ///       @selector '(' objc-keyword-selector ')'
-Parser::ExprResult Parser::ParseObjCSelectorExpression(SourceLocation AtLoc) {
+Parser::OwningExprResult
+Parser::ParseObjCSelectorExpression(SourceLocation AtLoc) {
   SourceLocation SelectorLoc = ConsumeToken();
-  
+
   if (Tok.isNot(tok::l_paren))
-    return Diag(Tok, diag::err_expected_lparen_after) << "@selector";
-  
+    return ExprError(Diag(Tok, diag::err_expected_lparen_after) << "@selector");
+
   llvm::SmallVector<IdentifierInfo *, 12> KeyIdents;
   SourceLocation LParenLoc = ConsumeParen();
   SourceLocation sLoc;
   IdentifierInfo *SelIdent = ParseObjCSelector(sLoc);
-  if (!SelIdent && Tok.isNot(tok::colon))
-    return Diag(Tok, diag::err_expected_ident); // missing selector name.
-  
+  if (!SelIdent && Tok.isNot(tok::colon)) // missing selector name.
+    return ExprError(Diag(Tok, diag::err_expected_ident));
+
   KeyIdents.push_back(SelIdent);
   unsigned nColons = 0;
   if (Tok.isNot(tok::r_paren)) {
     while (1) {
       if (Tok.isNot(tok::colon))
-        return Diag(Tok, diag::err_expected_colon);
-      
+        return ExprError(Diag(Tok, diag::err_expected_colon));
+
       nColons++;
       ConsumeToken(); // Eat the ':'.
       if (Tok.is(tok::r_paren))
@@ -1676,6 +1676,6 @@
   }
   SourceLocation RParenLoc = MatchRHSPunctuation(tok::r_paren, LParenLoc);
   Selector Sel = PP.getSelectorTable().getSelector(nColons, &KeyIdents[0]);
-  return Actions.ParseObjCSelectorExpression(Sel, AtLoc, SelectorLoc, LParenLoc, 
-                                             RParenLoc);
+  return Owned(Actions.ParseObjCSelectorExpression(Sel, AtLoc, SelectorLoc,
+                                                   LParenLoc, RParenLoc));
  }
