[llvm-branch-commits] [cfe-branch] r286966 - Merging r286584:
Alexey Bataev via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Tue Nov 15 06:23:10 PST 2016
Author: abataev
Date: Tue Nov 15 08:23:10 2016
New Revision: 286966
URL: http://llvm.org/viewvc/llvm-project?rev=286966&view=rev
Log:
Merging r286584:
------------------------------------------------------------------------
r286584 | abataev | 2016-11-11 12:36:20 +0000 (Fri, 11 Nov 2016) | 31 lines
Fix for PR28523: unexpected compilation error.
Clang emits error message for the following code:
```
template <class F> void parallel_loop(F &&f) { f(0); }
int main() {
int x;
parallel_loop([&](auto y) {
{
x = y;
};
});
}
```
$ clang++ --std=gnu++14 clang_test.cc -o clang_test
clang_test.cc:9:7: error: reference to local variable 'x' declared in enclosing function 'main'
x = y;
^
clang_test.cc:2:48: note: in instantiation of function template specialization 'main()::(anonymous class)::operator()<int>' requested here
template <class F> void parallel_loop(F &&f) { f(0); }
^
clang_test.cc:6:3: note: in instantiation of function template specialization 'parallel_loop<(lambda at clang_test.cc:6:17)>' requested here parallel_loop([&](auto y) {
^
clang_test.cc:5:7: note: 'x' declared here
int x;
^
1 error generated.
Patch fixes this issue.
------------------------------------------------------------------------
Added:
cfe/branches/release_39/test/CodeGenCXX/PR28523.cpp
- copied unchanged from r286584, cfe/trunk/test/CodeGenCXX/PR28523.cpp
Modified:
cfe/branches/release_39/ (props changed)
cfe/branches/release_39/include/clang/Sema/Sema.h
cfe/branches/release_39/lib/Sema/Sema.cpp
cfe/branches/release_39/lib/Sema/SemaExpr.cpp
cfe/branches/release_39/lib/Sema/SemaExprCXX.cpp
cfe/branches/release_39/lib/Sema/SemaLambda.cpp
Propchange: cfe/branches/release_39/
------------------------------------------------------------------------------
--- svn:mergeinfo (original)
+++ svn:mergeinfo Tue Nov 15 08:23:10 2016
@@ -1,4 +1,4 @@
/cfe/branches/type-system-rewrite:134693-134817
-/cfe/trunk:275880,275967,276102,276350,276361,276473,276653,276716,276887,276891,276900,276979,276983,277095,277138,277141,277221,277307,277522,277743,277783,277796-277797,277852,277866,277889,277900,278139,278156,278234-278235,278393,278395,278763,278786,278988,284110,286103,286106,286129
+/cfe/trunk:275880,275967,276102,276350,276361,276473,276653,276716,276887,276891,276900,276979,276983,277095,277138,277141,277221,277307,277522,277743,277783,277796-277797,277852,277866,277889,277900,278139,278156,278234-278235,278393,278395,278763,278786,278988,284110,286103,286106,286129,286584
/cfe/trunk/test:170344
/cfe/trunk/test/SemaTemplate:126920
Modified: cfe/branches/release_39/include/clang/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_39/include/clang/Sema/Sema.h?rev=286966&r1=286965&r2=286966&view=diff
==============================================================================
--- cfe/branches/release_39/include/clang/Sema/Sema.h (original)
+++ cfe/branches/release_39/include/clang/Sema/Sema.h Tue Nov 15 08:23:10 2016
@@ -1218,8 +1218,10 @@ public:
/// \brief Retrieve the current block, if any.
sema::BlockScopeInfo *getCurBlock();
- /// \brief Retrieve the current lambda scope info, if any.
- sema::LambdaScopeInfo *getCurLambda();
+ /// Retrieve the current lambda scope info, if any.
+ /// \param IgnoreCapturedRegions true if should find the top-most lambda scope
+ /// info ignoring all inner captured regions scope infos.
+ sema::LambdaScopeInfo *getCurLambda(bool IgnoreCapturedRegions = false);
/// \brief Retrieve the current generic lambda info, if any.
sema::LambdaScopeInfo *getCurGenericLambda();
Modified: cfe/branches/release_39/lib/Sema/Sema.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_39/lib/Sema/Sema.cpp?rev=286966&r1=286965&r2=286966&view=diff
==============================================================================
--- cfe/branches/release_39/lib/Sema/Sema.cpp (original)
+++ cfe/branches/release_39/lib/Sema/Sema.cpp Tue Nov 15 08:23:10 2016
@@ -1197,11 +1197,19 @@ BlockScopeInfo *Sema::getCurBlock() {
return CurBSI;
}
-LambdaScopeInfo *Sema::getCurLambda() {
+LambdaScopeInfo *Sema::getCurLambda(bool IgnoreCapturedRegions) {
if (FunctionScopes.empty())
return nullptr;
- auto CurLSI = dyn_cast<LambdaScopeInfo>(FunctionScopes.back());
+ auto I = FunctionScopes.rbegin();
+ if (IgnoreCapturedRegions) {
+ auto E = FunctionScopes.rend();
+ while (I != E && isa<CapturedRegionScopeInfo>(*I))
+ ++I;
+ if (I == E)
+ return nullptr;
+ }
+ auto *CurLSI = dyn_cast<LambdaScopeInfo>(*I);
if (CurLSI && CurLSI->Lambda &&
!CurLSI->Lambda->Encloses(CurContext)) {
// We have switched contexts due to template instantiation.
Modified: cfe/branches/release_39/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_39/lib/Sema/SemaExpr.cpp?rev=286966&r1=286965&r2=286966&view=diff
==============================================================================
--- cfe/branches/release_39/lib/Sema/SemaExpr.cpp (original)
+++ cfe/branches/release_39/lib/Sema/SemaExpr.cpp Tue Nov 15 08:23:10 2016
@@ -13885,7 +13885,8 @@ static void DoMarkVarDeclReferenced(Sema
(SemaRef.CurContext != Var->getDeclContext() &&
Var->getDeclContext()->isFunctionOrMethod() && Var->hasLocalStorage());
if (RefersToEnclosingScope) {
- if (LambdaScopeInfo *const LSI = SemaRef.getCurLambda()) {
+ if (LambdaScopeInfo *const LSI =
+ SemaRef.getCurLambda(/*IgnoreCapturedRegions=*/true)) {
// If a variable could potentially be odr-used, defer marking it so
// until we finish analyzing the full expression for any
// lvalue-to-rvalue
Modified: cfe/branches/release_39/lib/Sema/SemaExprCXX.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_39/lib/Sema/SemaExprCXX.cpp?rev=286966&r1=286965&r2=286966&view=diff
==============================================================================
--- cfe/branches/release_39/lib/Sema/SemaExprCXX.cpp (original)
+++ cfe/branches/release_39/lib/Sema/SemaExprCXX.cpp Tue Nov 15 08:23:10 2016
@@ -6582,10 +6582,16 @@ static inline bool VariableCanNeverBeACo
static void CheckIfAnyEnclosingLambdasMustCaptureAnyPotentialCaptures(
Expr *const FE, LambdaScopeInfo *const CurrentLSI, Sema &S) {
- assert(!S.isUnevaluatedContext());
- assert(S.CurContext->isDependentContext());
- assert(CurrentLSI->CallOperator == S.CurContext &&
+ assert(!S.isUnevaluatedContext());
+ assert(S.CurContext->isDependentContext());
+#ifndef NDEBUG
+ DeclContext *DC = S.CurContext;
+ while (DC && isa<CapturedDecl>(DC))
+ DC = DC->getParent();
+ assert(
+ CurrentLSI->CallOperator == DC &&
"The current call operator must be synchronized with Sema's CurContext");
+#endif // NDEBUG
const bool IsFullExprInstantiationDependent = FE->isInstantiationDependent();
@@ -7051,7 +7057,8 @@ ExprResult Sema::ActOnFinishFullExpr(Exp
// and then the full-expression +n + ({ 0; }); ends, but it's too late
// for us to see that we need to capture n after all.
- LambdaScopeInfo *const CurrentLSI = getCurLambda();
+ LambdaScopeInfo *const CurrentLSI =
+ getCurLambda(/*IgnoreCapturedRegions=*/true);
// FIXME: PR 17877 showed that getCurLambda() can return a valid pointer
// even if CurContext is not a lambda call operator. Refer to that Bug Report
// for an example of the code that might cause this asynchrony.
@@ -7066,7 +7073,10 @@ ExprResult Sema::ActOnFinishFullExpr(Exp
// constructor/destructor.
// - Teach the handful of places that iterate over FunctionScopes to
// stop at the outermost enclosing lexical scope."
- const bool IsInLambdaDeclContext = isLambdaCallOperator(CurContext);
+ DeclContext *DC = CurContext;
+ while (DC && isa<CapturedDecl>(DC))
+ DC = DC->getParent();
+ const bool IsInLambdaDeclContext = isLambdaCallOperator(DC);
if (IsInLambdaDeclContext && CurrentLSI &&
CurrentLSI->hasPotentialCaptures() && !FullExpr.isInvalid())
CheckIfAnyEnclosingLambdasMustCaptureAnyPotentialCaptures(FE, CurrentLSI,
Modified: cfe/branches/release_39/lib/Sema/SemaLambda.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/branches/release_39/lib/Sema/SemaLambda.cpp?rev=286966&r1=286965&r2=286966&view=diff
==============================================================================
--- cfe/branches/release_39/lib/Sema/SemaLambda.cpp (original)
+++ cfe/branches/release_39/lib/Sema/SemaLambda.cpp Tue Nov 15 08:23:10 2016
@@ -66,17 +66,20 @@ getStackIndexOfNearestEnclosingCaptureRe
// Label failure to capture.
const Optional<unsigned> NoLambdaIsCaptureReady;
+ // Ignore all inner captured regions.
+ unsigned CurScopeIndex = FunctionScopes.size() - 1;
+ while (CurScopeIndex > 0 && isa<clang::sema::CapturedRegionScopeInfo>(
+ FunctionScopes[CurScopeIndex]))
+ --CurScopeIndex;
assert(
- isa<clang::sema::LambdaScopeInfo>(
- FunctionScopes[FunctionScopes.size() - 1]) &&
+ isa<clang::sema::LambdaScopeInfo>(FunctionScopes[CurScopeIndex]) &&
"The function on the top of sema's function-info stack must be a lambda");
-
+
// If VarToCapture is null, we are attempting to capture 'this'.
const bool IsCapturingThis = !VarToCapture;
const bool IsCapturingVariable = !IsCapturingThis;
// Start with the current lambda at the top of the stack (highest index).
- unsigned CurScopeIndex = FunctionScopes.size() - 1;
DeclContext *EnclosingDC =
cast<sema::LambdaScopeInfo>(FunctionScopes[CurScopeIndex])->CallOperator;
More information about the llvm-branch-commits
mailing list