Skip to content

Commit 37f2776

Browse files
committed
[ConstantFold] Fold binary arithmetic on scalable vector splats.
It's a nice simplification, and it confuses instcombine if we don't do it. Differential Revision: https://reviews.llvm.org/D87422
1 parent 31ecf8d commit 37f2776

File tree

2 files changed

+32
-19
lines changed

2 files changed

+32
-19
lines changed

llvm/lib/IR/ConstantFold.cpp

Lines changed: 16 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1408,12 +1408,7 @@ Constant *llvm::ConstantFoldBinaryInstruction(unsigned Opcode, Constant *C1,
14081408
return ConstantFP::get(C1->getContext(), C3V);
14091409
}
14101410
}
1411-
} else if (IsScalableVector) {
1412-
// Do not iterate on scalable vector. The number of elements is unknown at
1413-
// compile-time.
1414-
// FIXME: this branch can potentially be removed
1415-
return nullptr;
1416-
} else if (auto *VTy = dyn_cast<FixedVectorType>(C1->getType())) {
1411+
} else if (auto *VTy = dyn_cast<VectorType>(C1->getType())) {
14171412
// Fast path for splatted constants.
14181413
if (Constant *C2Splat = C2->getSplatValue()) {
14191414
if (Instruction::isIntDivRem(Opcode) && C2Splat->isNullValue())
@@ -1425,22 +1420,24 @@ Constant *llvm::ConstantFoldBinaryInstruction(unsigned Opcode, Constant *C1,
14251420
}
14261421
}
14271422

1428-
// Fold each element and create a vector constant from those constants.
1429-
SmallVector<Constant*, 16> Result;
1430-
Type *Ty = IntegerType::get(VTy->getContext(), 32);
1431-
for (unsigned i = 0, e = VTy->getNumElements(); i != e; ++i) {
1432-
Constant *ExtractIdx = ConstantInt::get(Ty, i);
1433-
Constant *LHS = ConstantExpr::getExtractElement(C1, ExtractIdx);
1434-
Constant *RHS = ConstantExpr::getExtractElement(C2, ExtractIdx);
1423+
if (auto *FVTy = dyn_cast<FixedVectorType>(VTy)) {
1424+
// Fold each element and create a vector constant from those constants.
1425+
SmallVector<Constant*, 16> Result;
1426+
Type *Ty = IntegerType::get(FVTy->getContext(), 32);
1427+
for (unsigned i = 0, e = FVTy->getNumElements(); i != e; ++i) {
1428+
Constant *ExtractIdx = ConstantInt::get(Ty, i);
1429+
Constant *LHS = ConstantExpr::getExtractElement(C1, ExtractIdx);
1430+
Constant *RHS = ConstantExpr::getExtractElement(C2, ExtractIdx);
14351431

1436-
// If any element of a divisor vector is zero, the whole op is undef.
1437-
if (Instruction::isIntDivRem(Opcode) && RHS->isNullValue())
1438-
return UndefValue::get(VTy);
1432+
// If any element of a divisor vector is zero, the whole op is undef.
1433+
if (Instruction::isIntDivRem(Opcode) && RHS->isNullValue())
1434+
return UndefValue::get(VTy);
14391435

1440-
Result.push_back(ConstantExpr::get(Opcode, LHS, RHS));
1441-
}
1436+
Result.push_back(ConstantExpr::get(Opcode, LHS, RHS));
1437+
}
14421438

1443-
return ConstantVector::get(Result);
1439+
return ConstantVector::get(Result);
1440+
}
14441441
}
14451442

14461443
if (ConstantExpr *CE1 = dyn_cast<ConstantExpr>(C1)) {

llvm/test/Transforms/InstSimplify/ConstProp/vscale.ll

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,14 @@ define <vscale x 4 x i32> @sub() {
4141
ret <vscale x 4 x i32> %r
4242
}
4343

44+
define <vscale x 4 x i32> @sub_splat() {
45+
; CHECK-LABEL: @sub_splat(
46+
; CHECK-NEXT: ret <vscale x 4 x i32> shufflevector (<vscale x 4 x i32> insertelement (<vscale x 4 x i32> undef, i32 -16, i32 0), <vscale x 4 x i32> undef, <vscale x 4 x i32> zeroinitializer)
47+
;
48+
%r = sub <vscale x 4 x i32> zeroinitializer, shufflevector (<vscale x 4 x i32> insertelement (<vscale x 4 x i32> undef, i32 16, i32 0), <vscale x 4 x i32> undef, <vscale x 4 x i32> zeroinitializer)
49+
ret <vscale x 4 x i32> %r
50+
}
51+
4452
define <vscale x 4 x float> @fsub() {
4553
; CHECK-LABEL: @fsub(
4654
; CHECK-NEXT: ret <vscale x 4 x float> undef
@@ -73,6 +81,14 @@ define <vscale x 4 x i32> @udiv() {
7381
ret <vscale x 4 x i32> %r
7482
}
7583

84+
define <vscale x 4 x i32> @udiv_splat_zero() {
85+
; CHECK-LABEL: @udiv_splat_zero(
86+
; CHECK-NEXT: ret <vscale x 4 x i32> undef
87+
;
88+
%r = udiv <vscale x 4 x i32> zeroinitializer, zeroinitializer
89+
ret <vscale x 4 x i32> %r
90+
}
91+
7692
define <vscale x 4 x i32> @sdiv() {
7793
; CHECK-LABEL: @sdiv(
7894
; CHECK-NEXT: ret <vscale x 4 x i32> undef

0 commit comments

Comments
 (0)