diff options
author | Sanjoy Das <sanjoy@playingwithpointers.com> | 2016-06-08 17:48:42 +0000 |
---|---|---|
committer | Sanjoy Das <sanjoy@playingwithpointers.com> | 2016-06-08 17:48:42 +0000 |
commit | 8598412e24d7a8e2f31f41cbd11dde29e0c41090 (patch) | |
tree | da4bdfefb0ffa82d08c6324d461bc84537712043 /llvm/lib/Analysis/ScalarEvolution.cpp | |
parent | 9a65cd214d0caef30d0b353701e5a66bf59841e4 (diff) | |
download | llvm-8598412e24d7a8e2f31f41cbd11dde29e0c41090.zip llvm-8598412e24d7a8e2f31f41cbd11dde29e0c41090.tar.gz llvm-8598412e24d7a8e2f31f41cbd11dde29e0c41090.tar.bz2 |
[SCEV] Track no-abnormal-exits instead of no-throw calls
Absence of may-unwind calls is not enough to guarantee that a
UB-generating use of an add-rec poison in the loop latch will actually
cause UB. We also need to guard against calls that terminate the thread
or infinite loop themselves.
This partially addresses PR28012.
llvm-svn: 272181
Diffstat (limited to 'llvm/lib/Analysis/ScalarEvolution.cpp')
-rw-r--r-- | llvm/lib/Analysis/ScalarEvolution.cpp | 20 |
1 files changed, 10 insertions, 10 deletions
diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp index 111b9b6..2bd7e61 100644 --- a/llvm/lib/Analysis/ScalarEvolution.cpp +++ b/llvm/lib/Analysis/ScalarEvolution.cpp @@ -4909,19 +4909,19 @@ bool ScalarEvolution::isAddRecNeverPoison(const Instruction *I, const Loop *L) { if (!LatchControlDependentOnPoison) return false; - // Now check if loop is no-throw, and cache the information. In the future, - // we can consider commoning this logic with LICMSafetyInfo into a separate - // analysis pass. + // Now check if loop has abonormal exits (or not), and cache the information. - auto Itr = LoopMayThrow.find(L); - if (Itr == LoopMayThrow.end()) { - bool MayThrow = false; + auto Itr = LoopHasAbnormalExit.find(L); + if (Itr == LoopHasAbnormalExit.end()) { + bool HasAbnormalExit = false; for (auto *BB : L->getBlocks()) { - MayThrow = any_of(*BB, [](Instruction &I) { return I.mayThrow(); }); - if (MayThrow) + HasAbnormalExit = any_of(*BB, [](Instruction &I) { + return !isGuaranteedToTransferExecutionToSuccessor(&I); + }); + if (HasAbnormalExit) break; } - auto InsertPair = LoopMayThrow.insert({L, MayThrow}); + auto InsertPair = LoopHasAbnormalExit.insert({L, HasAbnormalExit}); assert(InsertPair.second && "We just checked!"); Itr = InsertPair.first; } @@ -5490,7 +5490,7 @@ void ScalarEvolution::forgetLoop(const Loop *L) { for (Loop::iterator I = L->begin(), E = L->end(); I != E; ++I) forgetLoop(*I); - LoopMayThrow.erase(L); + LoopHasAbnormalExit.erase(L); } void ScalarEvolution::forgetValue(Value *V) { |