diff options
author | David Majnemer <david.majnemer@gmail.com> | 2015-01-01 09:49:44 +0000 |
---|---|---|
committer | David Majnemer <david.majnemer@gmail.com> | 2015-01-01 09:49:44 +0000 |
commit | 602cfe7d62578359e4ba8b29839712dce67fe7a4 (patch) | |
tree | 2b36887c897c942e0f253f0b265a0f87bb37b68b /clang/lib/CodeGen/CGExpr.cpp | |
parent | 74ec80206597ce4b37ebfdb411a32178a0401d7c (diff) | |
download | bcm5719-llvm-602cfe7d62578359e4ba8b29839712dce67fe7a4.tar.gz bcm5719-llvm-602cfe7d62578359e4ba8b29839712dce67fe7a4.zip |
CodeGen: Don't crash when a lambda uses a local constexpr variable
The DeclRefExpr might be for a variable initialized by a constant
expression which hasn't been ODR used.
Emit the initializer for the variable instead of trying to capture the
variable itself.
This fixes PR22071.
llvm-svn: 225060
Diffstat (limited to 'clang/lib/CodeGen/CGExpr.cpp')
-rw-r--r-- | clang/lib/CodeGen/CGExpr.cpp | 32 |
1 files changed, 16 insertions, 16 deletions
diff --git a/clang/lib/CodeGen/CGExpr.cpp b/clang/lib/CodeGen/CGExpr.cpp index 16b624a9c31..8c04f138b8d 100644 --- a/clang/lib/CodeGen/CGExpr.cpp +++ b/clang/lib/CodeGen/CGExpr.cpp @@ -1902,22 +1902,6 @@ LValue CodeGenFunction::EmitDeclRefLValue(const DeclRefExpr *E) { QualType T = E->getType(); if (const auto *VD = dyn_cast<VarDecl>(ND)) { - // Check for captured variables. - if (E->refersToCapturedVariable()) { - if (auto *FD = LambdaCaptureFields.lookup(VD)) - return EmitCapturedFieldLValue(*this, FD, CXXABIThisValue); - else if (CapturedStmtInfo) { - if (auto *V = LocalDeclMap.lookup(VD)) - return MakeAddrLValue(V, T, Alignment); - else - return EmitCapturedFieldLValue(*this, CapturedStmtInfo->lookup(VD), - CapturedStmtInfo->getContextValue()); - } - assert(isa<BlockDecl>(CurCodeDecl)); - return MakeAddrLValue(GetAddrOfBlockDecl(VD, VD->hasAttr<BlocksAttr>()), - T, Alignment); - } - // Global Named registers access via intrinsics only if (VD->getStorageClass() == SC_Register && VD->hasAttr<AsmLabelAttr>() && !VD->isLocalVarDecl()) @@ -1935,6 +1919,22 @@ LValue CodeGenFunction::EmitDeclRefLValue(const DeclRefExpr *E) { // FIXME: Eventually we will want to emit vector element references. return MakeAddrLValue(Val, T, Alignment); } + + // Check for captured variables. + if (E->refersToCapturedVariable()) { + if (auto *FD = LambdaCaptureFields.lookup(VD)) + return EmitCapturedFieldLValue(*this, FD, CXXABIThisValue); + else if (CapturedStmtInfo) { + if (auto *V = LocalDeclMap.lookup(VD)) + return MakeAddrLValue(V, T, Alignment); + else + return EmitCapturedFieldLValue(*this, CapturedStmtInfo->lookup(VD), + CapturedStmtInfo->getContextValue()); + } + assert(isa<BlockDecl>(CurCodeDecl)); + return MakeAddrLValue(GetAddrOfBlockDecl(VD, VD->hasAttr<BlocksAttr>()), + T, Alignment); + } } // FIXME: We should be able to assert this for FunctionDecls as well! |