diff options
author | Anders Carlsson <andersca@mac.com> | 2009-08-16 05:13:48 +0000 |
---|---|---|
committer | Anders Carlsson <andersca@mac.com> | 2009-08-16 05:13:48 +0000 |
commit | 9abf2aedae7538cfd85f3ff0898a6d14385c8e36 (patch) | |
tree | a173ddcd8f0aa57278b894e1c9917e79bb556e0f | |
parent | 2d46eb21eb2c904831b0e9f75ab3523384c70e66 (diff) |
AddInitializerToDecl can't take a FullExprArg. Make it take an ExprArg, and create the CXXExprWithTemporaries before setting the initializer on the VarDecl.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@79176 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | include/clang/Parse/Action.h | 2 | ||||
-rw-r--r-- | lib/Frontend/PrintParserCallbacks.cpp | 2 | ||||
-rw-r--r-- | lib/Parse/ParseDecl.cpp | 2 | ||||
-rw-r--r-- | lib/Sema/Sema.h | 10 | ||||
-rw-r--r-- | lib/Sema/SemaDecl.cpp | 6 | ||||
-rw-r--r-- | lib/Sema/SemaDeclCXX.cpp | 28 | ||||
-rw-r--r-- | lib/Sema/SemaExprCXX.cpp | 6 | ||||
-rw-r--r-- | lib/Sema/SemaInit.cpp | 5 |
8 files changed, 42 insertions, 19 deletions
diff --git a/include/clang/Parse/Action.h b/include/clang/Parse/Action.h index cef378f558..8706139988 100644 --- a/include/clang/Parse/Action.h +++ b/include/clang/Parse/Action.h @@ -310,7 +310,7 @@ public: /// This allows ActOnDeclarator to register "xx" prior to parsing the /// initializer. The declaration above should still result in a warning, /// since the reference to "xx" is uninitialized. - virtual void AddInitializerToDecl(DeclPtrTy Dcl, FullExprArg Init) { + virtual void AddInitializerToDecl(DeclPtrTy Dcl, ExprArg Init) { return; } diff --git a/lib/Frontend/PrintParserCallbacks.cpp b/lib/Frontend/PrintParserCallbacks.cpp index 2101a85f41..9d6ea73eef 100644 --- a/lib/Frontend/PrintParserCallbacks.cpp +++ b/lib/Frontend/PrintParserCallbacks.cpp @@ -109,7 +109,7 @@ namespace { /// This allows ActOnDeclarator to register "xx" prior to parsing the /// initializer. The declaration above should still result in a warning, /// since the reference to "xx" is uninitialized. - virtual void AddInitializerToDecl(DeclPtrTy Dcl, FullExprArg Init) { + virtual void AddInitializerToDecl(DeclPtrTy Dcl, ExprArg Init) { Out << __FUNCTION__ << "\n"; } diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp index 029d9b5aae..9958bdf566 100644 --- a/lib/Parse/ParseDecl.cpp +++ b/lib/Parse/ParseDecl.cpp @@ -446,7 +446,7 @@ Parser::DeclPtrTy Parser::ParseDeclarationAfterDeclarator(Declarator &D, SkipUntil(tok::semi, true, true); return DeclPtrTy(); } - Actions.AddInitializerToDecl(ThisDecl, Actions.FullExpr(Init)); + Actions.AddInitializerToDecl(ThisDecl, move(Init)); } } else if (Tok.is(tok::l_paren)) { // Parse C++ direct initializer: '(' expression-list ')' diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h index d17e2f1498..d3bdec8f39 100644 --- a/lib/Sema/Sema.h +++ b/lib/Sema/Sema.h @@ -503,7 +503,7 @@ public: // argument locations. llvm::DenseMap<ParmVarDecl *,SourceLocation> UnparsedDefaultArgLocs; - virtual void AddInitializerToDecl(DeclPtrTy dcl, FullExprArg init); + virtual void AddInitializerToDecl(DeclPtrTy dcl, ExprArg init); void AddInitializerToDecl(DeclPtrTy dcl, ExprArg init, bool DirectInit); void ActOnUninitializedDecl(DeclPtrTy dcl, bool TypeContainsUndeducedAuto); virtual void SetDeclDeleted(DeclPtrTy dcl, SourceLocation DelLoc); @@ -1689,15 +1689,17 @@ public: CXXConstructorDecl *Constructor, QualType DeclInitType, Expr **Exprs, unsigned NumExprs); - + + Expr *BuildCXXConstructExpr(QualType DeclInitType, + CXXConstructorDecl *Constructor, + Expr **Exprs, unsigned NumExprs); + /// BuildCXXConstructExpr - Creates a complete call to a constructor, /// including handling of its default argument expressions. Expr *BuildCXXConstructExpr(QualType DeclInitType, CXXConstructorDecl *Constructor, bool Elidable, Expr **Exprs, unsigned NumExprs); - - Expr *BuildCXXCopyConstructExpr(Expr *Expr); /// FinalizeVarWithDestructor - Prepare for calling destructor on the /// constructed variable. diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp index bf1dd91f74..b672d0501a 100644 --- a/lib/Sema/SemaDecl.cpp +++ b/lib/Sema/SemaDecl.cpp @@ -2996,8 +2996,8 @@ bool Sema::CheckForConstantInitializer(Expr *Init, QualType DclT) { return true; } -void Sema::AddInitializerToDecl(DeclPtrTy dcl, FullExprArg init) { - AddInitializerToDecl(dcl, init.release(), /*DirectInit=*/false); +void Sema::AddInitializerToDecl(DeclPtrTy dcl, ExprArg init) { + AddInitializerToDecl(dcl, move(init), /*DirectInit=*/false); } /// AddInitializerToDecl - Adds the initializer Init to the @@ -3160,6 +3160,8 @@ void Sema::AddInitializerToDecl(DeclPtrTy dcl, ExprArg init, bool DirectInit) { Init->setType(DclT); } + Init = MaybeCreateCXXExprWithTemporaries(Init, + /*ShouldDestroyTemporaries=*/true); // Attach the initializer to the decl. VDecl->setInit(Context, Init); diff --git a/lib/Sema/SemaDeclCXX.cpp b/lib/Sema/SemaDeclCXX.cpp index d460950824..068978cd92 100644 --- a/lib/Sema/SemaDeclCXX.cpp +++ b/lib/Sema/SemaDeclCXX.cpp @@ -2377,6 +2377,32 @@ void Sema::DefineImplicitCopyConstructor(SourceLocation CurrentLocation, CopyConstructor->setUsed(); } +Expr *Sema::BuildCXXConstructExpr(QualType DeclInitType, + CXXConstructorDecl *Constructor, + Expr **Exprs, unsigned NumExprs) { + bool Elidable = false; + + // [class.copy]p15: + // Whenever a temporary class object is copied using a copy constructor, and + // this object and the copy have the same cv-unqualified type, an + // implementation is permitted to treat the original and the copy as two + // different ways of referring to the same object and not perform a copy at + //all, even if the class copy constructor or destructor have side effects. + + // FIXME: Is this enough? + if (Constructor->isCopyConstructor(Context) && NumExprs == 1) { + Expr *E = Exprs[0]; + while (CXXBindTemporaryExpr *BE = dyn_cast<CXXBindTemporaryExpr>(E)) + E = BE->getSubExpr(); + + if (isa<CallExpr>(E) || isa<CXXTemporaryObjectExpr>(E)) + Elidable = true; + } + + return BuildCXXConstructExpr(DeclInitType, Constructor, Elidable, + Exprs, NumExprs); +} + /// BuildCXXConstructExpr - Creates a complete call to a constructor, /// including handling of its default argument expressions. Expr *Sema::BuildCXXConstructExpr(QualType DeclInitType, @@ -2413,7 +2439,7 @@ void Sema::InitializeVarWithConstructor(VarDecl *VD, QualType DeclInitType, Expr **Exprs, unsigned NumExprs) { Expr *Temp = BuildCXXConstructExpr(DeclInitType, Constructor, - false, Exprs, NumExprs); + Exprs, NumExprs); MarkDeclarationReferenced(VD->getLocation(), Constructor); Temp = MaybeCreateCXXExprWithTemporaries(Temp, /*DestroyTemps=*/true); VD->setInit(Context, Temp); diff --git a/lib/Sema/SemaExprCXX.cpp b/lib/Sema/SemaExprCXX.cpp index 274893b99e..f313c5653e 100644 --- a/lib/Sema/SemaExprCXX.cpp +++ b/lib/Sema/SemaExprCXX.cpp @@ -902,11 +902,7 @@ Sema::PerformImplicitConversion(Expr *&From, QualType ToType, // FIXME: When can ToType be a reference type? assert(!ToType->isReferenceType()); - // FIXME: Keep track of whether the copy constructor is elidable or not. - bool Elidable = (isa<CallExpr>(From) || - isa<CXXTemporaryObjectExpr>(From)); - From = BuildCXXConstructExpr(ToType, SCS.CopyConstructor, - Elidable, &From, 1); + From = BuildCXXConstructExpr(ToType, SCS.CopyConstructor, &From, 1); return false; } diff --git a/lib/Sema/SemaInit.cpp b/lib/Sema/SemaInit.cpp index f734d9347a..ce6a99acd9 100644 --- a/lib/Sema/SemaInit.cpp +++ b/lib/Sema/SemaInit.cpp @@ -176,10 +176,7 @@ bool Sema::CheckInitializerTypes(Expr *&Init, QualType &DeclType, DirectInit? IK_Direct : IK_Copy); if (!Constructor) return true; - bool Elidable = (isa<CallExpr>(Init) || - isa<CXXTemporaryObjectExpr>(Init)); - Init = BuildCXXConstructExpr(DeclType, Constructor, Elidable, &Init, 1); - Init = MaybeCreateCXXExprWithTemporaries(Init, /*DestroyTemps=*/true); + Init = BuildCXXConstructExpr(DeclType, Constructor, &Init, 1); return false; } |