]> granicus.if.org Git - clang/commitdiff
Forgot the implementation. Thanks Eli.
authorAnders Carlsson <andersca@mac.com>
Sat, 30 May 2009 22:51:20 +0000 (22:51 +0000)
committerAnders Carlsson <andersca@mac.com>
Sat, 30 May 2009 22:51:20 +0000 (22:51 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@72647 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Sema/SemaExprCXX.cpp

index a8a260dd2e1081dcff09cb4046a13db04328d333..73cc0513f0489a355c31129d897ccb4190ea7d8f 100644 (file)
@@ -1542,6 +1542,47 @@ Sema::OwningExprResult Sema::MaybeBindToTemporary(Expr *E) {
   return Owned(CXXBindTemporaryExpr::Create(Context, Temp, E));
 }
 
+// FIXME: This doesn't handle casts yet.
+Expr *Sema::RemoveOutermostTemporaryBinding(Expr *E) {
+  const RecordType *RT = E->getType()->getAsRecordType();
+  if (!RT)
+    return E;
+  
+  CXXRecordDecl *RD = cast<CXXRecordDecl>(RT->getDecl());
+  if (RD->hasTrivialDestructor())
+    return E;
+  
+  /// The expr passed in must be a CXXExprWithTemporaries.
+  CXXExprWithTemporaries *TempExpr = dyn_cast<CXXExprWithTemporaries>(E);
+  if (!TempExpr)
+    return E;
+  
+  Expr *SubExpr = TempExpr->getSubExpr();
+  if (CXXBindTemporaryExpr *BE = dyn_cast<CXXBindTemporaryExpr>(SubExpr)) {
+    assert(BE->getTemporary() == 
+             TempExpr->getTemporary(TempExpr->getNumTemporaries() - 1) &&
+           "Found temporary is not last in list!");
+
+    Expr *BindSubExpr = BE->getSubExpr();
+    BE->setSubExpr(0);
+    
+    if (TempExpr->getNumTemporaries() == 1) {
+      // There's just one temporary left, so we don't need the TempExpr node.
+      TempExpr->Destroy(Context);
+      return BindSubExpr;
+    } else {
+      TempExpr->removeLastTemporary();
+      TempExpr->setSubExpr(BindSubExpr);
+      BE->Destroy(Context);
+    }
+    
+    return E;
+  } 
+  
+  // FIXME: We might need to handle other expressions here.
+  return E;
+}
+
 Sema::OwningExprResult Sema::ActOnFinishFullExpr(ExprArg Arg) {
   Expr *FullExpr = Arg.takeAs<Expr>();