[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: The internal code was fixed. Thanks everyone for helping to figure this out! https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: It turns out debug build of clang before this patch generated an assertion on the original code as well: ``` assert.h assertion failed at llvm-project/clang/lib/AST/ExprConstant.cpp:15739 in bool clang::Expr::EvaluateAsConstantExpr(EvalResult &, const ASTContext &, ConstantExprKind) const: !isValueDependent() && "Expression evaluator can't be called on a dependent expression." ... @ 0x5643bcdac9e4 __assert_fail @ 0x5643b9734df7 clang::Expr::EvaluateAsConstantExpr() @ 0x5643b89f7fea calculateConstraintSatisfaction<>() @ 0x5643b89f1bcf CheckConstraintSatisfaction() @ 0x5643b89f193e clang::Sema::CheckConstraintSatisfaction() @ 0x5643b90d9f23 clang::Sema::CheckConceptTemplateId() @ 0x5643b9259656 clang::TreeTransform<>::TransformConceptSpecializationExpr() @ 0x5643b925ce00 clang::TreeTransform<>::TransformCXXFoldExpr() @ 0x5643b924b6e0 clang::Sema::SubstConstraintExpr() @ 0x5643b89f9097 calculateConstraintSatisfaction()::$_0::operator()() @ 0x5643b89f7f50 calculateConstraintSatisfaction<>() @ 0x5643b89f1bcf CheckConstraintSatisfaction() @ 0x5643b89f193e clang::Sema::CheckConstraintSatisfaction() @ 0x5643b9237c6d FinishTemplateArgumentDeduction<>() @ 0x5643b9236cd2 llvm::function_ref<>::callback_fn<>() @ 0x5643b888fa2f clang::Sema::runWithSufficientStackSpace() @ 0x5643b91c2e17 clang::Sema::DeduceTemplateArguments() @ 0x5643b9248e19 clang::Sema::InstantiateClassTemplateSpecialization() @ 0x5643b9334e73 llvm::function_ref<>::callback_fn<>() @ 0x5643b888fa2f clang::Sema::runWithSufficientStackSpace() @ 0x5643b931fdc4 clang::Sema::RequireCompleteTypeImpl() @ 0x5643b931f535 clang::Sema::RequireCompleteType() @ 0x5643b891bad7 clang::Sema::RequireCompleteDeclContext() @ 0x5643b90eda4d clang::Sema::CheckTypenameType() @ 0x5643b926edd2 clang::TreeTransform<>::TransformDependentNameType() @ 0x5643b9243d1c clang::TreeTransform<>::TransformType() @ 0x5643b92436ff clang::TreeTransform<>::TransformType() @ 0x5643b9244293 clang::Sema::SubstType() @ 0x5643b90d0e8a clang::Sema::CheckTemplateIdType() @ 0x5643b90d5015 clang::Sema::ActOnTemplateIdType() @ 0x5643b8674084 clang::Parser::AnnotateTemplateIdTokenAsType() @ 0x5643b86536cf clang::Parser::ParseDeclarationSpecifiers() @ 0x5643b864fffa clang::Parser::ParseSpecifierQualifierList() @ 0x5643b863da31 clang::Parser::ParseTypeName() @ 0x5643b86262bd clang::Parser::ParseAliasDeclarationAfterDeclarator() @ 0x5643b8624ea0 clang::Parser::ParseUsingDeclaration() @ 0x5643b8623e70 clang::Parser::ParseUsingDirectiveOrDeclaration() @ 0x5643b864b6ef clang::Parser::ParseDeclaration() @ 0x5643b868a9a4 clang::Parser::ParseStatementOrDeclarationAfterAttributes() @ 0x5643b8689d78 clang::Parser::ParseStatementOrDeclaration() @ 0x5643b8693bc0 clang::Parser::ParseCompoundStatementBody() @ 0x5643b8694bce clang::Parser::ParseFunctionStatementBody() @ 0x5643b85da8ad clang::Parser::ParseFunctionDefinition() @ 0x5643b864df89 clang::Parser::ParseDeclGroup() @ 0x5643b85d8ec9 clang::Parser::ParseDeclOrFunctionDefInternal() @ 0x5643b85d868e clang::Parser::ParseDeclarationOrFunctionDefinition() @ 0x5643b85d7434 clang::Parser::ParseExternalDeclaration() @ 0x5643b8622693 clang::Parser::ParseInnerNamespace() @ 0x5643b8621893 clang::Parser::ParseNamespace() @ 0x5643b864b7de clang::Parser::ParseDeclaration() @ 0x5643b85d6fb6 clang::Parser::ParseExternalDeclaration() @ 0x5643b85d516b clang::Parser::ParseTopLevelDecl() @ 0x5643b85ceebe clang::ParseAST() @ 0x5643b831a4c3 clang::FrontendAction::Execute() @ 0x5643b8294efd clang::CompilerInstance::ExecuteAction() @ 0x5643b717f84e clang::ExecuteCompilerInvocation() @ 0x5643b71737c6 cc1_main() @ 0x5643b7171066 ExecuteCC1Tool() @ 0x5643b843fe3e llvm::function_ref<>::callback_fn<>() @ 0x5643bcc44415 llvm::CrashRecoveryContext::RunSafely() @ 0x5643b843f5bb clang::driver::CC1Command::Execute() @ 0x5643b8400494 clang::driver::Compilation::ExecuteCommand() @ 0x5643b84007af clang::driver::Compilation::ExecuteJobs() @ 0x5643b841ea80 clang::driver::Driver::ExecuteCompilation() @ 0x5643b717061b clang_main() @ 0x5643b716d834 main ``` I'll try to figure out what's wrong with the original code. https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: I guess the reduction could have dropped some important parts of this. Let me try the original code with assertions-enabled clang build... https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
zyn0217 wrote: > I have a reduced test case, which is accepted by clang 18, but fails with > this patch: https://gcc.godbolt.org/z/zMbKvsf7K > A bit more compact one: https://gcc.godbolt.org/z/4rzYPKaze Your case is rejected by all mainstream compilers as of now: https://gcc.godbolt.org/z/nrMf3zvfY Again, it was an accept-invalid before because of the constant evaluation on dependent expressions, which **is** an assertion failure if you compile it with debug mode. https://gcc.godbolt.org/z/eascd7j1G To clarify why the requirement should be evaluated to false: > The enclosing _requires-expression_ will evaluate to false if substitution of > template arguments into the expression fails. https://eel.is/c++draft/expr.prim.req#simple-1.sentence-2 https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
dwblaikie wrote: FWIW, @jyknight's example fails to compile with GCC - succeeds with clang 18 release but assert-fails with clang 18 +Asserts build. (not sure about the original/full internal reproduction - we have a way to run compile with assertions enaled, but I'm not sure I'm holding it right... ) https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
jyknight wrote: Can reduce further to: ``` template concept h = requires(T i) { [] {}(i); }; template struct k; template struct k { struct n; }; using o = k::n; ``` But, is `requires(T i) { [] {}(i); };` actually valid? I think that _should_ fail the requirement, since you cannot call that lambda with an argument? Maybe that's just an artifact of the reduction? https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: A bit more compact one: https://gcc.godbolt.org/z/4rzYPKaze https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: I have a reduced test case, which is accepted by clang 18, but fails with this patch: https://gcc.godbolt.org/z/zMbKvsf7K https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
zyn0217 wrote: > I'm reducing the test case. In the meantime, should this be reverted? I think this depends on the case. Note the issues addressed by this patch may not only cause some crashes in debug build, but probably lead to incorrect constraint evaluation in release build, which means there's possibility that your case was an accept-invalid before. (Sorry for making confusion earlier; my office hour just begins and I'm sitting here for your case. If there is really something wrong caused by this PR, I'll revert it in time. Don't worry.) https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: I'm reducing the test case. In the meantime, should this be reverted? https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
zyn0217 wrote: > Was this sort of a behavior change expected? I don't think so; a reproducer would be really appreciated. https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
alexfh wrote: Hi folks, we've started seeing "implicit instantiation of undefined template" compilation errors after this commit. In all cases code used to compile fine before this commit. I haven't spotted any particular issues in the code (though the examples are looked at are rather convoluted, thus, I'm not 100% sure). I'll try to prepare a self-sufficient test case. Was this sort of a behavior change expected? https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 closed https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 updated https://github.com/llvm/llvm-project/pull/83997 >From 69414d7352b170f6fcff22c6f5dfa91cc76b0b58 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Tue, 5 Mar 2024 19:56:59 +0800 Subject: [PATCH 1/3] gh56556 --- clang/lib/Sema/TreeTransform.h | 6 -- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 7389a48fe56fcc..c96ffcb97a7591 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13649,10 +13649,12 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || getSema().isConstantEvaluatedContext()) && - (getSema().CurContext->isFileContext() || - !getSema().CurContext->getParent()->isDependentContext())) + (DC->isFileContext() || !DC->getParent()->isDependentContext())) DependencyKind = CXXRecordDecl::LDK_NeverDependent; CXXRecordDecl *OldClass = E->getLambdaClass(); >From b905083e5d5186ad08ac3d553be3e8f47dabc1b6 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Wed, 6 Mar 2024 13:46:43 +0800 Subject: [PATCH 2/3] Tests & release notes --- clang/docs/ReleaseNotes.rst | 2 + clang/lib/Sema/TreeTransform.h | 17 +++ clang/test/SemaTemplate/concepts-lambda.cpp | 52 + 3 files changed, 71 insertions(+) diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index d4e6bcf661da1a..141099fb68a200 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -302,6 +302,8 @@ Bug Fixes to C++ Support our attention by an attempt to fix in (#GH77703). Fixes (#GH83385). - Fix evaluation of some immediate calls in default arguments. Fixes (#GH80630) +- Fixed an issue where the ``RequiresExprBody`` was involved in the lambda dependency + calculation. (#GH56556), (#GH82849). Bug Fixes to AST Handling ^ diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index c96ffcb97a7591..84348e13567e71 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13650,6 +13650,23 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || diff --git a/clang/test/SemaTemplate/concepts-lambda.cpp b/clang/test/SemaTemplate/concepts-lambda.cpp index 0b7580f91043c7..ef04cad4eef98b 100644 --- a/clang/test/SemaTemplate/concepts-lambda.cpp +++ b/clang/test/SemaTemplate/concepts-lambda.cpp @@ -90,6 +90,58 @@ struct Foo { static_assert(ConstructibleWithN); +namespace GH56556 { + +template +inline constexpr It declare (); + +template typename Template> +concept D = requires { + { [] (Template &) {}(declare()) }; +}; + +template +struct B {}; + +template +struct Adapter; + +template T> +struct Adapter {}; + +template struct Adapter>; + +} // namespace GH56556 + +namespace GH82849 { + +template +concept C = requires(T t) { + [](T) {}(t); +}; + +template +struct Widget; + +template +struct Widget { + static F create(F from) { +return from; + } +}; + +template +bool foo() { + return C; +} + +void bar() { + // https://github.com/llvm/llvm-project/issues/49570#issuecomment-1664966972 + Widget::create(0); +} + +} // namespace GH82849 + } // GH60642 reported an assert being hit, make sure we don't assert. >From 6b36f74b6aede38766674c99a803c86becacd01d Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Wed, 6 Mar 2024 18:56:53 +0800 Subject: [PATCH 3/3] Address Corentin's comments --- clang/lib/Sema/TreeTransform.h | 6 +++--- clang/test/SemaTemplate/concepts-lambda.cpp | 8 +++- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 84348e13567e71..409aee73d960eb 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/Tr
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/yuxuanchen1997 approved this pull request. Thank you so much! This looks good. https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/cor3ntin approved this pull request. LGTM https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
zyn0217 wrote: @cor3ntin Thanks! I have updated the test to reflect the nested `requires` cases. PTAL? https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
@@ -13649,10 +13649,29 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); zyn0217 wrote: Oops, this should be a `while` loop, I think https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 updated https://github.com/llvm/llvm-project/pull/83997 >From 69414d7352b170f6fcff22c6f5dfa91cc76b0b58 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Tue, 5 Mar 2024 19:56:59 +0800 Subject: [PATCH 1/3] gh56556 --- clang/lib/Sema/TreeTransform.h | 6 -- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 7389a48fe56fcc..c96ffcb97a7591 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13649,10 +13649,12 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || getSema().isConstantEvaluatedContext()) && - (getSema().CurContext->isFileContext() || - !getSema().CurContext->getParent()->isDependentContext())) + (DC->isFileContext() || !DC->getParent()->isDependentContext())) DependencyKind = CXXRecordDecl::LDK_NeverDependent; CXXRecordDecl *OldClass = E->getLambdaClass(); >From b905083e5d5186ad08ac3d553be3e8f47dabc1b6 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Wed, 6 Mar 2024 13:46:43 +0800 Subject: [PATCH 2/3] Tests & release notes --- clang/docs/ReleaseNotes.rst | 2 + clang/lib/Sema/TreeTransform.h | 17 +++ clang/test/SemaTemplate/concepts-lambda.cpp | 52 + 3 files changed, 71 insertions(+) diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index d4e6bcf661da1a..141099fb68a200 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -302,6 +302,8 @@ Bug Fixes to C++ Support our attention by an attempt to fix in (#GH77703). Fixes (#GH83385). - Fix evaluation of some immediate calls in default arguments. Fixes (#GH80630) +- Fixed an issue where the ``RequiresExprBody`` was involved in the lambda dependency + calculation. (#GH56556), (#GH82849). Bug Fixes to AST Handling ^ diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index c96ffcb97a7591..84348e13567e71 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13650,6 +13650,23 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || diff --git a/clang/test/SemaTemplate/concepts-lambda.cpp b/clang/test/SemaTemplate/concepts-lambda.cpp index 0b7580f91043c7..ef04cad4eef98b 100644 --- a/clang/test/SemaTemplate/concepts-lambda.cpp +++ b/clang/test/SemaTemplate/concepts-lambda.cpp @@ -90,6 +90,58 @@ struct Foo { static_assert(ConstructibleWithN); +namespace GH56556 { + +template +inline constexpr It declare (); + +template typename Template> +concept D = requires { + { [] (Template &) {}(declare()) }; +}; + +template +struct B {}; + +template +struct Adapter; + +template T> +struct Adapter {}; + +template struct Adapter>; + +} // namespace GH56556 + +namespace GH82849 { + +template +concept C = requires(T t) { + [](T) {}(t); +}; + +template +struct Widget; + +template +struct Widget { + static F create(F from) { +return from; + } +}; + +template +bool foo() { + return C; +} + +void bar() { + // https://github.com/llvm/llvm-project/issues/49570#issuecomment-1664966972 + Widget::create(0); +} + +} // namespace GH82849 + } // GH60642 reported an assert being hit, make sure we don't assert. >From 6b36f74b6aede38766674c99a803c86becacd01d Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Wed, 6 Mar 2024 18:56:53 +0800 Subject: [PATCH 3/3] Address Corentin's comments --- clang/lib/Sema/TreeTransform.h | 6 +++--- clang/test/SemaTemplate/concepts-lambda.cpp | 8 +++- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 84348e13567e71..409aee73d960eb 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/Tr
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
@@ -13649,10 +13649,29 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. cor3ntin wrote: ```suggestion // will be deemed as dependent even if there is are no dependent template // arguments. ``` https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
@@ -13649,10 +13649,29 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); cor3ntin wrote: Do we get into the same issue if there are multiple nested `requires`? https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
@@ -13649,10 +13649,29 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be cor3ntin wrote: ```suggestion // While we are substituting Widget, the parent of DC would be ``` https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 edited https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 edited https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
llvmbot wrote: @llvm/pr-subscribers-clang Author: Younan Zhang (zyn0217) Changes The dependency of a lambda inside of a `RequiresExprBodyDecl` was previously affected by its parent, e.g., `ClassTemplateSpecializationDecl`. This made the lambda always dependent regardless of the template arguments we had, which caused some crashes on the constraint evaluation later. This fixes https://github.com/llvm/llvm-project/issues/56556, https://github.com/llvm/llvm-project/issues/82849 and a case demonstrated by https://github.com/llvm/llvm-project/issues/49570#issuecomment-1664966972. --- Full diff: https://github.com/llvm/llvm-project/pull/83997.diff 3 Files Affected: - (modified) clang/docs/ReleaseNotes.rst (+2) - (modified) clang/lib/Sema/TreeTransform.h (+21-2) - (modified) clang/test/SemaTemplate/concepts-lambda.cpp (+52) ``diff diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 5e0352a7eaf6cd..9c64cd2b5f6a10 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -311,6 +311,8 @@ Bug Fixes to C++ Support Fixes (#GH80630) - Fix a crash when an explicit template argument list is used with a name for which lookup finds a non-template function and a dependent using declarator. +- Fixed an issue where the ``RequiresExprBody`` was involved in the lambda dependency + calculation. (#GH56556), (#GH82849). Bug Fixes to AST Handling ^ diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 7389a48fe56fcc..84348e13567e71 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13649,10 +13649,29 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || getSema().isConstantEvaluatedContext()) && - (getSema().CurContext->isFileContext() || - !getSema().CurContext->getParent()->isDependentContext())) + (DC->isFileContext() || !DC->getParent()->isDependentContext())) DependencyKind = CXXRecordDecl::LDK_NeverDependent; CXXRecordDecl *OldClass = E->getLambdaClass(); diff --git a/clang/test/SemaTemplate/concepts-lambda.cpp b/clang/test/SemaTemplate/concepts-lambda.cpp index 0b7580f91043c7..ef04cad4eef98b 100644 --- a/clang/test/SemaTemplate/concepts-lambda.cpp +++ b/clang/test/SemaTemplate/concepts-lambda.cpp @@ -90,6 +90,58 @@ struct Foo { static_assert(ConstructibleWithN); +namespace GH56556 { + +template +inline constexpr It declare (); + +template typename Template> +concept D = requires { + { [] (Template &) {}(declare()) }; +}; + +template +struct B {}; + +template +struct Adapter; + +template T> +struct Adapter {}; + +template struct Adapter>; + +} // namespace GH56556 + +namespace GH82849 { + +template +concept C = requires(T t) { + [](T) {}(t); +}; + +template +struct Widget; + +template +struct Widget { + static F create(F from) { +return from; + } +}; + +template +bool foo() { + return C; +} + +void bar() { + // https://github.com/llvm/llvm-project/issues/49570#issuecomment-1664966972 + Widget::create(0); +} + +} // namespace GH82849 + } // GH60642 reported an assert being hit, make sure we don't assert. `` https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 ready_for_review https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 updated https://github.com/llvm/llvm-project/pull/83997 >From 69414d7352b170f6fcff22c6f5dfa91cc76b0b58 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Tue, 5 Mar 2024 19:56:59 +0800 Subject: [PATCH 1/2] gh56556 --- clang/lib/Sema/TreeTransform.h | 6 -- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index 7389a48fe56fcc..c96ffcb97a7591 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13649,10 +13649,12 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { // use evaluation contexts to distinguish the function parameter case. CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; + DeclContext *DC = getSema().CurContext; + if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) +DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || getSema().isConstantEvaluatedContext()) && - (getSema().CurContext->isFileContext() || - !getSema().CurContext->getParent()->isDependentContext())) + (DC->isFileContext() || !DC->getParent()->isDependentContext())) DependencyKind = CXXRecordDecl::LDK_NeverDependent; CXXRecordDecl *OldClass = E->getLambdaClass(); >From b905083e5d5186ad08ac3d553be3e8f47dabc1b6 Mon Sep 17 00:00:00 2001 From: Younan Zhang Date: Wed, 6 Mar 2024 13:46:43 +0800 Subject: [PATCH 2/2] Tests & release notes --- clang/docs/ReleaseNotes.rst | 2 + clang/lib/Sema/TreeTransform.h | 17 +++ clang/test/SemaTemplate/concepts-lambda.cpp | 52 + 3 files changed, 71 insertions(+) diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index d4e6bcf661da1a..141099fb68a200 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -302,6 +302,8 @@ Bug Fixes to C++ Support our attention by an attempt to fix in (#GH77703). Fixes (#GH83385). - Fix evaluation of some immediate calls in default arguments. Fixes (#GH80630) +- Fixed an issue where the ``RequiresExprBody`` was involved in the lambda dependency + calculation. (#GH56556), (#GH82849). Bug Fixes to AST Handling ^ diff --git a/clang/lib/Sema/TreeTransform.h b/clang/lib/Sema/TreeTransform.h index c96ffcb97a7591..84348e13567e71 100644 --- a/clang/lib/Sema/TreeTransform.h +++ b/clang/lib/Sema/TreeTransform.h @@ -13650,6 +13650,23 @@ TreeTransform::TransformLambdaExpr(LambdaExpr *E) { CXXRecordDecl::LambdaDependencyKind DependencyKind = CXXRecordDecl::LDK_Unknown; DeclContext *DC = getSema().CurContext; + // A RequiresExprBodyDecl is not interesting for dependencies. + // For the following case, + // + // template + // concept C = requires { [] {}; }; + // + // template + // struct Widget; + // + // template + // struct Widget {}; + // + // While we are here in substitution for Widget, the parent of DC would be + // the template specialization itself. Thus, the lambda expression + // will be deemed as dependent even if we have non-dependent template + // arguments. + // (A ClassTemplateSpecializationDecl is always a dependent context.) if (DC->getDeclKind() == Decl::Kind::RequiresExprBody) DC = DC->getParent(); if ((getSema().isUnevaluatedContext() || diff --git a/clang/test/SemaTemplate/concepts-lambda.cpp b/clang/test/SemaTemplate/concepts-lambda.cpp index 0b7580f91043c7..ef04cad4eef98b 100644 --- a/clang/test/SemaTemplate/concepts-lambda.cpp +++ b/clang/test/SemaTemplate/concepts-lambda.cpp @@ -90,6 +90,58 @@ struct Foo { static_assert(ConstructibleWithN); +namespace GH56556 { + +template +inline constexpr It declare (); + +template typename Template> +concept D = requires { + { [] (Template &) {}(declare()) }; +}; + +template +struct B {}; + +template +struct Adapter; + +template T> +struct Adapter {}; + +template struct Adapter>; + +} // namespace GH56556 + +namespace GH82849 { + +template +concept C = requires(T t) { + [](T) {}(t); +}; + +template +struct Widget; + +template +struct Widget { + static F create(F from) { +return from; + } +}; + +template +bool foo() { + return C; +} + +void bar() { + // https://github.com/llvm/llvm-project/issues/49570#issuecomment-1664966972 + Widget::create(0); +} + +} // namespace GH82849 + } // GH60642 reported an assert being hit, make sure we don't assert. ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
[clang] [clang][Sema] Skip the RequiresExprBodyDecls for lambda dependencies (PR #83997)
https://github.com/zyn0217 edited https://github.com/llvm/llvm-project/pull/83997 ___ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits