[llvm] 68fed27 - [Attributor] Handle calls in AAValueConstantRange properly
Johannes Doerfert via llvm-commits
llvm-commits at lists.llvm.org
Mon Mar 23 08:46:44 PDT 2020
Author: Johannes Doerfert
Date: 2020-03-23T10:45:24-05:00
New Revision: 68fed2706743ffc921221caea6dfe38b17aaf73b
URL: https://github.com/llvm/llvm-project/commit/68fed2706743ffc921221caea6dfe38b17aaf73b
DIFF: https://github.com/llvm/llvm-project/commit/68fed2706743ffc921221caea6dfe38b17aaf73b.diff
LOG: [Attributor] Handle calls in AAValueConstantRange properly
We did handle calls that were operands of certain instructions but not
standalone calls we visit via indirection, e.g., selects.
Added:
Modified:
llvm/lib/Transforms/IPO/Attributor.cpp
llvm/test/Transforms/Attributor/range.ll
Removed:
################################################################################
diff --git a/llvm/lib/Transforms/IPO/Attributor.cpp b/llvm/lib/Transforms/IPO/Attributor.cpp
index fb860bdf7a01..594e7146d2b9 100644
--- a/llvm/lib/Transforms/IPO/Attributor.cpp
+++ b/llvm/lib/Transforms/IPO/Attributor.cpp
@@ -7134,7 +7134,7 @@ struct AAValueConstantRangeFloating : AAValueConstantRangeImpl {
auto VisitValueCB = [&](Value &V, IntegerRangeState &T,
bool Stripped) -> bool {
Instruction *I = dyn_cast<Instruction>(&V);
- if (!I) {
+ if (!I || isa<CallBase>(I)) {
// If the value is not instruction, we query AA to Attributor.
const auto &AA =
diff --git a/llvm/test/Transforms/Attributor/range.ll b/llvm/test/Transforms/Attributor/range.ll
index 25cf27e7886a..1e93e97634b2 100644
--- a/llvm/test/Transforms/Attributor/range.ll
+++ b/llvm/test/Transforms/Attributor/range.ll
@@ -1264,6 +1264,108 @@ define i8 @undef_collapse_caller() {
ret i8 %a
}
+define i32 @ret1or2(i1 %c) {
+; CHECK-LABEL: define {{[^@]+}}@ret1or2
+; CHECK-SAME: (i1 [[C:%.*]])
+; CHECK-NEXT: [[S:%.*]] = select i1 [[C]], i32 1, i32 2
+; CHECK-NEXT: ret i32 [[S]]
+;
+ %s = select i1 %c, i32 1, i32 2
+ ret i32 %s
+}
+define i1 @callee_range_1(i1 %c1, i1 %c2, i1 %c3) {
+; OLD_PM-LABEL: define {{[^@]+}}@callee_range_1
+; OLD_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]])
+; OLD_PM-NEXT: [[F:%.*]] = and i1 true, true
+; OLD_PM-NEXT: ret i1 [[F]]
+;
+; NEW_PM-LABEL: define {{[^@]+}}@callee_range_1
+; NEW_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]])
+; NEW_PM-NEXT: [[F:%.*]] = and i1 true, true
+; NEW_PM-NEXT: ret i1 [[F]]
+;
+; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@callee_range_1
+; CGSCC_OLD_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]])
+; CGSCC_OLD_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]])
+; CGSCC_OLD_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]])
+; CGSCC_OLD_PM-NEXT: [[INDIRECTION:%.*]] = select i1 [[C3]], i32 [[R1]], i32 [[R2]]
+; CGSCC_OLD_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[INDIRECTION]]
+; CGSCC_OLD_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 4
+; CGSCC_OLD_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; CGSCC_OLD_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; CGSCC_OLD_PM-NEXT: ret i1 [[F]]
+;
+; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@callee_range_1
+; CGSCC_NEW_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]], i1 [[C3:%.*]])
+; CGSCC_NEW_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]])
+; CGSCC_NEW_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]])
+; CGSCC_NEW_PM-NEXT: [[INDIRECTION:%.*]] = select i1 [[C3]], i32 [[R1]], i32 [[R2]]
+; CGSCC_NEW_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[INDIRECTION]]
+; CGSCC_NEW_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 4
+; CGSCC_NEW_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; CGSCC_NEW_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; CGSCC_NEW_PM-NEXT: ret i1 [[F]]
+;
+ %r1 = call i32 @ret1or2(i1 %c1)
+ %r2 = call i32 @ret1or2(i1 %c2)
+ %indirection = select i1 %c3, i32 %r1, i32 %r2
+ %a = add i32 %r1, %indirection
+ %i1 = icmp sle i32 %a, 4
+ %i2 = icmp sge i32 %a, 2
+ %f = and i1 %i1, %i2
+ ret i1 %f
+}
+
+define i1 @callee_range_2(i1 %c1, i1 %c2) {
+; OLD_PM-LABEL: define {{[^@]+}}@callee_range_2
+; OLD_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]])
+; OLD_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]]) #2, !range !4
+; OLD_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]]) #3, !range !4
+; OLD_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[R2]]
+; OLD_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 3
+; OLD_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; OLD_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; OLD_PM-NEXT: ret i1 [[F]]
+;
+; NEW_PM-LABEL: define {{[^@]+}}@callee_range_2
+; NEW_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]])
+; NEW_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]]) #2, !range !5
+; NEW_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]]) #3, !range !5
+; NEW_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[R2]]
+; NEW_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 3
+; NEW_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; NEW_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; NEW_PM-NEXT: ret i1 [[F]]
+;
+; CGSCC_OLD_PM-LABEL: define {{[^@]+}}@callee_range_2
+; CGSCC_OLD_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]])
+; CGSCC_OLD_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]])
+; CGSCC_OLD_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]])
+; CGSCC_OLD_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[R2]]
+; CGSCC_OLD_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 3
+; CGSCC_OLD_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; CGSCC_OLD_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; CGSCC_OLD_PM-NEXT: ret i1 [[F]]
+;
+; CGSCC_NEW_PM-LABEL: define {{[^@]+}}@callee_range_2
+; CGSCC_NEW_PM-SAME: (i1 [[C1:%.*]], i1 [[C2:%.*]])
+; CGSCC_NEW_PM-NEXT: [[R1:%.*]] = call i32 @ret1or2(i1 [[C1]])
+; CGSCC_NEW_PM-NEXT: [[R2:%.*]] = call i32 @ret1or2(i1 [[C2]])
+; CGSCC_NEW_PM-NEXT: [[A:%.*]] = add i32 [[R1]], [[R2]]
+; CGSCC_NEW_PM-NEXT: [[I1:%.*]] = icmp sle i32 [[A]], 3
+; CGSCC_NEW_PM-NEXT: [[I2:%.*]] = icmp sge i32 [[A]], 2
+; CGSCC_NEW_PM-NEXT: [[F:%.*]] = and i1 [[I1]], [[I2]]
+; CGSCC_NEW_PM-NEXT: ret i1 [[F]]
+;
+ %r1 = call i32 @ret1or2(i1 %c1)
+ %r2 = call i32 @ret1or2(i1 %c2)
+ %a = add i32 %r1, %r2
+ %i1 = icmp sle i32 %a, 3
+ %i2 = icmp sge i32 %a, 2
+ %f = and i1 %i1, %i2
+ ret i1 %f
+}
+
!0 = !{i32 0, i32 10}
!1 = !{i32 10, i32 100}
More information about the llvm-commits
mailing list