[llvm] [InstCombine] Use InstSimplify in FoldOpIntoSelect (PR #116073)
Nikita Popov via llvm-commits
llvm-commits at lists.llvm.org
Wed Nov 13 08:02:23 PST 2024
https://github.com/nikic created https://github.com/llvm/llvm-project/pull/116073
Instead of only trying to constant fold the select arms, try to simplify them.
There is no impact on compile-time: https://llvm-compile-time-tracker.com/compare.php?from=6ff41e860fdb69bb9e234e003255aae9accff79a&to=d4af6ba92f72c37cb869b5c9bf56afe08f3d2057&stat=instructions:u
>From 6bca19c69f85cae4b7c5a7a1149f3f4ebc0008bf Mon Sep 17 00:00:00 2001
From: Nikita Popov <npopov at redhat.com>
Date: Wed, 13 Nov 2024 14:30:18 +0100
Subject: [PATCH] [InstCombine] Use InstSimplify in FoldOpIntoSelect
Instead of only trying to constant fold the select arms, try to
simplify them.
---
.../InstCombine/InstructionCombining.cpp | 36 ++++++++-----------
.../Transforms/InstCombine/cast-mul-select.ll | 8 ++---
.../InstCombine/extract-select-agg.ll | 9 ++---
llvm/test/Transforms/InstCombine/fptrunc.ll | 6 ++--
.../Transforms/InstCombine/known-never-nan.ll | 15 ++++----
.../AArch64/deterministic-type-shrinkage.ll | 9 +++--
6 files changed, 35 insertions(+), 48 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
index 563b45de49836f..e2c974fbb9fdee 100644
--- a/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstructionCombining.cpp
@@ -1649,31 +1649,26 @@ Instruction *InstCombinerImpl::foldBinopOfSextBoolToSelect(BinaryOperator &BO) {
return SelectInst::Create(X, TVal, FVal);
}
-static Constant *constantFoldOperationIntoSelectOperand(Instruction &I,
- SelectInst *SI,
- bool IsTrueArm) {
- SmallVector<Constant *> ConstOps;
+static Value *simplifyOperationIntoSelectOperand(Instruction &I, SelectInst *SI,
+ bool IsTrueArm) {
+ SmallVector<Value *> Ops;
for (Value *Op : I.operands()) {
- Constant *C = nullptr;
+ Value *V = nullptr;
if (Op == SI) {
- C = dyn_cast<Constant>(IsTrueArm ? SI->getTrueValue()
- : SI->getFalseValue());
+ V = IsTrueArm ? SI->getTrueValue() : SI->getFalseValue();
} else if (match(SI->getCondition(),
m_SpecificICmp(IsTrueArm ? ICmpInst::ICMP_EQ
: ICmpInst::ICMP_NE,
- m_Specific(Op), m_Constant(C))) &&
- isGuaranteedNotToBeUndefOrPoison(C)) {
+ m_Specific(Op), m_Value(V))) &&
+ isGuaranteedNotToBeUndefOrPoison(V)) {
// Pass
} else {
- C = dyn_cast<Constant>(Op);
+ V = Op;
}
- if (C == nullptr)
- return nullptr;
-
- ConstOps.push_back(C);
+ Ops.push_back(V);
}
- return ConstantFoldInstOperands(&I, ConstOps, I.getDataLayout());
+ return simplifyInstructionWithOperands(&I, Ops, I.getDataLayout());
}
static Value *foldOperationIntoSelectOperand(Instruction &I, SelectInst *SI,
@@ -1681,7 +1676,7 @@ static Value *foldOperationIntoSelectOperand(Instruction &I, SelectInst *SI,
Instruction *Clone = I.clone();
Clone->replaceUsesOfWith(SI, NewOp);
Clone->dropUBImplyingAttrsAndMetadata();
- IC.InsertNewInstBefore(Clone, SI->getIterator());
+ IC.InsertNewInstBefore(Clone, I.getIterator());
return Clone;
}
@@ -1693,8 +1688,6 @@ Instruction *InstCombinerImpl::FoldOpIntoSelect(Instruction &Op, SelectInst *SI,
Value *TV = SI->getTrueValue();
Value *FV = SI->getFalseValue();
- if (!(isa<Constant>(TV) || isa<Constant>(FV)))
- return nullptr;
// Bool selects with constant operands can be folded to logical ops.
if (SI->getType()->isIntOrIntVectorTy(1))
@@ -1715,9 +1708,10 @@ Instruction *InstCombinerImpl::FoldOpIntoSelect(Instruction &Op, SelectInst *SI,
}
}
- // Make sure that one of the select arms constant folds successfully.
- Value *NewTV = constantFoldOperationIntoSelectOperand(Op, SI, /*IsTrueArm*/ true);
- Value *NewFV = constantFoldOperationIntoSelectOperand(Op, SI, /*IsTrueArm*/ false);
+ // Make sure that one of the select arms folds successfully.
+ Value *NewTV = simplifyOperationIntoSelectOperand(Op, SI, /*IsTrueArm*/ true);
+ Value *NewFV =
+ simplifyOperationIntoSelectOperand(Op, SI, /*IsTrueArm*/ false);
if (!NewTV && !NewFV)
return nullptr;
diff --git a/llvm/test/Transforms/InstCombine/cast-mul-select.ll b/llvm/test/Transforms/InstCombine/cast-mul-select.ll
index 6eb3a8c0a2049b..7999aa5e8ae075 100644
--- a/llvm/test/Transforms/InstCombine/cast-mul-select.ll
+++ b/llvm/test/Transforms/InstCombine/cast-mul-select.ll
@@ -73,10 +73,10 @@ define i8 @select2(i1 %cond, i8 %x, i8 %y, i8 %z) {
; DBGINFO-NEXT: #dbg_value(i8 [[Z:%.*]], [[META39:![0-9]+]], !DIExpression(DW_OP_LLVM_convert, 8, DW_ATE_unsigned, DW_OP_LLVM_convert, 32, DW_ATE_unsigned, DW_OP_stack_value), [[META45:![0-9]+]])
; DBGINFO-NEXT: [[D:%.*]] = add i8 [[X]], [[Y]], !dbg [[DBG46:![0-9]+]]
; DBGINFO-NEXT: #dbg_value(!DIArgList(i8 [[X]], i8 [[Y]]), [[META40:![0-9]+]], !DIExpression(DW_OP_LLVM_arg, 0, DW_OP_LLVM_convert, 8, DW_ATE_unsigned, DW_OP_LLVM_convert, 32, DW_ATE_unsigned, DW_OP_LLVM_arg, 1, DW_OP_LLVM_convert, 8, DW_ATE_unsigned, DW_OP_LLVM_convert, 32, DW_ATE_unsigned, DW_OP_plus, DW_OP_stack_value), [[DBG46]])
-; DBGINFO-NEXT: [[E:%.*]] = select i1 [[COND:%.*]], i8 [[Z]], i8 [[D]], !dbg [[DBG47:![0-9]+]]
-; DBGINFO-NEXT: #dbg_value(i32 poison, [[META41:![0-9]+]], !DIExpression(), [[DBG47]])
-; DBGINFO-NEXT: #dbg_value(i8 [[E]], [[META42:![0-9]+]], !DIExpression(), [[META48:![0-9]+]])
-; DBGINFO-NEXT: ret i8 [[E]], !dbg [[DBG49:![0-9]+]]
+; DBGINFO-NEXT: #dbg_value(i32 poison, [[META41:![0-9]+]], !DIExpression(), [[META47:![0-9]+]])
+; DBGINFO-NEXT: [[F:%.*]] = select i1 [[COND:%.*]], i8 [[Z]], i8 [[D]], !dbg [[META47]]
+; DBGINFO-NEXT: #dbg_value(i8 [[F]], [[META42:![0-9]+]], !DIExpression(), [[META48:![0-9]+]])
+; DBGINFO-NEXT: ret i8 [[F]], !dbg [[DBG49:![0-9]+]]
;
%A = zext i8 %x to i32
%B = zext i8 %y to i32
diff --git a/llvm/test/Transforms/InstCombine/extract-select-agg.ll b/llvm/test/Transforms/InstCombine/extract-select-agg.ll
index 6ba6b1a575601d..83b17c93620502 100644
--- a/llvm/test/Transforms/InstCombine/extract-select-agg.ll
+++ b/llvm/test/Transforms/InstCombine/extract-select-agg.ll
@@ -56,14 +56,9 @@ define void @test_select_agg_multiuse(i1 %cond, i64 %v1, i64 %v2, i64 %v3, i64 %
; CHECK-LABEL: define void @test_select_agg_multiuse(
; CHECK-SAME: i1 [[COND:%.*]], i64 [[V1:%.*]], i64 [[V2:%.*]], i64 [[V3:%.*]], i64 [[V4:%.*]]) {
; CHECK-NEXT: entry:
-; CHECK-NEXT: [[A0:%.*]] = insertvalue { i64, i64 } poison, i64 [[V1]], 0
-; CHECK-NEXT: [[A1:%.*]] = insertvalue { i64, i64 } [[A0]], i64 [[V2]], 1
-; CHECK-NEXT: [[B0:%.*]] = insertvalue { i64, i64 } poison, i64 [[V3]], 0
-; CHECK-NEXT: [[B1:%.*]] = insertvalue { i64, i64 } [[B0]], i64 [[V4]], 1
-; CHECK-NEXT: [[SEL:%.*]] = select i1 [[COND]], { i64, i64 } [[A1]], { i64, i64 } [[B1]]
-; CHECK-NEXT: [[X:%.*]] = extractvalue { i64, i64 } [[SEL]], 0
+; CHECK-NEXT: [[X:%.*]] = select i1 [[COND]], i64 [[V1]], i64 [[V3]]
; CHECK-NEXT: call void @use(i64 [[X]])
-; CHECK-NEXT: [[Y:%.*]] = extractvalue { i64, i64 } [[SEL]], 1
+; CHECK-NEXT: [[Y:%.*]] = select i1 [[COND]], i64 [[V2]], i64 [[V4]]
; CHECK-NEXT: call void @use(i64 [[Y]])
; CHECK-NEXT: ret void
;
diff --git a/llvm/test/Transforms/InstCombine/fptrunc.ll b/llvm/test/Transforms/InstCombine/fptrunc.ll
index 825868b1070336..f46940ff060d41 100644
--- a/llvm/test/Transforms/InstCombine/fptrunc.ll
+++ b/llvm/test/Transforms/InstCombine/fptrunc.ll
@@ -52,7 +52,7 @@ define <2 x half> @fmul_constant_op1(<2 x float> %x) {
define float @fptrunc_select_true_val(float %x, double %y, i1 %cond) {
; CHECK-LABEL: @fptrunc_select_true_val(
; CHECK-NEXT: [[TMP1:%.*]] = fptrunc double [[Y:%.*]] to float
-; CHECK-NEXT: [[NARROW_SEL:%.*]] = select fast i1 [[COND:%.*]], float [[TMP1]], float [[X:%.*]]
+; CHECK-NEXT: [[NARROW_SEL:%.*]] = select i1 [[COND:%.*]], float [[TMP1]], float [[X:%.*]]
; CHECK-NEXT: ret float [[NARROW_SEL]]
;
%e = fpext float %x to double
@@ -64,7 +64,7 @@ define float @fptrunc_select_true_val(float %x, double %y, i1 %cond) {
define <2 x float> @fptrunc_select_false_val(<2 x float> %x, <2 x double> %y, <2 x i1> %cond) {
; CHECK-LABEL: @fptrunc_select_false_val(
; CHECK-NEXT: [[TMP1:%.*]] = fptrunc <2 x double> [[Y:%.*]] to <2 x float>
-; CHECK-NEXT: [[NARROW_SEL:%.*]] = select nnan <2 x i1> [[COND:%.*]], <2 x float> [[X:%.*]], <2 x float> [[TMP1]]
+; CHECK-NEXT: [[NARROW_SEL:%.*]] = select <2 x i1> [[COND:%.*]], <2 x float> [[X:%.*]], <2 x float> [[TMP1]]
; CHECK-NEXT: ret <2 x float> [[NARROW_SEL]]
;
%e = fpext <2 x float> %x to <2 x double>
@@ -80,7 +80,7 @@ define half @fptrunc_select_true_val_extra_use(half %x, float %y, i1 %cond) {
; CHECK-NEXT: [[E:%.*]] = fpext half [[X:%.*]] to float
; CHECK-NEXT: call void @use(float [[E]])
; CHECK-NEXT: [[TMP1:%.*]] = fptrunc float [[Y:%.*]] to half
-; CHECK-NEXT: [[NARROW_SEL:%.*]] = select ninf i1 [[COND:%.*]], half [[TMP1]], half [[X]]
+; CHECK-NEXT: [[NARROW_SEL:%.*]] = select i1 [[COND:%.*]], half [[TMP1]], half [[X]]
; CHECK-NEXT: ret half [[NARROW_SEL]]
;
%e = fpext half %x to float
diff --git a/llvm/test/Transforms/InstCombine/known-never-nan.ll b/llvm/test/Transforms/InstCombine/known-never-nan.ll
index 1ca24671d65c49..c4ce8740296470 100644
--- a/llvm/test/Transforms/InstCombine/known-never-nan.ll
+++ b/llvm/test/Transforms/InstCombine/known-never-nan.ll
@@ -20,10 +20,10 @@ define i1 @fabs_sqrt_src_maybe_nan(double %arg0, double %arg1) {
define i1 @select_maybe_nan_lhs(i1 %cond, double %lhs, double %arg1) {
; CHECK-LABEL: @select_maybe_nan_lhs(
-; CHECK-NEXT: [[RHS:%.*]] = fadd nnan double [[ARG1:%.*]], 1.000000e+00
-; CHECK-NEXT: [[OP:%.*]] = select i1 [[COND:%.*]], double [[LHS:%.*]], double [[RHS]]
-; CHECK-NEXT: [[TMP:%.*]] = fcmp ord double [[OP]], 0.000000e+00
-; CHECK-NEXT: ret i1 [[TMP]]
+; CHECK-NEXT: [[TMP:%.*]] = fcmp ord double [[OP:%.*]], 0.000000e+00
+; CHECK-NEXT: [[NOT_COND:%.*]] = xor i1 [[COND:%.*]], true
+; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[NOT_COND]], i1 true, i1 [[TMP]]
+; CHECK-NEXT: ret i1 [[TMP1]]
;
%rhs = fadd nnan double %arg1, 1.0
%op = select i1 %cond, double %lhs, double %rhs
@@ -33,10 +33,9 @@ define i1 @select_maybe_nan_lhs(i1 %cond, double %lhs, double %arg1) {
define i1 @select_maybe_nan_rhs(i1 %cond, double %arg0, double %rhs) {
; CHECK-LABEL: @select_maybe_nan_rhs(
-; CHECK-NEXT: [[LHS:%.*]] = fadd nnan double [[ARG0:%.*]], 1.000000e+00
-; CHECK-NEXT: [[OP:%.*]] = select i1 [[COND:%.*]], double [[LHS]], double [[RHS:%.*]]
-; CHECK-NEXT: [[TMP:%.*]] = fcmp ord double [[OP]], 0.000000e+00
-; CHECK-NEXT: ret i1 [[TMP]]
+; CHECK-NEXT: [[TMP:%.*]] = fcmp ord double [[OP:%.*]], 0.000000e+00
+; CHECK-NEXT: [[TMP1:%.*]] = select i1 [[COND:%.*]], i1 true, i1 [[TMP]]
+; CHECK-NEXT: ret i1 [[TMP1]]
;
%lhs = fadd nnan double %arg0, 1.0
%op = select i1 %cond, double %lhs, double %rhs
diff --git a/llvm/test/Transforms/LoopVectorize/AArch64/deterministic-type-shrinkage.ll b/llvm/test/Transforms/LoopVectorize/AArch64/deterministic-type-shrinkage.ll
index 2ba460255c607d..7642d0d36be7b7 100644
--- a/llvm/test/Transforms/LoopVectorize/AArch64/deterministic-type-shrinkage.ll
+++ b/llvm/test/Transforms/LoopVectorize/AArch64/deterministic-type-shrinkage.ll
@@ -393,7 +393,6 @@ define void @replicate_operands_in_with_operands_in_minbws(ptr %dst, ptr noalias
; CHECK-LABEL: define void @replicate_operands_in_with_operands_in_minbws
; CHECK-SAME: (ptr [[DST:%.*]], ptr noalias [[SRC_1:%.*]], ptr noalias [[SRC_2:%.*]], i32 [[X:%.*]]) {
; CHECK-NEXT: entry:
-; CHECK-NEXT: [[SUB:%.*]] = add i32 [[X]], 65526
; CHECK-NEXT: br label [[LOOP_HEADER:%.*]]
; CHECK: loop.header:
; CHECK-NEXT: [[IV:%.*]] = phi i64 [ 0, [[ENTRY:%.*]] ], [ [[IV_NEXT:%.*]], [[LOOP_LATCH:%.*]] ]
@@ -405,10 +404,10 @@ define void @replicate_operands_in_with_operands_in_minbws(ptr %dst, ptr noalias
; CHECK-NEXT: [[GEP_SRC_2:%.*]] = getelementptr inbounds i16, ptr [[SRC_2]], i64 [[IV]]
; CHECK-NEXT: [[L_2:%.*]] = load i16, ptr [[GEP_SRC_2]], align 2
; CHECK-NEXT: [[C_2:%.*]] = icmp ult i16 [[L_2]], 100
-; CHECK-NEXT: [[CONV:%.*]] = zext i16 [[L_2]] to i32
-; CHECK-NEXT: [[SEL:%.*]] = select i1 [[C_2]], i32 [[SUB]], i32 [[CONV]]
-; CHECK-NEXT: [[TMP0:%.*]] = trunc i32 [[SEL]] to i16
-; CHECK-NEXT: [[TRUNC:%.*]] = add i16 [[L_2]], [[TMP0]]
+; CHECK-NEXT: [[TMP0:%.*]] = trunc i32 [[X]] to i16
+; CHECK-NEXT: [[TMP1:%.*]] = add i16 [[TMP0]], -10
+; CHECK-NEXT: [[TMP2:%.*]] = select i1 [[C_2]], i16 [[TMP1]], i16 [[L_2]]
+; CHECK-NEXT: [[TRUNC:%.*]] = add i16 [[TMP2]], [[L_2]]
; CHECK-NEXT: [[GEP_DST:%.*]] = getelementptr inbounds i32, ptr [[DST]], i64 [[IV]]
; CHECK-NEXT: store i16 [[TRUNC]], ptr [[GEP_DST]], align 2
; CHECK-NEXT: br label [[LOOP_LATCH]]
More information about the llvm-commits
mailing list