Skip to content

Commit 08ea7f3

Browse files
committed
[InstCombine] Fold (icmp eq/ne (add nuw x, y), 0) -> (icmp eq/ne (or x, y), 0)
`(icmp eq/ne (or x, y), 0)` is probably easier to analyze than `(icmp eq/ne x, -y)` Proof: https://alive2.llvm.org/ce/z/2-VTb6
1 parent 98bfa63 commit 08ea7f3

File tree

2 files changed

+11
-10
lines changed

2 files changed

+11
-10
lines changed

llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3453,6 +3453,11 @@ Instruction *InstCombinerImpl::foldICmpBinOpEqualityWithConstant(
34533453
if (Value *NegVal = dyn_castNegVal(BOp0))
34543454
return new ICmpInst(Pred, NegVal, BOp1);
34553455
if (BO->hasOneUse()) {
3456+
// (add nuw A, B) != 0 -> (or A, B) != 0
3457+
if (match(BO, m_NUWAdd(m_Value(), m_Value()))) {
3458+
Value *Or = Builder.CreateOr(BOp0, BOp1);
3459+
return new ICmpInst(Pred, Or, Constant::getNullValue(BO->getType()));
3460+
}
34563461
Value *Neg = Builder.CreateNeg(BOp1);
34573462
Neg->takeName(BO);
34583463
return new ICmpInst(Pred, BOp0, Neg);

llvm/test/Transforms/InstCombine/icmp-add.ll

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,8 @@ declare void @use(i32)
99
define i1 @cvt_icmp_0_zext_plus_zext_eq_i16(i16 %arg, i16 %arg1) {
1010
; CHECK-LABEL: @cvt_icmp_0_zext_plus_zext_eq_i16(
1111
; CHECK-NEXT: bb:
12-
; CHECK-NEXT: [[I:%.*]] = zext i16 [[ARG:%.*]] to i32
13-
; CHECK-NEXT: [[I2:%.*]] = zext i16 [[ARG1:%.*]] to i32
14-
; CHECK-NEXT: [[I3:%.*]] = sub nsw i32 0, [[I]]
15-
; CHECK-NEXT: [[I4:%.*]] = icmp eq i32 [[I2]], [[I3]]
12+
; CHECK-NEXT: [[TMP0:%.*]] = or i16 [[ARG1:%.*]], [[ARG:%.*]]
13+
; CHECK-NEXT: [[I4:%.*]] = icmp eq i16 [[TMP0]], 0
1614
; CHECK-NEXT: ret i1 [[I4]]
1715
;
1816
bb:
@@ -27,10 +25,8 @@ bb:
2725
define i1 @cvt_icmp_0_zext_plus_zext_eq_i8(i8 %arg, i8 %arg1) {
2826
; CHECK-LABEL: @cvt_icmp_0_zext_plus_zext_eq_i8(
2927
; CHECK-NEXT: bb:
30-
; CHECK-NEXT: [[I:%.*]] = zext i8 [[ARG:%.*]] to i32
31-
; CHECK-NEXT: [[I2:%.*]] = zext i8 [[ARG1:%.*]] to i32
32-
; CHECK-NEXT: [[I3:%.*]] = sub nsw i32 0, [[I]]
33-
; CHECK-NEXT: [[I4:%.*]] = icmp eq i32 [[I2]], [[I3]]
28+
; CHECK-NEXT: [[TMP0:%.*]] = or i8 [[ARG1:%.*]], [[ARG:%.*]]
29+
; CHECK-NEXT: [[I4:%.*]] = icmp eq i8 [[TMP0]], 0
3430
; CHECK-NEXT: ret i1 [[I4]]
3531
;
3632
bb:
@@ -3005,8 +3001,8 @@ define i1 @icmp_dec_notnonzero(i8 %x) {
30053001

30063002
define i1 @icmp_addnuw_nonzero(i8 %x, i8 %y) {
30073003
; CHECK-LABEL: @icmp_addnuw_nonzero(
3008-
; CHECK-NEXT: [[I:%.*]] = sub i8 0, [[Y:%.*]]
3009-
; CHECK-NEXT: [[C:%.*]] = icmp eq i8 [[I]], [[X:%.*]]
3004+
; CHECK-NEXT: [[TMP1:%.*]] = or i8 [[X:%.*]], [[Y:%.*]]
3005+
; CHECK-NEXT: [[C:%.*]] = icmp eq i8 [[TMP1]], 0
30103006
; CHECK-NEXT: ret i1 [[C]]
30113007
;
30123008
%i = add nuw i8 %x, %y

0 commit comments

Comments
 (0)