-
Notifications
You must be signed in to change notification settings - Fork 12.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Clang] Fix the order of addInstantiatedParameters in LambdaScopeForCallOperatorInstantiationRAII #97215
Conversation
@llvm/pr-subscribers-clang Author: Yupei Liu (LYP951018) ChangesCurrently, This PR corrects this behavior by calling repro code: https://godbolt.org/z/KbsxWesW6 namespace dependent_param_concept {
template <typename... Ts> void sink(Ts...) {}
void dependent_param() {
auto L = [](auto... x) {
return [](decltype(x)... y) { // `y` depends on `x`
return [](int z)
requires requires { sink(y..., z); }
{};
};
};
L(0, 1)(1, 2)(1);
}
} // namespace dependent_param_concept Full diff: https://github.com/llvm/llvm-project/pull/97215.diff 2 Files Affected:
diff --git a/clang/lib/Sema/SemaLambda.cpp b/clang/lib/Sema/SemaLambda.cpp
index e9476a0c93c5d..b6344f53861f4 100644
--- a/clang/lib/Sema/SemaLambda.cpp
+++ b/clang/lib/Sema/SemaLambda.cpp
@@ -2379,23 +2379,32 @@ Sema::LambdaScopeForCallOperatorInstantiationRAII::
SemaRef.RebuildLambdaScopeInfo(cast<CXXMethodDecl>(FD));
- FunctionDecl *Pattern = getPatternFunctionDecl(FD);
- if (Pattern) {
- SemaRef.addInstantiatedCapturesToScope(FD, Pattern, Scope, MLTAL);
+ FunctionDecl *FDPattern = getPatternFunctionDecl(FD);
+ if (!FDPattern)
+ return;
- FunctionDecl *ParentFD = FD;
- while (ShouldAddDeclsFromParentScope) {
+ SemaRef.addInstantiatedCapturesToScope(FD, FDPattern, Scope, MLTAL);
- ParentFD =
- dyn_cast<FunctionDecl>(getLambdaAwareParentOfDeclContext(ParentFD));
- Pattern =
- dyn_cast<FunctionDecl>(getLambdaAwareParentOfDeclContext(Pattern));
+ if (!ShouldAddDeclsFromParentScope)
+ return;
- if (!FD || !Pattern)
- break;
+ llvm::SmallVector<std::pair<FunctionDecl *, FunctionDecl *>, 4>
+ ParentInstantiations;
+ std::pair<FunctionDecl *, FunctionDecl *> Current = {FDPattern, FD};
+ while (true) {
+ Current.first = dyn_cast<FunctionDecl>(
+ getLambdaAwareParentOfDeclContext(Current.first));
+ Current.second = dyn_cast<FunctionDecl>(
+ getLambdaAwareParentOfDeclContext(Current.second));
- SemaRef.addInstantiatedParametersToScope(ParentFD, Pattern, Scope, MLTAL);
- SemaRef.addInstantiatedLocalVarsToScope(ParentFD, Pattern, Scope);
- }
+ if (!Current.first || !Current.second)
+ break;
+
+ ParentInstantiations.push_back(Current);
+ }
+
+ for (const auto &[Pattern, Inst] : llvm::reverse(ParentInstantiations)) {
+ SemaRef.addInstantiatedParametersToScope(Inst, Pattern, Scope, MLTAL);
+ SemaRef.addInstantiatedLocalVarsToScope(Inst, Pattern, Scope);
}
}
diff --git a/clang/test/SemaTemplate/concepts-lambda.cpp b/clang/test/SemaTemplate/concepts-lambda.cpp
index 280be71284f97..252ef08549a48 100644
--- a/clang/test/SemaTemplate/concepts-lambda.cpp
+++ b/clang/test/SemaTemplate/concepts-lambda.cpp
@@ -237,3 +237,17 @@ concept D = []<C T = int>() { return true; }();
D auto x = 0;
} // namespace GH93821
+
+namespace dependent_param_concept {
+template <typename... Ts> void sink(Ts...) {}
+void dependent_param() {
+ auto L = [](auto... x) {
+ return [](decltype(x)... y) {
+ return [](int z)
+ requires requires { sink(y..., z); }
+ {};
+ };
+ };
+ L(0, 1)(1, 2)(1);
+}
+} // namespace dependent_param_concept
|
…torInstantiationRAII.
015088d
to
a997ae7
Compare
Sorry for disturbing... I'm trying to get the CI working. I can't figure out why buildkite/github-pull-requests failed... |
4174914
to
a997ae7
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks! I think the approach makes sense. Just some nits from me
@cor3ntin do you have any other comments? I think you can do the last approval. :)
FunctionDecl *Pattern = getPatternFunctionDecl(FD); | ||
if (Pattern) { | ||
SemaRef.addInstantiatedCapturesToScope(FD, Pattern, Scope, MLTAL); | ||
FunctionDecl *FDPattern = getPatternFunctionDecl(FD); | ||
if (!FDPattern) | ||
return; | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: Can you revert unrelated changes?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would prefer to keep the current change. Firstly, this change is minimal and won’t significantly impact the review workload for this PR. Secondly, it reduces one level of indentation, which slightly improves readability. ;)
Oh, I forgot it: this also needs a release note. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
Thanks for the review ;) |
…allOperatorInstantiationRAII (llvm#97215) Currently, `addInstantiatedParameters` is called from the innermost lambda outward. However, when the function parameters of an inner lambda depend on the function parameters of an outer lambda, it can lead to a crash due to the inability to find a mapping for the instantiated decl. This PR corrects this behavior by calling `addInstantiatedParameters` from the outside in. repro code: https://godbolt.org/z/KbsxWesW6 ```cpp namespace dependent_param_concept { template <typename... Ts> void sink(Ts...) {} void dependent_param() { auto L = [](auto... x) { return [](decltype(x)... y) { // `y` depends on `x` return [](int z) requires requires { sink(y..., z); } {}; }; }; L(0, 1)(1, 2)(1); } } // namespace dependent_param_concept ``` This PR is a prerequisite for implmenting llvm#61426
Currently,
addInstantiatedParameters
is called from the innermost lambda outward. However, when the function parameters of an inner lambda depend on the function parameters of an outer lambda, it can lead to a crash due to the inability to find a mapping for the instantiated decl.This PR corrects this behavior by calling
addInstantiatedParameters
from the outside in.repro code: https://godbolt.org/z/KbsxWesW6
This PR is a prerequisite for implmenting #61426