https://github.com/MitalAshok updated https://github.com/llvm/llvm-project/pull/101385
>From 555373715bc2eb025d6580129cead087f7f45ed1 Mon Sep 17 00:00:00 2001 From: Mital Ashok <mi...@mitalashok.co.uk> Date: Fri, 7 Jul 2023 14:31:03 +0100 Subject: [PATCH] [Clang][SemaCXX] Fix bug where unexpanded lambda captures where assumed to have size 1 --- clang/docs/ReleaseNotes.rst | 1 + clang/lib/Sema/SemaTemplateInstantiate.cpp | 3 ++- clang/lib/Sema/TreeTransform.h | 6 ++--- clang/test/SemaCXX/lambda-pack-expansion.cpp | 27 ++++++++++++++++++++ 4 files changed, 33 insertions(+), 4 deletions(-) diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 3c2e0282d1c72..2f4158ac36ac2 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -170,6 +170,7 @@ Bug Fixes to C++ Support - Fixed a failed assertion when checking invalid delete operator declaration. (#GH96191) - Fix a crash when checking destructor reference with an invalid initializer. (#GH97230) - Clang now correctly parses potentially declarative nested-name-specifiers in pointer-to-member declarators. +- Fix init-capture packs having a size of one before being instantiated. (#GH63677) Bug Fixes to AST Handling ^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/clang/lib/Sema/SemaTemplateInstantiate.cpp b/clang/lib/Sema/SemaTemplateInstantiate.cpp index 8995d461362d7..de470739ab78e 100644 --- a/clang/lib/Sema/SemaTemplateInstantiate.cpp +++ b/clang/lib/Sema/SemaTemplateInstantiate.cpp @@ -1447,7 +1447,8 @@ namespace { } void transformedLocalDecl(Decl *Old, ArrayRef<Decl *> NewDecls) { - if (Old->isParameterPack()) { + if (Old->isParameterPack() && + (NewDecls.size() != 1 || !NewDecls.front()->isParameterPack())) { SemaRef.CurrentInstantiationScope->MakeInstantiatedLocalArgPack(Old); for (auto *New : NewDecls) SemaRef.CurrentInstantiationScope->InstantiatedLocalPackArg( diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 8d3e1edf7a45d..540e1e0cb8df0 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -14340,14 +14340,14 @@ TreeTransform<Derived>::TransformLambdaExpr(LambdaExpr *E) { OldVD->getInit()->getSourceRange(), Unexpanded, Expand, RetainExpansion, NumExpansions)) return ExprError(); + assert(!RetainExpansion && "Should not need to retain expansion after a " + "capture since it cannot be extended"); if (Expand) { for (unsigned I = 0; I != *NumExpansions; ++I) { Sema::ArgumentPackSubstitutionIndexRAII SubstIndex(getSema(), I); SubstInitCapture(SourceLocation(), std::nullopt); } - } - if (!Expand || RetainExpansion) { - ForgetPartiallySubstitutedPackRAII Forget(getDerived()); + } else { SubstInitCapture(ExpansionTL.getEllipsisLoc(), NumExpansions); Result.EllipsisLoc = ExpansionTL.getEllipsisLoc(); } diff --git a/clang/test/SemaCXX/lambda-pack-expansion.cpp b/clang/test/SemaCXX/lambda-pack-expansion.cpp index 221d1d01a06ae..77b2e244753a9 100644 --- a/clang/test/SemaCXX/lambda-pack-expansion.cpp +++ b/clang/test/SemaCXX/lambda-pack-expansion.cpp @@ -41,3 +41,30 @@ int h(Ts... ts) { } } + +namespace GH63677 { + +template<typename> +void f() { + []<typename... Ts>() -> void { + [...us = Ts{}]{ + (Ts(us), ...); + }; + }.template operator()<int, int>(); +} + +template void f<int>(); + +template <class> +inline constexpr auto fun = + []<class... Ts>(Ts... ts) { + return [... us = (Ts&&) ts]<class Fun>(Fun&& fn) mutable { + return static_cast<Fun&&>(fn)(static_cast<Ts&&>(us)...); + }; + }; + +void f() { + [[maybe_unused]] auto s = fun<int>(1, 2, 3, 4); +} + +} _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits