summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRichard Smith <richard-llvm@metafoo.co.uk>2019-09-27 05:36:16 +0000
committerRichard Smith <richard-llvm@metafoo.co.uk>2019-09-27 05:36:16 +0000
commit49494733533dd3f0be7d0ae216b267e71ee946b4 (patch)
treef230139ea7a8977f3cd617dca37ccda062504067
parent3fcdd25ad5566114ac3322dcbf71d3c38bfec1ed (diff)
downloadbcm5719-llvm-49494733533dd3f0be7d0ae216b267e71ee946b4.tar.gz
bcm5719-llvm-49494733533dd3f0be7d0ae216b267e71ee946b4.zip
Fix use-after-free found in Clang's testsuite.
We need to discard all remaining cleanups if an earlier cleanup failed, otherwise we may try to rerun the remaining cleanups later, potentially after the scope containing the object is destroyed. (This can happen when checking a potential constant expression.) llvm-svn: 373042
-rw-r--r--clang/lib/AST/ExprConstant.cpp9
1 files changed, 6 insertions, 3 deletions
diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp
index a2a6168ddbf..12dc054b81e 100644
--- a/clang/lib/AST/ExprConstant.cpp
+++ b/clang/lib/AST/ExprConstant.cpp
@@ -1239,11 +1239,14 @@ namespace {
// Run all cleanups for a block scope, and non-lifetime-extended cleanups
// for a full-expression scope.
+ bool Success = true;
for (unsigned I = Info.CleanupStack.size(); I > OldStackSize; --I) {
if (!(IsFullExpression &&
Info.CleanupStack[I - 1].isLifetimeExtended())) {
- if (!Info.CleanupStack[I - 1].endLifetime(Info, RunDestructors))
- return false;
+ if (!Info.CleanupStack[I - 1].endLifetime(Info, RunDestructors)) {
+ Success = false;
+ break;
+ }
}
}
@@ -1254,7 +1257,7 @@ namespace {
std::remove_if(NewEnd, Info.CleanupStack.end(),
[](Cleanup &C) { return !C.isLifetimeExtended(); });
Info.CleanupStack.erase(NewEnd, Info.CleanupStack.end());
- return true;
+ return Success;
}
};
typedef ScopeRAII<false> BlockScopeRAII;
OpenPOWER on IntegriCloud