<div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr"><div dir="ltr">Hey Richard,<div><br></div><div>It appears this broke the lldb bots:</div><div><br></div><div><a href="http://lab.llvm.org:8011/builders/lldb-x86_64-debian">http://lab.llvm.org:8011/builders/lldb-x86_64-debian</a><br></div><div><a href="http://green.lab.llvm.org/green/view/LLDB/job/lldb-cmake/20549/">http://green.lab.llvm.org/green/view/LLDB/job/lldb-cmake/20549/</a><br></div><div><br></div><div>It's hitting an assertion in llvm-project/clang/include/clang/AST/DeclCXX.h:887: </div><div><br></div><div>Assertion `(data().DefaultedCopyAssignmentIsDeleted || needsOverloadResolutionForCopyAssignment()) && "copy assignment should not be deleted"' failed.</div><div><br></div><div>I've reverted this commit and the subsequent one (c57f8a3a20540fcf9fbf98c0a73f381ec32fce2a) to turn the bots green again overnight. Could you please take a look tomorrow?</div><div><br></div><div>Thanks,</div><div>Jonas </div><div><br></div><div><br></div></div></div></div></div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Thu, Jun 4, 2020 at 7:25 PM Richard Smith via cfe-commits <<a href="mailto:cfe-commits@lists.llvm.org">cfe-commits@lists.llvm.org</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-style:solid;border-left-color:rgb(204,204,204);padding-left:1ex"><br>
Author: Richard Smith<br>
Date: 2020-06-04T19:19:01-07:00<br>
New Revision: c13dd74e311d2ac70dd3ea663d800307d1aa5b6b<br>
<br>
URL: <a href="https://github.com/llvm/llvm-project/commit/c13dd74e311d2ac70dd3ea663d800307d1aa5b6b" rel="noreferrer" target="_blank">https://github.com/llvm/llvm-project/commit/c13dd74e311d2ac70dd3ea663d800307d1aa5b6b</a><br>
DIFF: <a href="https://github.com/llvm/llvm-project/commit/c13dd74e311d2ac70dd3ea663d800307d1aa5b6b.diff" rel="noreferrer" target="_blank">https://github.com/llvm/llvm-project/commit/c13dd74e311d2ac70dd3ea663d800307d1aa5b6b.diff</a><br>
<br>
LOG: Set the captures on a CXXRecordDecl representing a lambda closure type<br>
before marking it complete.<br>
<br>
No functionality change intended.<br>
<br>
Added: <br>
<br>
<br>
Modified: <br>
clang/include/clang/AST/DeclCXX.h<br>
clang/include/clang/AST/ExprCXX.h<br>
clang/lib/AST/ASTImporter.cpp<br>
clang/lib/AST/DeclCXX.cpp<br>
clang/lib/AST/ExprCXX.cpp<br>
clang/lib/Sema/SemaLambda.cpp<br>
<br>
Removed: <br>
<br>
<br>
<br>
################################################################################<br>
diff --git a/clang/include/clang/AST/DeclCXX.h b/clang/include/clang/AST/DeclCXX.h<br>
index 3a400a778e53..856717fa0abb 100644<br>
--- a/clang/include/clang/AST/DeclCXX.h<br>
+++ b/clang/include/clang/AST/DeclCXX.h<br>
@@ -999,6 +999,9 @@ class CXXRecordDecl : public RecordDecl {<br>
return static_cast<LambdaCaptureDefault>(getLambdaData().CaptureDefault);<br>
}<br>
<br>
+ /// Set the captures for this lambda closure type.<br>
+ void setCaptures(ArrayRef<LambdaCapture> Captures);<br>
+<br>
/// For a closure type, retrieve the mapping from captured<br>
/// variables and \c this to the non-static data members that store the<br>
/// values or references of the captures.<br>
@@ -1030,6 +1033,8 @@ class CXXRecordDecl : public RecordDecl {<br>
: nullptr;<br>
}<br>
<br>
+ unsigned capture_size() const { return getLambdaData().NumCaptures; }<br>
+<br>
using conversion_iterator = UnresolvedSetIterator;<br>
<br>
conversion_iterator conversion_begin() const {<br>
<br>
diff --git a/clang/include/clang/AST/ExprCXX.h b/clang/include/clang/AST/ExprCXX.h<br>
index 272ad138d14a..56b27d57bd5c 100644<br>
--- a/clang/include/clang/AST/ExprCXX.h<br>
+++ b/clang/include/clang/AST/ExprCXX.h<br>
@@ -1862,10 +1862,9 @@ class LambdaExpr final : public Expr,<br>
/// Construct a lambda expression.<br>
LambdaExpr(QualType T, SourceRange IntroducerRange,<br>
LambdaCaptureDefault CaptureDefault,<br>
- SourceLocation CaptureDefaultLoc, ArrayRef<LambdaCapture> Captures,<br>
- bool ExplicitParams, bool ExplicitResultType,<br>
- ArrayRef<Expr *> CaptureInits, SourceLocation ClosingBrace,<br>
- bool ContainsUnexpandedParameterPack);<br>
+ SourceLocation CaptureDefaultLoc, bool ExplicitParams,<br>
+ bool ExplicitResultType, ArrayRef<Expr *> CaptureInits,<br>
+ SourceLocation ClosingBrace, bool ContainsUnexpandedParameterPack);<br>
<br>
/// Construct an empty lambda expression.<br>
LambdaExpr(EmptyShell Empty, unsigned NumCaptures)<br>
@@ -1888,9 +1887,9 @@ class LambdaExpr final : public Expr,<br>
static LambdaExpr *<br>
Create(const ASTContext &C, CXXRecordDecl *Class, SourceRange IntroducerRange,<br>
LambdaCaptureDefault CaptureDefault, SourceLocation CaptureDefaultLoc,<br>
- ArrayRef<LambdaCapture> Captures, bool ExplicitParams,<br>
- bool ExplicitResultType, ArrayRef<Expr *> CaptureInits,<br>
- SourceLocation ClosingBrace, bool ContainsUnexpandedParameterPack);<br>
+ bool ExplicitParams, bool ExplicitResultType,<br>
+ ArrayRef<Expr *> CaptureInits, SourceLocation ClosingBrace,<br>
+ bool ContainsUnexpandedParameterPack);<br>
<br>
/// Construct a new lambda expression that will be deserialized from<br>
/// an external source.<br>
<br>
diff --git a/clang/lib/AST/ASTImporter.cpp b/clang/lib/AST/ASTImporter.cpp<br>
index 10035162299e..a2a712e6b6ca 100644<br>
--- a/clang/lib/AST/ASTImporter.cpp<br>
+++ b/clang/lib/AST/ASTImporter.cpp<br>
@@ -1890,6 +1890,19 @@ Error ASTNodeImporter::ImportDefinition(<br>
// set in CXXRecordDecl::CreateLambda. We must import the contained<br>
// decls here and finish the definition.<br>
(To->isLambda() && shouldForceImportDeclContext(Kind))) {<br>
+ if (To->isLambda()) {<br>
+ auto *FromCXXRD = cast<CXXRecordDecl>(From);<br>
+ SmallVector<LambdaCapture, 8> ToCaptures;<br>
+ ToCaptures.reserve(FromCXXRD->capture_size());<br>
+ for (const auto &FromCapture : FromCXXRD->captures()) {<br>
+ if (auto ToCaptureOrErr = import(FromCapture))<br>
+ ToCaptures.push_back(*ToCaptureOrErr);<br>
+ else<br>
+ return ToCaptureOrErr.takeError();<br>
+ }<br>
+ cast<CXXRecordDecl>(To)->setCaptures(ToCaptures);<br>
+ }<br>
+<br>
Error Result = ImportDeclContext(From, /*ForceImport=*/true);<br>
// Finish the definition of the lambda, set isBeingDefined to false.<br>
if (To->isLambda())<br>
@@ -7588,15 +7601,6 @@ ExpectedStmt ASTNodeImporter::VisitLambdaExpr(LambdaExpr *E) {<br>
if (!ToCallOpOrErr)<br>
return ToCallOpOrErr.takeError();<br>
<br>
- SmallVector<LambdaCapture, 8> ToCaptures;<br>
- ToCaptures.reserve(E->capture_size());<br>
- for (const auto &FromCapture : E->captures()) {<br>
- if (auto ToCaptureOrErr = import(FromCapture))<br>
- ToCaptures.push_back(*ToCaptureOrErr);<br>
- else<br>
- return ToCaptureOrErr.takeError();<br>
- }<br>
-<br>
SmallVector<Expr *, 8> ToCaptureInits(E->capture_size());<br>
if (Error Err = ImportContainerChecked(E->capture_inits(), ToCaptureInits))<br>
return std::move(Err);<br>
@@ -7608,11 +7612,11 @@ ExpectedStmt ASTNodeImporter::VisitLambdaExpr(LambdaExpr *E) {<br>
if (Err)<br>
return std::move(Err);<br>
<br>
- return LambdaExpr::Create(<br>
- Importer.getToContext(), ToClass, ToIntroducerRange,<br>
- E->getCaptureDefault(), ToCaptureDefaultLoc, ToCaptures,<br>
- E->hasExplicitParameters(), E->hasExplicitResultType(), ToCaptureInits,<br>
- ToEndLoc, E->containsUnexpandedParameterPack());<br>
+ return LambdaExpr::Create(Importer.getToContext(), ToClass, ToIntroducerRange,<br>
+ E->getCaptureDefault(), ToCaptureDefaultLoc,<br>
+ E->hasExplicitParameters(),<br>
+ E->hasExplicitResultType(), ToCaptureInits,<br>
+ ToEndLoc, E->containsUnexpandedParameterPack());<br>
}<br>
<br>
<br>
<br>
diff --git a/clang/lib/AST/DeclCXX.cpp b/clang/lib/AST/DeclCXX.cpp<br>
index 5412aa7ed5e0..4d184b5a4703 100644<br>
--- a/clang/lib/AST/DeclCXX.cpp<br>
+++ b/clang/lib/AST/DeclCXX.cpp<br>
@@ -664,8 +664,7 @@ bool CXXRecordDecl::lambdaIsDefaultConstructibleAndAssignable() const {<br>
// C++17 [expr.prim.lambda]p21:<br>
// The closure type associated with a lambda-expression has no default<br>
// constructor and a deleted copy assignment operator.<br>
- if (getLambdaCaptureDefault() != LCD_None ||<br>
- getLambdaData().NumCaptures != 0)<br>
+ if (getLambdaCaptureDefault() != LCD_None || capture_size() != 0)<br>
return false;<br>
return getASTContext().getLangOpts().CPlusPlus20;<br>
}<br>
@@ -1367,6 +1366,24 @@ void CXXRecordDecl::finishedDefaultedOrDeletedMember(CXXMethodDecl *D) {<br>
data().DeclaredNonTrivialSpecialMembers |= SMKind;<br>
}<br>
<br>
+void CXXRecordDecl::setCaptures(ArrayRef<LambdaCapture> Captures) {<br>
+ ASTContext &Context = getASTContext();<br>
+ CXXRecordDecl::LambdaDefinitionData &Data = getLambdaData();<br>
+<br>
+ // Copy captures.<br>
+ Data.NumCaptures = Captures.size();<br>
+ Data.NumExplicitCaptures = 0;<br>
+ Data.Captures = (LambdaCapture *)Context.Allocate(sizeof(LambdaCapture) *<br>
+ Captures.size());<br>
+ LambdaCapture *ToCapture = Data.Captures;<br>
+ for (unsigned I = 0, N = Captures.size(); I != N; ++I) {<br>
+ if (Captures[I].isExplicit())<br>
+ ++Data.NumExplicitCaptures;<br>
+<br>
+ *ToCapture++ = Captures[I];<br>
+ }<br>
+}<br>
+<br>
void CXXRecordDecl::setTrivialForCallFlags(CXXMethodDecl *D) {<br>
unsigned SMKind = 0;<br>
<br>
<br>
diff --git a/clang/lib/AST/ExprCXX.cpp b/clang/lib/AST/ExprCXX.cpp<br>
index cfbf2c88c4cc..2b148b4fa768 100644<br>
--- a/clang/lib/AST/ExprCXX.cpp<br>
+++ b/clang/lib/AST/ExprCXX.cpp<br>
@@ -1087,35 +1087,18 @@ LambdaCaptureKind LambdaCapture::getCaptureKind() const {<br>
<br>
LambdaExpr::LambdaExpr(QualType T, SourceRange IntroducerRange,<br>
LambdaCaptureDefault CaptureDefault,<br>
- SourceLocation CaptureDefaultLoc,<br>
- ArrayRef<LambdaCapture> Captures, bool ExplicitParams,<br>
+ SourceLocation CaptureDefaultLoc, bool ExplicitParams,<br>
bool ExplicitResultType, ArrayRef<Expr *> CaptureInits,<br>
SourceLocation ClosingBrace,<br>
bool ContainsUnexpandedParameterPack)<br>
: Expr(LambdaExprClass, T, VK_RValue, OK_Ordinary),<br>
IntroducerRange(IntroducerRange), CaptureDefaultLoc(CaptureDefaultLoc),<br>
- NumCaptures(Captures.size()), CaptureDefault(CaptureDefault),<br>
+ NumCaptures(CaptureInits.size()), CaptureDefault(CaptureDefault),<br>
ExplicitParams(ExplicitParams), ExplicitResultType(ExplicitResultType),<br>
ClosingBrace(ClosingBrace) {<br>
- assert(CaptureInits.size() == Captures.size() && "Wrong number of arguments");<br>
CXXRecordDecl *Class = getLambdaClass();<br>
- CXXRecordDecl::LambdaDefinitionData &Data = Class->getLambdaData();<br>
-<br>
- // FIXME: Propagate "has unexpanded parameter pack" bit.<br>
-<br>
- // Copy captures.<br>
- const ASTContext &Context = Class->getASTContext();<br>
- Data.NumCaptures = NumCaptures;<br>
- Data.NumExplicitCaptures = 0;<br>
- Data.Captures =<br>
- (LambdaCapture *)Context.Allocate(sizeof(LambdaCapture) * NumCaptures);<br>
- LambdaCapture *ToCapture = Data.Captures;<br>
- for (unsigned I = 0, N = Captures.size(); I != N; ++I) {<br>
- if (Captures[I].isExplicit())<br>
- ++Data.NumExplicitCaptures;<br>
-<br>
- *ToCapture++ = Captures[I];<br>
- }<br>
+ assert(NumCaptures == Class->capture_size() && "Wrong number of captures");<br>
+ assert(CaptureDefault == Class->getLambdaCaptureDefault());<br>
<br>
// Copy initialization expressions for the non-static data members.<br>
Stmt **Stored = getStoredStmts();<br>
@@ -1128,22 +1111,24 @@ LambdaExpr::LambdaExpr(QualType T, SourceRange IntroducerRange,<br>
setDependence(computeDependence(this, ContainsUnexpandedParameterPack));<br>
}<br>
<br>
-LambdaExpr *LambdaExpr::Create(<br>
- const ASTContext &Context, CXXRecordDecl *Class,<br>
- SourceRange IntroducerRange, LambdaCaptureDefault CaptureDefault,<br>
- SourceLocation CaptureDefaultLoc, ArrayRef<LambdaCapture> Captures,<br>
- bool ExplicitParams, bool ExplicitResultType, ArrayRef<Expr *> CaptureInits,<br>
- SourceLocation ClosingBrace, bool ContainsUnexpandedParameterPack) {<br>
+LambdaExpr *LambdaExpr::Create(const ASTContext &Context, CXXRecordDecl *Class,<br>
+ SourceRange IntroducerRange,<br>
+ LambdaCaptureDefault CaptureDefault,<br>
+ SourceLocation CaptureDefaultLoc,<br>
+ bool ExplicitParams, bool ExplicitResultType,<br>
+ ArrayRef<Expr *> CaptureInits,<br>
+ SourceLocation ClosingBrace,<br>
+ bool ContainsUnexpandedParameterPack) {<br>
// Determine the type of the expression (i.e., the type of the<br>
// function object we're creating).<br>
QualType T = Context.getTypeDeclType(Class);<br>
<br>
- unsigned Size = totalSizeToAlloc<Stmt *>(Captures.size() + 1);<br>
+ unsigned Size = totalSizeToAlloc<Stmt *>(CaptureInits.size() + 1);<br>
void *Mem = Context.Allocate(Size);<br>
return new (Mem)<br>
LambdaExpr(T, IntroducerRange, CaptureDefault, CaptureDefaultLoc,<br>
- Captures, ExplicitParams, ExplicitResultType, CaptureInits,<br>
- ClosingBrace, ContainsUnexpandedParameterPack);<br>
+ ExplicitParams, ExplicitResultType, CaptureInits, ClosingBrace,<br>
+ ContainsUnexpandedParameterPack);<br>
}<br>
<br>
LambdaExpr *LambdaExpr::CreateDeserialized(const ASTContext &C,<br>
<br>
diff --git a/clang/lib/Sema/SemaLambda.cpp b/clang/lib/Sema/SemaLambda.cpp<br>
index b4336aa430eb..e751a73957d0 100644<br>
--- a/clang/lib/Sema/SemaLambda.cpp<br>
+++ b/clang/lib/Sema/SemaLambda.cpp<br>
@@ -1782,6 +1782,8 @@ ExprResult Sema::BuildLambdaExpr(SourceLocation StartLoc, SourceLocation EndLoc,<br>
CaptureInits.push_back(Init.get());<br>
}<br>
<br>
+ Class->setCaptures(Captures);<br>
+<br>
// C++11 [expr.prim.lambda]p6:<br>
// The closure type for a lambda-expression with no lambda-capture<br>
// has a public non-virtual non-explicit const conversion function<br>
@@ -1811,7 +1813,6 @@ ExprResult Sema::BuildLambdaExpr(SourceLocation StartLoc, SourceLocation EndLoc,<br>
<br>
LambdaExpr *Lambda = LambdaExpr::Create(Context, Class, IntroducerRange,<br>
CaptureDefault, CaptureDefaultLoc,<br>
- Captures,<br>
ExplicitParams, ExplicitResultType,<br>
CaptureInits, EndLoc,<br>
ContainsUnexpandedParameterPack);<br>
<br>
<br>
<br>
_______________________________________________<br>
cfe-commits mailing list<br>
<a href="mailto:cfe-commits@lists.llvm.org" target="_blank">cfe-commits@lists.llvm.org</a><br>
<a href="https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits" rel="noreferrer" target="_blank">https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits</a><br>
</blockquote></div>