Skip to content

Commit 330a589

Browse files
authored
[PredicateInfo] Handle trunc nuw i1 condition. (llvm#152988)
proof: https://alive2.llvm.org/ce/z/mxtn4L
1 parent d934554 commit 330a589

File tree

3 files changed

+121
-0
lines changed

3 files changed

+121
-0
lines changed

llvm/lib/Transforms/Utils/PredicateInfo.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -370,6 +370,8 @@ void PredicateInfoBuilder::processAssume(
370370
Values.push_back(Cond);
371371
if (auto *Cmp = dyn_cast<CmpInst>(Cond))
372372
collectCmpOps(Cmp, Values);
373+
else if (match(Cond, m_NUWTrunc(m_Value(Op0))))
374+
Values.push_back(Op0);
373375

374376
for (Value *V : Values) {
375377
if (shouldRename(V)) {
@@ -416,6 +418,8 @@ void PredicateInfoBuilder::processBranch(
416418
Values.push_back(Cond);
417419
if (auto *Cmp = dyn_cast<CmpInst>(Cond))
418420
collectCmpOps(Cmp, Values);
421+
else if (match(Cond, m_NUWTrunc(m_Value(Op0))))
422+
Values.push_back(Op0);
419423

420424
for (Value *V : Values) {
421425
if (shouldRename(V)) {
@@ -709,6 +713,11 @@ std::optional<PredicateConstraint> PredicateBase::getConstraint() const {
709713
: ConstantInt::getFalse(Condition->getType())}};
710714
}
711715

716+
if (match(Condition, m_NUWTrunc(m_Specific(RenamedOp)))) {
717+
return {{TrueEdge ? CmpInst::ICMP_NE : CmpInst::ICMP_EQ,
718+
ConstantInt::getNullValue(RenamedOp->getType())}};
719+
}
720+
712721
CmpInst *Cmp = dyn_cast<CmpInst>(Condition);
713722
if (!Cmp) {
714723
// TODO: Make this an assertion once RenamedOp is fully accurate.

llvm/test/Transforms/SCCP/assume.ll

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,3 +69,53 @@ define void @nonnull(ptr %v) {
6969
call void @use(i1 %c4)
7070
ret void
7171
}
72+
73+
define void @trunc_nuw(i8 %v) {
74+
; CHECK-LABEL: @trunc_nuw(
75+
; CHECK-NEXT: [[A:%.*]] = trunc nuw i8 [[V:%.*]] to i1
76+
; CHECK-NEXT: call void @llvm.assume(i1 [[A]])
77+
; CHECK-NEXT: call void @use(i1 false)
78+
; CHECK-NEXT: call void @use(i1 true)
79+
; CHECK-NEXT: call void @use(i1 false)
80+
; CHECK-NEXT: call void @use(i1 true)
81+
; CHECK-NEXT: ret void
82+
;
83+
%a = trunc nuw i8 %v to i1
84+
call void @llvm.assume(i1 %a)
85+
%c1 = icmp eq i8 %v, 0
86+
call void @use(i1 %c1)
87+
%c2 = icmp ne i8 %v, 0
88+
call void @use(i1 %c2)
89+
%c3 = icmp eq i8 0, %v
90+
call void @use(i1 %c3)
91+
%c4 = icmp ne i8 0, %v
92+
call void @use(i1 %c4)
93+
ret void
94+
}
95+
96+
define void @neg_trunc(i8 %v) {
97+
; CHECK-LABEL: @neg_trunc(
98+
; CHECK-NEXT: [[A:%.*]] = trunc i8 [[V:%.*]] to i1
99+
; CHECK-NEXT: call void @llvm.assume(i1 [[A]])
100+
; CHECK-NEXT: [[C1:%.*]] = icmp eq i8 [[V]], 0
101+
; CHECK-NEXT: call void @use(i1 [[C1]])
102+
; CHECK-NEXT: [[C2:%.*]] = icmp ne i8 [[V]], 0
103+
; CHECK-NEXT: call void @use(i1 [[C2]])
104+
; CHECK-NEXT: [[C3:%.*]] = icmp eq i8 0, [[V]]
105+
; CHECK-NEXT: call void @use(i1 [[C3]])
106+
; CHECK-NEXT: [[C4:%.*]] = icmp ne i8 0, [[V]]
107+
; CHECK-NEXT: call void @use(i1 [[C4]])
108+
; CHECK-NEXT: ret void
109+
;
110+
%a = trunc i8 %v to i1
111+
call void @llvm.assume(i1 %a)
112+
%c1 = icmp eq i8 %v, 0
113+
call void @use(i1 %c1)
114+
%c2 = icmp ne i8 %v, 0
115+
call void @use(i1 %c2)
116+
%c3 = icmp eq i8 0, %v
117+
call void @use(i1 %c3)
118+
%c4 = icmp ne i8 0, %v
119+
call void @use(i1 %c4)
120+
ret void
121+
}

llvm/test/Transforms/SCCP/conditions-ranges.ll

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1444,3 +1444,65 @@ define i1 @ptr_icmp_data_layout() {
14441444
%cmp = icmp eq ptr %a.end, @A
14451445
ret i1 %cmp
14461446
}
1447+
1448+
define void @trunc_nuw_1_dominating_icmp_ne_0(i8 %x) {
1449+
; CHECK-LABEL: @trunc_nuw_1_dominating_icmp_ne_0(
1450+
; CHECK-NEXT: [[TRUNC:%.*]] = trunc nuw i8 [[X:%.*]] to i1
1451+
; CHECK-NEXT: br i1 [[TRUNC]], label [[BB1:%.*]], label [[BB2:%.*]]
1452+
; CHECK: bb1:
1453+
; CHECK-NEXT: call void @use(i1 true)
1454+
; CHECK-NEXT: call void @use(i1 true)
1455+
; CHECK-NEXT: ret void
1456+
; CHECK: bb2:
1457+
; CHECK-NEXT: call void @use(i1 false)
1458+
; CHECK-NEXT: call void @use(i1 false)
1459+
; CHECK-NEXT: ret void
1460+
;
1461+
%trunc = trunc nuw i8 %x to i1
1462+
br i1 %trunc, label %bb1, label %bb2
1463+
bb1:
1464+
%c1 = icmp ne i8 %x , 0
1465+
call void @use(i1 %c1)
1466+
%c2 = icmp ne i8 0, %x
1467+
call void @use(i1 %c2)
1468+
ret void
1469+
bb2:
1470+
%c3 = icmp ne i8 %x , 0
1471+
call void @use(i1 %c3)
1472+
%c4 = icmp ne i8 0, %x
1473+
call void @use(i1 %c4)
1474+
ret void
1475+
}
1476+
1477+
define void @neg_trunc_1_dominating_icmp_ne_0(i8 %x) {
1478+
; CHECK-LABEL: @neg_trunc_1_dominating_icmp_ne_0(
1479+
; CHECK-NEXT: [[TRUNC:%.*]] = trunc i8 [[X:%.*]] to i1
1480+
; CHECK-NEXT: br i1 [[TRUNC]], label [[BB1:%.*]], label [[BB2:%.*]]
1481+
; CHECK: bb1:
1482+
; CHECK-NEXT: [[C1:%.*]] = icmp ne i8 [[X]], 0
1483+
; CHECK-NEXT: call void @use(i1 [[C1]])
1484+
; CHECK-NEXT: [[C2:%.*]] = icmp ne i8 0, [[X]]
1485+
; CHECK-NEXT: call void @use(i1 [[C2]])
1486+
; CHECK-NEXT: ret void
1487+
; CHECK: bb2:
1488+
; CHECK-NEXT: [[C3:%.*]] = icmp ne i8 [[X]], 0
1489+
; CHECK-NEXT: call void @use(i1 [[C3]])
1490+
; CHECK-NEXT: [[C4:%.*]] = icmp ne i8 0, [[X]]
1491+
; CHECK-NEXT: call void @use(i1 [[C4]])
1492+
; CHECK-NEXT: ret void
1493+
;
1494+
%trunc = trunc i8 %x to i1
1495+
br i1 %trunc, label %bb1, label %bb2
1496+
bb1:
1497+
%c1 = icmp ne i8 %x , 0
1498+
call void @use(i1 %c1)
1499+
%c2 = icmp ne i8 0, %x
1500+
call void @use(i1 %c2)
1501+
ret void
1502+
bb2:
1503+
%c3 = icmp ne i8 %x , 0
1504+
call void @use(i1 %c3)
1505+
%c4 = icmp ne i8 0, %x
1506+
call void @use(i1 %c4)
1507+
ret void
1508+
}

0 commit comments

Comments
 (0)