diff options
| author | Sanjoy Das <sanjoy@playingwithpointers.com> | 2015-09-27 21:09:48 +0000 |
|---|---|---|
| committer | Sanjoy Das <sanjoy@playingwithpointers.com> | 2015-09-27 21:09:48 +0000 |
| commit | f1090b6061b34177ad826a595064232a1c08fb4e (patch) | |
| tree | 79d2e31753788a88bb9492ce67b5f30aa3835546 /llvm/lib | |
| parent | 9533407566c3bafa96d7000e460cf49919acbd38 (diff) | |
| download | bcm5719-llvm-f1090b6061b34177ad826a595064232a1c08fb4e.tar.gz bcm5719-llvm-f1090b6061b34177ad826a595064232a1c08fb4e.zip | |
[SCEV] identical instructions don't compute equal values
Before this change `HasSameValue` would return true for distinct
`alloca` instructions if they happened to be allocating the same
type (`alloca` instructions are not specified as reading memory). This
change adds an explicit whitelist of instruction types for which
"identical" instructions compute the same value.
Fixes PR24952.
llvm-svn: 248690
Diffstat (limited to 'llvm/lib')
| -rw-r--r-- | llvm/lib/Analysis/ScalarEvolution.cpp | 9 |
1 files changed, 8 insertions, 1 deletions
diff --git a/llvm/lib/Analysis/ScalarEvolution.cpp b/llvm/lib/Analysis/ScalarEvolution.cpp index 32d3d36c739..57caa9d368a 100644 --- a/llvm/lib/Analysis/ScalarEvolution.cpp +++ b/llvm/lib/Analysis/ScalarEvolution.cpp @@ -6412,13 +6412,20 @@ static bool HasSameValue(const SCEV *A, const SCEV *B) { // Quick check to see if they are the same SCEV. if (A == B) return true; + auto ComputesEqualValues = [](const Instruction *A, const Instruction *B) { + // Not all instructions that are "identical" compute the same value. For + // instance, two distinct alloca instructions allocating the same type are + // identical and do not read memory; but compute distinct values. + return A->isIdenticalTo(B) && (isa<BinaryOperator>(A) || isa<GetElementPtrInst>(A)); + }; + // Otherwise, if they're both SCEVUnknown, it's possible that they hold // two different instructions with the same value. Check for this case. if (const SCEVUnknown *AU = dyn_cast<SCEVUnknown>(A)) if (const SCEVUnknown *BU = dyn_cast<SCEVUnknown>(B)) if (const Instruction *AI = dyn_cast<Instruction>(AU->getValue())) if (const Instruction *BI = dyn_cast<Instruction>(BU->getValue())) - if (AI->isIdenticalTo(BI) && !AI->mayReadFromMemory()) + if (ComputesEqualValues(AI, BI)) return true; // Otherwise assume they may have a different value. |

