Skip to content

Commit e558575

Browse files
committed
[GISel] Set more MIFlags when translating GEPs
The IRTranslator sets the flags now more consistently with `SelectionDAGBuilder::visitGetElementPtr()`. This affects `nuw` and `nusw`, as well as the recently introduced `inbounds` MIFlag (see PR #150900). This PR also adds more tests to `AArch64/GlobalISel/irtranslator-gep-flags.ll` to cover all points in `IRTranslator::translateGetElementPtr` that set flags. For SWDEV-516125.
1 parent 6b7a8e9 commit e558575

File tree

6 files changed

+220
-37
lines changed

6 files changed

+220
-37
lines changed

llvm/lib/CodeGen/GlobalISel/IRTranslator.cpp

Lines changed: 30 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1592,9 +1592,19 @@ bool IRTranslator::translateGetElementPtr(const User &U,
15921592
Type *OffsetIRTy = DL->getIndexType(PtrIRTy);
15931593
LLT OffsetTy = getLLTForType(*OffsetIRTy, *DL);
15941594

1595-
uint32_t Flags = 0;
1595+
uint32_t PtrAddFlags = 0;
1596+
// Each PtrAdd generated to implement the GEP inherits its nuw, nusw, inbounds
1597+
// flags.
15961598
if (const Instruction *I = dyn_cast<Instruction>(&U))
1597-
Flags = MachineInstr::copyFlagsFromInstruction(*I);
1599+
PtrAddFlags = MachineInstr::copyFlagsFromInstruction(*I);
1600+
1601+
auto PtrAddFlagsWithConst = [&](int64_t Offset) {
1602+
// For nusw/inbounds GEP with an offset that is nonnegative when interpreted
1603+
// as signed, assume there is no unsigned overflow.
1604+
if (Offset >= 0 && (PtrAddFlags & MachineInstr::MIFlag::NoUSWrap))
1605+
return PtrAddFlags | MachineInstr::MIFlag::NoUWrap;
1606+
return PtrAddFlags;
1607+
};
15981608

15991609
// Normalize Vector GEP - all scalar operands should be converted to the
16001610
// splat vector.
@@ -1644,7 +1654,9 @@ bool IRTranslator::translateGetElementPtr(const User &U,
16441654

16451655
if (Offset != 0) {
16461656
auto OffsetMIB = MIRBuilder.buildConstant({OffsetTy}, Offset);
1647-
BaseReg = MIRBuilder.buildPtrAdd(PtrTy, BaseReg, OffsetMIB.getReg(0))
1657+
BaseReg = MIRBuilder
1658+
.buildPtrAdd(PtrTy, BaseReg, OffsetMIB.getReg(0),
1659+
PtrAddFlagsWithConst(Offset))
16481660
.getReg(0);
16491661
Offset = 0;
16501662
}
@@ -1668,24 +1680,32 @@ bool IRTranslator::translateGetElementPtr(const User &U,
16681680
if (ElementSize != 1) {
16691681
auto ElementSizeMIB = MIRBuilder.buildConstant(
16701682
getLLTForType(*OffsetIRTy, *DL), ElementSize);
1683+
1684+
// The multiplication is NUW if the GEP is NUW and NSW if the GEP is
1685+
// NUSW.
1686+
uint32_t ScaleFlags = PtrAddFlags & MachineInstr::MIFlag::NoUWrap;
1687+
if (PtrAddFlags & MachineInstr::MIFlag::NoUSWrap)
1688+
ScaleFlags |= MachineInstr::MIFlag::NoSWrap;
1689+
16711690
GepOffsetReg =
1672-
MIRBuilder.buildMul(OffsetTy, IdxReg, ElementSizeMIB).getReg(0);
1673-
} else
1691+
MIRBuilder.buildMul(OffsetTy, IdxReg, ElementSizeMIB, ScaleFlags)
1692+
.getReg(0);
1693+
} else {
16741694
GepOffsetReg = IdxReg;
1695+
}
16751696

1676-
BaseReg = MIRBuilder.buildPtrAdd(PtrTy, BaseReg, GepOffsetReg).getReg(0);
1697+
BaseReg =
1698+
MIRBuilder.buildPtrAdd(PtrTy, BaseReg, GepOffsetReg, PtrAddFlags)
1699+
.getReg(0);
16771700
}
16781701
}
16791702

16801703
if (Offset != 0) {
16811704
auto OffsetMIB =
16821705
MIRBuilder.buildConstant(OffsetTy, Offset);
16831706

1684-
if (Offset >= 0 && cast<GEPOperator>(U).isInBounds())
1685-
Flags |= MachineInstr::MIFlag::NoUWrap;
1686-
16871707
MIRBuilder.buildPtrAdd(getOrCreateVReg(U), BaseReg, OffsetMIB.getReg(0),
1688-
Flags);
1708+
PtrAddFlagsWithConst(Offset));
16891709
return true;
16901710
}
16911711

llvm/test/CodeGen/AArch64/GlobalISel/arm64-irtranslator-gep.ll

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,12 +13,12 @@ define i32 @cse_gep(ptr %ptr, i32 %idx) {
1313
; O0-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
1414
; O0-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
1515
; O0-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
16-
; O0-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
17-
; O0-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
16+
; O0-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
17+
; O0-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
1818
; O0-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
1919
; O0-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
20-
; O0-NEXT: [[MUL1:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
21-
; O0-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL1]](s64)
20+
; O0-NEXT: [[MUL1:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
21+
; O0-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL1]](s64)
2222
; O0-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 4
2323
; O0-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
2424
; O0-NEXT: [[LOAD1:%[0-9]+]]:_(s32) = G_LOAD [[PTR_ADD2]](p0) :: (load (s32) from %ir.gep2)
@@ -34,8 +34,8 @@ define i32 @cse_gep(ptr %ptr, i32 %idx) {
3434
; O3-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
3535
; O3-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
3636
; O3-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
37-
; O3-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
38-
; O3-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
37+
; O3-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
38+
; O3-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
3939
; O3-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
4040
; O3-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
4141
; O3-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 4

llvm/test/CodeGen/AArch64/GlobalISel/arm64-irtranslator-switch.ll

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -792,8 +792,8 @@ define void @jt_multiple_jump_tables(ptr %arg, i32 %arg1, ptr %arg2) {
792792
; CHECK-NEXT: bb.56.bb57:
793793
; CHECK-NEXT: [[PHI:%[0-9]+]]:_(s64) = G_PHI [[C56]](s64), %bb.1, [[C57]](s64), %bb.2, [[C58]](s64), %bb.3, [[C59]](s64), %bb.4, [[C60]](s64), %bb.5, [[C61]](s64), %bb.6, [[C62]](s64), %bb.7, [[C63]](s64), %bb.8, [[C64]](s64), %bb.9, [[C65]](s64), %bb.10, [[C66]](s64), %bb.11, [[C67]](s64), %bb.12, [[C68]](s64), %bb.13, [[C69]](s64), %bb.14, [[C70]](s64), %bb.15, [[C71]](s64), %bb.16, [[C72]](s64), %bb.17, [[C73]](s64), %bb.18, [[C74]](s64), %bb.19, [[C75]](s64), %bb.20, [[C76]](s64), %bb.21, [[C77]](s64), %bb.22, [[C78]](s64), %bb.23, [[C79]](s64), %bb.24, [[C80]](s64), %bb.25, [[C81]](s64), %bb.26, [[C82]](s64), %bb.27, [[C83]](s64), %bb.28, [[C84]](s64), %bb.29, [[C85]](s64), %bb.30, [[C86]](s64), %bb.31, [[C87]](s64), %bb.32, [[C88]](s64), %bb.33, [[C89]](s64), %bb.34, [[C90]](s64), %bb.35, [[C91]](s64), %bb.36, [[C92]](s64), %bb.37, [[C93]](s64), %bb.38, [[C94]](s64), %bb.39, [[C95]](s64), %bb.40, [[C96]](s64), %bb.41, [[C97]](s64), %bb.42, [[C98]](s64), %bb.43, [[C99]](s64), %bb.44, [[C100]](s64), %bb.45, [[C101]](s64), %bb.46, [[C102]](s64), %bb.47, [[C103]](s64), %bb.48, [[C104]](s64), %bb.49, [[C105]](s64), %bb.50, [[C106]](s64), %bb.51, [[C107]](s64), %bb.52, [[C108]](s64), %bb.53, [[C109]](s64), %bb.54, [[C110]](s64), %bb.55
794794
; CHECK-NEXT: [[C111:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
795-
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[PHI]], [[C111]]
796-
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[GV]], [[MUL]](s64)
795+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[PHI]], [[C111]]
796+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[GV]], [[MUL]](s64)
797797
; CHECK-NEXT: [[C112:%[0-9]+]]:_(s64) = G_CONSTANT i64 8
798798
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[PTR_ADD]], [[C112]](s64)
799799
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(p0) = G_LOAD [[PTR_ADD1]](p0) :: (load (p0) from %ir.tmp59)

llvm/test/CodeGen/AArch64/GlobalISel/irtranslator-gep-flags.ll

Lines changed: 178 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,12 @@ define i32 @gep_nusw_nuw(ptr %ptr, i32 %idx) {
1010
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
1111
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
1212
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
13-
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
14-
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
13+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
14+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
1515
; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
1616
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
17-
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
18-
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL1]](s64)
17+
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = nuw nsw G_MUL [[SEXT]], [[C]]
18+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[COPY]], [[MUL1]](s64)
1919
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 4
2020
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
2121
; CHECK-NEXT: [[LOAD1:%[0-9]+]]:_(s32) = G_LOAD [[PTR_ADD2]](p0) :: (load (s32) from %ir.gep2)
@@ -40,12 +40,12 @@ define i32 @gep_nuw(ptr %ptr, i32 %idx) {
4040
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
4141
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
4242
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
43-
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
44-
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
43+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
44+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
4545
; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
4646
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
47-
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
48-
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL1]](s64)
47+
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = nuw G_MUL [[SEXT]], [[C]]
48+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw G_PTR_ADD [[COPY]], [[MUL1]](s64)
4949
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 4
5050
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
5151
; CHECK-NEXT: [[LOAD1:%[0-9]+]]:_(s32) = G_LOAD [[PTR_ADD2]](p0) :: (load (s32) from %ir.gep2)
@@ -70,14 +70,14 @@ define i32 @gep_nusw(ptr %ptr, i32 %idx) {
7070
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
7171
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
7272
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
73-
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
74-
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
73+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
74+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
7575
; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
7676
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
77-
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
78-
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL1]](s64)
77+
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
78+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[COPY]], [[MUL1]](s64)
7979
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 4
80-
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
80+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
8181
; CHECK-NEXT: [[LOAD1:%[0-9]+]]:_(s32) = G_LOAD [[PTR_ADD2]](p0) :: (load (s32) from %ir.gep2)
8282
; CHECK-NEXT: [[ADD:%[0-9]+]]:_(s32) = G_ADD [[LOAD]], [[LOAD1]]
8383
; CHECK-NEXT: $w0 = COPY [[ADD]](s32)
@@ -100,8 +100,8 @@ define i32 @gep_none(ptr %ptr, i32 %idx) {
100100
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
101101
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
102102
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
103-
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
104-
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[MUL]](s64)
103+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
104+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
105105
; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
106106
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
107107
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C]]
@@ -120,3 +120,166 @@ define i32 @gep_none(ptr %ptr, i32 %idx) {
120120
%res = add i32 %v1, %v2
121121
ret i32 %res
122122
}
123+
124+
define i32 @gep_nusw_negative(ptr %ptr, i32 %idx) {
125+
; CHECK-LABEL: name: gep_nusw_negative
126+
; CHECK: bb.1 (%ir-block.0):
127+
; CHECK-NEXT: liveins: $w1, $x0
128+
; CHECK-NEXT: {{ $}}
129+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
130+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
131+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
132+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 16
133+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
134+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[COPY]], [[MUL]](s64)
135+
; CHECK-NEXT: [[COPY2:%[0-9]+]]:_(p0) = COPY [[PTR_ADD]](p0)
136+
; CHECK-NEXT: [[LOAD:%[0-9]+]]:_(s32) = G_LOAD [[COPY2]](p0) :: (load (s32) from %ir.gep1)
137+
; CHECK-NEXT: [[MUL1:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C]]
138+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[COPY]], [[MUL1]](s64)
139+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
140+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[PTR_ADD1]], [[C1]](s64)
141+
; CHECK-NEXT: [[LOAD1:%[0-9]+]]:_(s32) = G_LOAD [[PTR_ADD2]](p0) :: (load (s32) from %ir.gep2)
142+
; CHECK-NEXT: [[ADD:%[0-9]+]]:_(s32) = G_ADD [[LOAD]], [[LOAD1]]
143+
; CHECK-NEXT: $w0 = COPY [[ADD]](s32)
144+
; CHECK-NEXT: RET_ReallyLR implicit $w0
145+
%sidx = sext i32 %idx to i64
146+
%gep1 = getelementptr inbounds [4 x i32], ptr %ptr, i64 %sidx, i64 0
147+
%v1 = load i32, ptr %gep1
148+
%gep2 = getelementptr nusw [4 x i32], ptr %ptr, i64 %sidx, i64 -1
149+
%v2 = load i32, ptr %gep2
150+
%res = add i32 %v1, %v2
151+
ret i32 %res
152+
}
153+
154+
define ptr @gep_many_indices(ptr %ptr, i32 %idx) {
155+
; CHECK-LABEL: name: gep_many_indices
156+
; CHECK: bb.1 (%ir-block.0):
157+
; CHECK-NEXT: liveins: $w1, $x0
158+
; CHECK-NEXT: {{ $}}
159+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
160+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
161+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
162+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
163+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = G_PTR_ADD [[COPY]], [[C]](s64)
164+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
165+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = G_MUL [[SEXT]], [[C1]]
166+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
167+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
168+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
169+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
170+
; CHECK-NEXT: RET_ReallyLR implicit $x0
171+
%sidx = sext i32 %idx to i64
172+
%gep = getelementptr {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
173+
ret ptr %gep
174+
}
175+
176+
define ptr @gep_nuw_many_indices(ptr %ptr, i32 %idx) {
177+
; CHECK-LABEL: name: gep_nuw_many_indices
178+
; CHECK: bb.1 (%ir-block.0):
179+
; CHECK-NEXT: liveins: $w1, $x0
180+
; CHECK-NEXT: {{ $}}
181+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
182+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
183+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
184+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
185+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nuw G_PTR_ADD [[COPY]], [[C]](s64)
186+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
187+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nuw G_MUL [[SEXT]], [[C1]]
188+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
189+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
190+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
191+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
192+
; CHECK-NEXT: RET_ReallyLR implicit $x0
193+
%sidx = sext i32 %idx to i64
194+
%gep = getelementptr nuw {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
195+
ret ptr %gep
196+
}
197+
198+
define ptr @gep_nusw_many_indices(ptr %ptr, i32 %idx) {
199+
; CHECK-LABEL: name: gep_nusw_many_indices
200+
; CHECK: bb.1 (%ir-block.0):
201+
; CHECK-NEXT: liveins: $w1, $x0
202+
; CHECK-NEXT: {{ $}}
203+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
204+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
205+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
206+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
207+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[COPY]], [[C]](s64)
208+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
209+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C1]]
210+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
211+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
212+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nusw G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
213+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
214+
; CHECK-NEXT: RET_ReallyLR implicit $x0
215+
%sidx = sext i32 %idx to i64
216+
%gep = getelementptr nusw {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
217+
ret ptr %gep
218+
}
219+
220+
define ptr @gep_inbounds_many_indices(ptr %ptr, i32 %idx) {
221+
; CHECK-LABEL: name: gep_inbounds_many_indices
222+
; CHECK: bb.1 (%ir-block.0):
223+
; CHECK-NEXT: liveins: $w1, $x0
224+
; CHECK-NEXT: {{ $}}
225+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
226+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
227+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
228+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
229+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[COPY]], [[C]](s64)
230+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
231+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nsw G_MUL [[SEXT]], [[C1]]
232+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
233+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
234+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nusw inbounds G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
235+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
236+
; CHECK-NEXT: RET_ReallyLR implicit $x0
237+
%sidx = sext i32 %idx to i64
238+
%gep = getelementptr inbounds {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
239+
ret ptr %gep
240+
}
241+
242+
define ptr @gep_nuw_nusw_many_indices(ptr %ptr, i32 %idx) {
243+
; CHECK-LABEL: name: gep_nuw_nusw_many_indices
244+
; CHECK: bb.1 (%ir-block.0):
245+
; CHECK-NEXT: liveins: $w1, $x0
246+
; CHECK-NEXT: {{ $}}
247+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
248+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
249+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
250+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
251+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[COPY]], [[C]](s64)
252+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
253+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nuw nsw G_MUL [[SEXT]], [[C1]]
254+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
255+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
256+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw nusw G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
257+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
258+
; CHECK-NEXT: RET_ReallyLR implicit $x0
259+
%sidx = sext i32 %idx to i64
260+
%gep = getelementptr nuw nusw {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
261+
ret ptr %gep
262+
}
263+
264+
define ptr @gep_nuw_inbounds_many_indices(ptr %ptr, i32 %idx) {
265+
; CHECK-LABEL: name: gep_nuw_inbounds_many_indices
266+
; CHECK: bb.1 (%ir-block.0):
267+
; CHECK-NEXT: liveins: $w1, $x0
268+
; CHECK-NEXT: {{ $}}
269+
; CHECK-NEXT: [[COPY:%[0-9]+]]:_(p0) = COPY $x0
270+
; CHECK-NEXT: [[COPY1:%[0-9]+]]:_(s32) = COPY $w1
271+
; CHECK-NEXT: [[SEXT:%[0-9]+]]:_(s64) = G_SEXT [[COPY1]](s32)
272+
; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 108
273+
; CHECK-NEXT: [[PTR_ADD:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[COPY]], [[C]](s64)
274+
; CHECK-NEXT: [[C1:%[0-9]+]]:_(s64) = G_CONSTANT i64 12
275+
; CHECK-NEXT: [[MUL:%[0-9]+]]:_(s64) = nuw nsw G_MUL [[SEXT]], [[C1]]
276+
; CHECK-NEXT: [[PTR_ADD1:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[PTR_ADD]], [[MUL]](s64)
277+
; CHECK-NEXT: [[C2:%[0-9]+]]:_(s64) = G_CONSTANT i64 -4
278+
; CHECK-NEXT: [[PTR_ADD2:%[0-9]+]]:_(p0) = nuw nusw inbounds G_PTR_ADD [[PTR_ADD1]], [[C2]](s64)
279+
; CHECK-NEXT: $x0 = COPY [[PTR_ADD2]](p0)
280+
; CHECK-NEXT: RET_ReallyLR implicit $x0
281+
%sidx = sext i32 %idx to i64
282+
%gep = getelementptr nuw inbounds {i32, [4 x [3 x i32]]}, ptr %ptr, i64 2, i32 1, i64 %sidx, i64 -1
283+
ret ptr %gep
284+
}
285+

0 commit comments

Comments
 (0)