Skip to content

Commit 9facaad

Browse files
committed
[ValueTracking] Improve tracking for constant range of {s|u}rem C, x
Current we only support `C` as the remainder, but we can also limit with a constant numerator. Proofs: https://alive2.llvm.org/ce/z/QB95gU Closes #82303
1 parent aa7076f commit 9facaad

File tree

2 files changed

+17
-15
lines changed

2 files changed

+17
-15
lines changed

llvm/lib/Analysis/ValueTracking.cpp

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8776,13 +8776,25 @@ static void setLimitsForBinOp(const BinaryOperator &BO, APInt &Lower,
87768776
// 'srem x, C' produces (-|C|, |C|).
87778777
Upper = C->abs();
87788778
Lower = (-Upper) + 1;
8779+
} else if (match(BO.getOperand(0), m_APInt(C))) {
8780+
if (C->isNegative()) {
8781+
// 'srem -|C|, x' produces [-|C|, 0].
8782+
Upper = 1;
8783+
Lower = *C;
8784+
} else {
8785+
// 'srem |C|, x' produces [0, |C|].
8786+
Upper = *C + 1;
8787+
}
87798788
}
87808789
break;
87818790

87828791
case Instruction::URem:
87838792
if (match(BO.getOperand(1), m_APInt(C)))
87848793
// 'urem x, C' produces [0, C).
87858794
Upper = *C;
8795+
else if (match(BO.getOperand(0), m_APInt(C)))
8796+
// 'urem C, x' produces [0, C].
8797+
Upper = *C + 1;
87868798
break;
87878799

87888800
default:

llvm/test/Analysis/ValueTracking/constant-ranges.ll

Lines changed: 5 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -133,9 +133,7 @@ define i1 @and_ugt_fail(i8 %xx) {
133133

134134
define i1 @urem_okay(i8 %x) {
135135
; CHECK-LABEL: @urem_okay(
136-
; CHECK-NEXT: [[VAL:%.*]] = urem i8 34, [[X:%.*]]
137-
; CHECK-NEXT: [[R:%.*]] = icmp ule i8 [[VAL]], 35
138-
; CHECK-NEXT: ret i1 [[R]]
136+
; CHECK-NEXT: ret i1 true
139137
;
140138
%val = urem i8 34, %x
141139
%r = icmp ule i8 %val, 35
@@ -155,9 +153,7 @@ define i1 @urem_fail(i8 %x) {
155153

156154
define i1 @srem_posC_okay0(i8 %x) {
157155
; CHECK-LABEL: @srem_posC_okay0(
158-
; CHECK-NEXT: [[VAL:%.*]] = srem i8 34, [[X:%.*]]
159-
; CHECK-NEXT: [[R:%.*]] = icmp sle i8 [[VAL]], 34
160-
; CHECK-NEXT: ret i1 [[R]]
156+
; CHECK-NEXT: ret i1 true
161157
;
162158
%val = srem i8 34, %x
163159
%r = icmp sle i8 %val, 34
@@ -166,9 +162,7 @@ define i1 @srem_posC_okay0(i8 %x) {
166162

167163
define i1 @srem_posC_okay1(i8 %x) {
168164
; CHECK-LABEL: @srem_posC_okay1(
169-
; CHECK-NEXT: [[VAL:%.*]] = srem i8 34, [[X:%.*]]
170-
; CHECK-NEXT: [[R:%.*]] = icmp sge i8 [[VAL]], -3
171-
; CHECK-NEXT: ret i1 [[R]]
165+
; CHECK-NEXT: ret i1 true
172166
;
173167
%val = srem i8 34, %x
174168
%r = icmp sge i8 %val, -3
@@ -177,9 +171,7 @@ define i1 @srem_posC_okay1(i8 %x) {
177171

178172
define i1 @srem_negC_okay0(i8 %x) {
179173
; CHECK-LABEL: @srem_negC_okay0(
180-
; CHECK-NEXT: [[VAL:%.*]] = srem i8 -34, [[X:%.*]]
181-
; CHECK-NEXT: [[R:%.*]] = icmp sle i8 [[VAL]], 0
182-
; CHECK-NEXT: ret i1 [[R]]
174+
; CHECK-NEXT: ret i1 true
183175
;
184176
%val = srem i8 -34, %x
185177
%r = icmp sle i8 %val, 0
@@ -188,9 +180,7 @@ define i1 @srem_negC_okay0(i8 %x) {
188180

189181
define i1 @srem_negC_okay1(i8 %x) {
190182
; CHECK-LABEL: @srem_negC_okay1(
191-
; CHECK-NEXT: [[VAL:%.*]] = srem i8 -34, [[X:%.*]]
192-
; CHECK-NEXT: [[R:%.*]] = icmp sge i8 [[VAL]], -34
193-
; CHECK-NEXT: ret i1 [[R]]
183+
; CHECK-NEXT: ret i1 true
194184
;
195185
%val = srem i8 -34, %x
196186
%r = icmp sge i8 %val, -34

0 commit comments

Comments
 (0)