aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/Analysis/ValueTracking.cpp
diff options
context:
space:
mode:
authorJuneyoung Lee <aqjune@gmail.com>2021-04-01 02:01:17 +0900
committerJuneyoung Lee <aqjune@gmail.com>2021-04-01 02:41:38 +0900
commitdf0b97dab08abb8605533974f6b977c183f6be37 (patch)
treedab7c8df854d92efbf38427cf922258a668e4b8c /llvm/lib/Analysis/ValueTracking.cpp
parentae7b1e8823a51068cfa64875fc5222e5b1d16760 (diff)
downloadllvm-df0b97dab08abb8605533974f6b977c183f6be37.zip
llvm-df0b97dab08abb8605533974f6b977c183f6be37.tar.gz
llvm-df0b97dab08abb8605533974f6b977c183f6be37.tar.bz2
[ValueTracking] Add with.overflow intrinsics to poison analysis functions
This is a patch teaching ValueTracking that `s/u*.with.overflow` intrinsics do not create undef/poison and they propagate poison. I couldn't write a nice example like the one with ctpop; ValueTrackingTest.cpp were simply updated to check these instead. This patch helps reducing regression while fixing https://llvm.org/pr49688 . Reviewed By: nikic Differential Revision: https://reviews.llvm.org/D99671
Diffstat (limited to 'llvm/lib/Analysis/ValueTracking.cpp')
-rw-r--r--llvm/lib/Analysis/ValueTracking.cpp24
1 files changed, 23 insertions, 1 deletions
diff --git a/llvm/lib/Analysis/ValueTracking.cpp b/llvm/lib/Analysis/ValueTracking.cpp
index 39d8f9b..e5c3f3f 100644
--- a/llvm/lib/Analysis/ValueTracking.cpp
+++ b/llvm/lib/Analysis/ValueTracking.cpp
@@ -4887,6 +4887,12 @@ static bool canCreateUndefOrPoison(const Operator *Op, bool PoisonOnly) {
switch (II->getIntrinsicID()) {
// TODO: Add more intrinsics.
case Intrinsic::ctpop:
+ case Intrinsic::sadd_with_overflow:
+ case Intrinsic::ssub_with_overflow:
+ case Intrinsic::smul_with_overflow:
+ case Intrinsic::uadd_with_overflow:
+ case Intrinsic::usub_with_overflow:
+ case Intrinsic::umul_with_overflow:
return false;
}
}
@@ -5214,9 +5220,25 @@ bool llvm::propagatesPoison(const Operator *I) {
case Instruction::Freeze:
case Instruction::Select:
case Instruction::PHI:
- case Instruction::Call:
case Instruction::Invoke:
return false;
+ case Instruction::Call:
+ if (auto *II = dyn_cast<IntrinsicInst>(I)) {
+ switch (II->getIntrinsicID()) {
+ // TODO: Add more intrinsics.
+ case Intrinsic::sadd_with_overflow:
+ case Intrinsic::ssub_with_overflow:
+ case Intrinsic::smul_with_overflow:
+ case Intrinsic::uadd_with_overflow:
+ case Intrinsic::usub_with_overflow:
+ case Intrinsic::umul_with_overflow:
+ // If an input is a vector containing a poison element, the
+ // two output vectors (calculated results, overflow bits)'
+ // corresponding lanes are poison.
+ return true;
+ }
+ }
+ return false;
case Instruction::ICmp:
case Instruction::FCmp:
case Instruction::GetElementPtr: