[llvm] [InstCombine] Fold fcmp ogt (x - y), 0 into fcmp ogt x, y #85245 (PR #85506)
via llvm-commits
llvm-commits at lists.llvm.org
Wed Jun 12 01:49:45 PDT 2024
https://github.com/SahilPatidar updated https://github.com/llvm/llvm-project/pull/85506
>From 1cec33cb675c86f434de67d627e0f736a4e5d36a Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Mon, 18 Mar 2024 15:11:30 +0530
Subject: [PATCH 01/19] Added tests to verify fast math flag behavior
---
llvm/test/Transforms/InstCombine/fcmp.ll | 90 ++++++++++++++++++++++++
1 file changed, 90 insertions(+)
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index 4d907800219d6..9cdba4678b484 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1718,3 +1718,93 @@ define <2 x i1> @fcmp_une_sel_x_negx_with_any_fpzero_nnan_vec(<2 x i1> %cond, <2
%icmp = fcmp nnan une <2 x float> %sel, <float 0.0, float -0.0>
ret <2 x i1> %icmp
}
+
+define <8 x i1> @fcmp_vec_ogt_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ogt_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_olt_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_olt_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp olt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_one_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_one_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp one <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_ogt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ogt_fm_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_olt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_olt_fm_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp olt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_one_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_one_fm_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp one <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @ffcmp_vec_ogt_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @ffcmp_vec_ogt_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp fast ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @ffcmp_vec_olt_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @ffcmp_vec_olt_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp fast olt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @ffcmp_vec_one_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @ffcmp_vec_one_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp fast one <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
>From 18c3aa5a4e7d7e2f88f907561c4b6ddb8726eda0 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Fri, 22 Mar 2024 22:23:05 +0530
Subject: [PATCH 02/19] Modifies code and updates relevant tests
---
.../InstCombine/InstCombineCompares.cpp | 31 +++
llvm/test/Transforms/InstCombine/fcmp.ll | 198 ++++++++++++++----
2 files changed, 193 insertions(+), 36 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 89193f8ff94b6..9bef812e0ea73 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8075,6 +8075,37 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
return replaceOperand(I, 0, X);
if (Instruction *NV = FoldOpIntoSelect(I, cast<SelectInst>(LHSI)))
return NV;
+ case Instruction::FSub:
+ switch (Pred) {
+ default:
+ break;
+ case FCmpInst::FCMP_UGT:
+ case FCmpInst::FCMP_ULT:
+ case FCmpInst::FCMP_UNE:
+ case FCmpInst::FCMP_OEQ:
+ case FCmpInst::FCMP_OGE:
+ case FCmpInst::FCMP_OLE: {
+ BinaryOperator *SubI = cast<BinaryOperator>(LHSI);
+ if (!computeKnownFPClass(SubI->getOperand(0), SubI->getFastMathFlags(),
+ fcInf, LHSI, 0)
+ .isKnownNeverInfinity() &&
+ !computeKnownFPClass(SubI->getOperand(1), SubI->getFastMathFlags(),
+ fcInf, LHSI, 0)
+ .isKnownNeverInfinity())
+ break;
+ }
+ LLVM_FALLTHROUGH;
+ case FCmpInst::FCMP_OGT:
+ case FCmpInst::FCMP_OLT:
+ case FCmpInst::FCMP_ONE:
+ case FCmpInst::FCMP_UEQ:
+ case FCmpInst::FCMP_UGE:
+ case FCmpInst::FCMP_ULE:
+ if (match(RHSC, m_AnyZeroFP()) &&
+ match(LHSI, m_FSub(m_Value(X), m_Value(Y))))
+ return new FCmpInst(Pred, X, Y);
+ break;
+ }
break;
case Instruction::PHI:
if (Instruction *NV = foldOpIntoPhi(I, cast<PHINode>(LHSI)))
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index 9cdba4678b484..b5093cba98083 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1719,38 +1719,164 @@ define <2 x i1> @fcmp_une_sel_x_negx_with_any_fpzero_nnan_vec(<2 x i1> %cond, <2
ret <2 x i1> %icmp
}
-define <8 x i1> @fcmp_vec_ogt_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ogt_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+define i1 @fcmp_oeq_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_oeq_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp oeq float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_oge_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_oge_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oge float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp oge float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_ole_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ole_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ole float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp ole float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_ueq_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ueq_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp ueq float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_uge_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_uge_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp uge float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp uge float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_ule_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ule_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ule float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp ule float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_ugt_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ugt_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ugt float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp ugt float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_ult_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ult_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ult float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp ult float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define i1 @fcmp_une_fsub_const(float %x, float %y) {
+; CHECK-LABEL: @fcmp_une_fsub_const(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp une float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ %cmp = fcmp une float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+define <8 x i1> @fcmp_vec_uge_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_uge_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp uge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp uge <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_olt_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_olt_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ule_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ule_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ule <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp olt <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ule <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_one_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_one_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ueq_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ueq_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp one <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ueq <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ogt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ogt_fm_fsub_const(
+define <8 x i1> @fcmp_vec_oge_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_oge_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oge <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp oge <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_ole_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ole_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ole <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ole <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_oeq_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_oeq_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp oeq <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_vec_ogt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ogt_fast_fsub_const(
; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
@@ -1759,8 +1885,8 @@ define <8 x i1> @fcmp_vec_ogt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_olt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_olt_fm_fsub_const(
+define <8 x i1> @fcmp_vec_olt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_olt_fast_fsub_const(
; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
@@ -1769,8 +1895,8 @@ define <8 x i1> @fcmp_vec_olt_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_one_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_one_fm_fsub_const(
+define <8 x i1> @fcmp_vec_one_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_one_fast_fsub_const(
; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
@@ -1779,32 +1905,32 @@ define <8 x i1> @fcmp_vec_one_fm_fsub_const(<8 x float> %x, <8 x float> %y) {
ret <8 x i1> %cmp
}
-define <8 x i1> @ffcmp_vec_ogt_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @ffcmp_vec_ogt_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ugt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ugt_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ugt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp fast ogt <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ugt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @ffcmp_vec_olt_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @ffcmp_vec_olt_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ult_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ult_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ult <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp fast olt <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp ult <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @ffcmp_vec_one_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @ffcmp_vec_one_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_une_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_une_fast_fsub_const(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp une <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub <8 x float> %x, %y
- %cmp = fcmp fast one <8 x float> %fs, zeroinitializer
+ %fs = fsub fast <8 x float> %x, %y
+ %cmp = fcmp une <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
>From a3bb17fabf44e60b0eb6e6cf7e79322521923c74 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Wed, 27 Mar 2024 16:18:22 +0530
Subject: [PATCH 03/19] added fmf flag to fcmp
---
.../InstCombine/InstCombineCompares.cpp | 2 +-
llvm/test/Transforms/InstCombine/fcmp.ll | 96 +++++++++----------
2 files changed, 49 insertions(+), 49 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 9bef812e0ea73..e0a277e27682e 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8103,7 +8103,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_ULE:
if (match(RHSC, m_AnyZeroFP()) &&
match(LHSI, m_FSub(m_Value(X), m_Value(Y))))
- return new FCmpInst(Pred, X, Y);
+ return new FCmpInst(Pred, X, Y, "", &I);
break;
}
break;
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index b5093cba98083..85ca56f687126 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1815,122 +1815,122 @@ define i1 @fcmp_une_fsub_const(float %x, float %y) {
ret i1 %cmp
}
-define <8 x i1> @fcmp_vec_uge_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_uge_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp uge <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_uge_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_uge_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast uge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp uge <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast uge <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ule_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ule_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ule <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ule_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ule_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ule <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ule <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ule <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ueq_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ueq_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ueq_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ueq_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ueq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ueq <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ueq <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_oge_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_oge_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp oge <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_oge_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_oge_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast oge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp oge <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast oge <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ole_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ole_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ole <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ole_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ole_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ole <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ole <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ole <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_oeq_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_oeq_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_oeq_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_oeq_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast oeq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp oeq <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast oeq <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ogt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ogt_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ogt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ogt_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ogt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ogt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_olt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_olt_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp olt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_olt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_olt_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast olt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp olt <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast olt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_one_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_one_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp one <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_one_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_one_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast one <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp one <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast one <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ugt_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ugt_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ugt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ugt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ugt_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ugt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ugt <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ugt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ult_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ult_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ult <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_ult_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_ult_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ult <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp ult <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast ult <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_une_fast_fsub_const(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_une_fast_fsub_const(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp une <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_vec_une_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_vec_une_fsub_const_fmf(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast une <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp une <8 x float> %fs, zeroinitializer
+ %cmp = fcmp fast une <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
>From 30fd3054b7a527857f79e00c3824b09c409c5a7a Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Sat, 13 Apr 2024 15:10:25 +0530
Subject: [PATCH 04/19] Fix code to handle ninf and nnan
---
.../InstCombine/InstCombineCompares.cpp | 8 +-
llvm/test/Transforms/InstCombine/fcmp.ll | 244 ++++++++++++++----
2 files changed, 190 insertions(+), 62 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index e0a277e27682e..ebfda901746a1 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,12 +8086,8 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE: {
BinaryOperator *SubI = cast<BinaryOperator>(LHSI);
- if (!computeKnownFPClass(SubI->getOperand(0), SubI->getFastMathFlags(),
- fcInf, LHSI, 0)
- .isKnownNeverInfinity() &&
- !computeKnownFPClass(SubI->getOperand(1), SubI->getFastMathFlags(),
- fcInf, LHSI, 0)
- .isKnownNeverInfinity())
+ if (!isKnownNeverInfOrNaN(SubI->getOperand(0), 0, SQ) &&
+ !isKnownNeverInfOrNaN(SubI->getOperand(1), 0, SQ))
break;
}
LLVM_FALLTHROUGH;
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index 85ca56f687126..cdaa1e2775f56 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1815,109 +1815,240 @@ define i1 @fcmp_une_fsub_const(float %x, float %y) {
ret i1 %cmp
}
-define <8 x i1> @fcmp_vec_uge_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_uge_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast uge <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_uge_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_uge_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf uge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast uge <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf uge <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ule_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ule_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ule <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ule_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ule_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ule <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ule <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ule <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ueq_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ueq_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ueq <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ueq_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ueq_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ueq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ueq <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ueq <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_oge_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_oge_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast oge <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_oge_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_oge_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oge <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast oge <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf oge <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ole_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ole_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ole <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ole_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ole_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ole <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ole <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ole <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_oeq_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_oeq_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast oeq <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_oeq_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_oeq_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oeq <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast oeq <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf oeq <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ogt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ogt_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ogt_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ogt_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ogt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ogt <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ogt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_olt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_olt_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast olt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_olt_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_olt_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf olt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast olt <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf olt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_one_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_one_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast one <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_one_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_one_fsub_const_ninf_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf one <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast one <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf one <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ugt_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ugt_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ugt <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ugt_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ugt_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ugt <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ugt <8 x float> %fs, zeroinitializer
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ugt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ult_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ult_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ult <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf ult <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_une_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_une_fsub_const_ninf_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf une <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub ninf <8 x float> %x, %y
+ %cmp = fcmp ninf une <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_uge_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_uge_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan uge <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan uge <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ule_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ule_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ule <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ule <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ueq_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ueq_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ueq <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ueq <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_oge_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_oge_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oge <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan oge <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ole_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ole_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ole <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ole <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_oeq_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_oeq_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oeq <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan oeq <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ogt_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ogt_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ogt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_olt_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_olt_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan olt <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan olt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_one_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_one_fsub_const_nnan_vec(
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan one <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan one <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ugt_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ugt_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ugt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ugt <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_ult_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_ult_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ult <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_ult_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_ult_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub fast <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ult <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
@@ -1925,9 +2056,10 @@ define <8 x i1> @fcmp_vec_ult_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_vec_une_fsub_const_fmf(<8 x float> %x, <8 x float> %y) {
-; CHECK-LABEL: @fcmp_vec_une_fsub_const_fmf(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast une <8 x float> [[X:%.*]], [[Y:%.*]]
+define <8 x i1> @fcmp_une_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
+; CHECK-LABEL: @fcmp_une_fsub_const_nnan_vec(
+; CHECK-NEXT: [[FS:%.*]] = fsub fast <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp fast une <8 x float> [[FS]], zeroinitializer
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub fast <8 x float> %x, %y
>From 7f6e313c83ff0e53bb07d5de4ae9770b50da8f7e Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Wed, 17 Apr 2024 15:06:58 +0530
Subject: [PATCH 05/19] fix: Handle ninf values (update test)
---
.../InstCombine/InstCombineCompares.cpp | 15 ++++---
llvm/test/Transforms/InstCombine/fcmp.ll | 44 +++++++------------
2 files changed, 26 insertions(+), 33 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index ebfda901746a1..ce31e16dd7146 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8085,9 +8085,11 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE: {
- BinaryOperator *SubI = cast<BinaryOperator>(LHSI);
- if (!isKnownNeverInfOrNaN(SubI->getOperand(0), 0, SQ) &&
- !isKnownNeverInfOrNaN(SubI->getOperand(1), 0, SQ))
+ if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
+ !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
+ getSimplifyQuery().getWithInstruction(&I)) &&
+ !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
+ getSimplifyQuery().getWithInstruction(&I)))
break;
}
LLVM_FALLTHROUGH;
@@ -8098,8 +8100,11 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_UGE:
case FCmpInst::FCMP_ULE:
if (match(RHSC, m_AnyZeroFP()) &&
- match(LHSI, m_FSub(m_Value(X), m_Value(Y))))
- return new FCmpInst(Pred, X, Y, "", &I);
+ match(LHSI, m_FSub(m_Value(X), m_Value(Y)))) {
+ replaceOperand(I, 0, X);
+ replaceOperand(I, 1, Y);
+ return &I;
+ }
break;
}
break;
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index cdaa1e2775f56..bd4f8a56069d7 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1847,8 +1847,7 @@ define <8 x i1> @fcmp_ueq_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_oge_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_oge_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oge <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1858,8 +1857,7 @@ define <8 x i1> @fcmp_oge_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ole_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ole_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ole <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ole <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1869,8 +1867,7 @@ define <8 x i1> @fcmp_ole_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_oeq_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_oeq_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oeq <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oeq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1910,8 +1907,7 @@ define <8 x i1> @fcmp_one_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ugt_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ugt_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ugt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ugt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1921,8 +1917,7 @@ define <8 x i1> @fcmp_ugt_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ult_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ult_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ult <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf ult <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1932,8 +1927,7 @@ define <8 x i1> @fcmp_ult_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_une_fsub_const_ninf_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_une_fsub_const_ninf_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub ninf <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf une <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf une <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub ninf <8 x float> %x, %y
@@ -1973,8 +1967,7 @@ define <8 x i1> @fcmp_ueq_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_oge_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_oge_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oge <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oge <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub nnan <8 x float> %x, %y
@@ -1984,8 +1977,7 @@ define <8 x i1> @fcmp_oge_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ole_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ole_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ole <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ole <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub nnan <8 x float> %x, %y
@@ -1995,8 +1987,7 @@ define <8 x i1> @fcmp_ole_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_oeq_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_oeq_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oeq <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan oeq <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub nnan <8 x float> %x, %y
@@ -2036,8 +2027,7 @@ define <8 x i1> @fcmp_one_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ugt_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ugt_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub nnan <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ugt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ugt <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
%fs = fsub nnan <8 x float> %x, %y
@@ -2047,22 +2037,20 @@ define <8 x i1> @fcmp_ugt_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
define <8 x i1> @fcmp_ult_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_ult_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub fast <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast ult <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ult <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast ult <8 x float> %fs, zeroinitializer
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan ult <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
define <8 x i1> @fcmp_une_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
; CHECK-LABEL: @fcmp_une_fsub_const_nnan_vec(
-; CHECK-NEXT: [[FS:%.*]] = fsub fast <8 x float> [[X:%.*]], [[Y:%.*]]
-; CHECK-NEXT: [[CMP:%.*]] = fcmp fast une <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan une <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret <8 x i1> [[CMP]]
;
- %fs = fsub fast <8 x float> %x, %y
- %cmp = fcmp fast une <8 x float> %fs, zeroinitializer
+ %fs = fsub nnan <8 x float> %x, %y
+ %cmp = fcmp nnan une <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
>From 6179573b87f3aeb306f95b615e7adbc901eb5c7f Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Thu, 25 Apr 2024 11:47:03 +0530
Subject: [PATCH 06/19] adds test and update to check denormals being flushed
---
.../InstCombine/InstCombineCompares.cpp | 9 ++-
llvm/test/Transforms/InstCombine/fcmp.ll | 61 ++++++++++++++-----
2 files changed, 53 insertions(+), 17 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index ce31e16dd7146..6ef425f5b5d9b 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,9 +8086,9 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE: {
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
- !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I)) &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
+ getSimplifyQuery().getWithInstruction(&I)) &&
+ !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)))
break;
}
@@ -8100,7 +8100,10 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_UGE:
case FCmpInst::FCMP_ULE:
if (match(RHSC, m_AnyZeroFP()) &&
- match(LHSI, m_FSub(m_Value(X), m_Value(Y)))) {
+ match(LHSI, m_FSub(m_Value(X), m_Value(Y))) &&
+ I.getFunction()->getDenormalMode(
+ LHSI->getType()->getScalarType()->getFltSemantics()) ==
+ DenormalMode::getIEEE()) {
replaceOperand(I, 0, X);
replaceOperand(I, 1, Y);
return &I;
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index bd4f8a56069d7..cffa31e0afbe0 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1289,7 +1289,7 @@ define <1 x i1> @bitcast_1vec_eq0(i32 %x) {
define i1 @fcmp_fadd_zero_ugt(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ugt(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ugt float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ugt float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1299,7 +1299,7 @@ define i1 @fcmp_fadd_zero_ugt(float %x, float %y) {
define i1 @fcmp_fadd_zero_uge(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_uge(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp uge float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp uge float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1309,7 +1309,7 @@ define i1 @fcmp_fadd_zero_uge(float %x, float %y) {
define i1 @fcmp_fadd_zero_ogt(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ogt(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1319,7 +1319,7 @@ define i1 @fcmp_fadd_zero_ogt(float %x, float %y) {
define i1 @fcmp_fadd_zero_oge(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_oge(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp oge float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oge float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1329,7 +1329,7 @@ define i1 @fcmp_fadd_zero_oge(float %x, float %y) {
define i1 @fcmp_fadd_zero_ult(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ult(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ult float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ult float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1339,7 +1339,7 @@ define i1 @fcmp_fadd_zero_ult(float %x, float %y) {
define i1 @fcmp_fadd_zero_ule(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ule(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ule float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ule float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1349,7 +1349,7 @@ define i1 @fcmp_fadd_zero_ule(float %x, float %y) {
define i1 @fcmp_fadd_zero_olt(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_olt(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp olt float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp olt float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1359,7 +1359,7 @@ define i1 @fcmp_fadd_zero_olt(float %x, float %y) {
define i1 @fcmp_fadd_zero_ole(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ole(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ole float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ole float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1369,7 +1369,7 @@ define i1 @fcmp_fadd_zero_ole(float %x, float %y) {
define i1 @fcmp_fadd_zero_oeq(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_oeq(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp oeq float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1379,7 +1379,7 @@ define i1 @fcmp_fadd_zero_oeq(float %x, float %y) {
define i1 @fcmp_fadd_zero_one(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_one(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp one float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp one float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1389,7 +1389,7 @@ define i1 @fcmp_fadd_zero_one(float %x, float %y) {
define i1 @fcmp_fadd_zero_ueq(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ueq(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1399,7 +1399,7 @@ define i1 @fcmp_fadd_zero_ueq(float %x, float %y) {
define i1 @fcmp_fadd_zero_une(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_une(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp une float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp une float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1409,7 +1409,7 @@ define i1 @fcmp_fadd_zero_une(float %x, float %y) {
define i1 @fcmp_fadd_zero_ord(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_ord(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ord float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ord float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -1419,7 +1419,7 @@ define i1 @fcmp_fadd_zero_ord(float %x, float %y) {
define i1 @fcmp_fadd_zero_uno(float %x, float %y) {
; CHECK-LABEL: @fcmp_fadd_zero_uno(
-; CHECK-NEXT: [[CMP:%.*]] = fcmp uno float [[ADD:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp uno float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: ret i1 [[CMP]]
;
%add = fadd float %x, 0.000000e+00
@@ -2054,3 +2054,36 @@ define <8 x i1> @fcmp_une_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
%cmp = fcmp nnan une <8 x float> %fs, zeroinitializer
ret <8 x i1> %cmp
}
+
+define <8 x i1> @fcmp_ugt_fsub_const_vec_denormal_positive-zero(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="positive-zero" {
+; CHECK-LABEL: @fcmp_ugt_fsub_const_vec_denormal_positive-zero(
+; CHECK-NEXT: [[FS:%.*]] = fsub <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ogt_fsub_const_vec_denormal_dynamic(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="dynamic,dynamic" {
+; CHECK-LABEL: @fcmp_ogt_fsub_const_vec_denormal_dynamic(
+; CHECK-NEXT: [[FS:%.*]] = fsub <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
+
+define <8 x i1> @fcmp_ogt_fsub_const_vec_denormal_preserve-sign(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="preserve-sign" {
+; CHECK-LABEL: @fcmp_ogt_fsub_const_vec_denormal_preserve-sign(
+; CHECK-NEXT: [[FS:%.*]] = fsub <8 x float> [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[FS]], zeroinitializer
+; CHECK-NEXT: ret <8 x i1> [[CMP]]
+;
+ %fs = fsub <8 x float> %x, %y
+ %cmp = fcmp ogt <8 x float> %fs, zeroinitializer
+ ret <8 x i1> %cmp
+}
>From 6d017b54374d1aa7ec3497d400101ab34f670882 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Thu, 9 May 2024 09:45:53 +0530
Subject: [PATCH 07/19] minor fixes
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 9 ++++++---
llvm/test/Transforms/InstCombine/fcmp.ll | 4 ++--
2 files changed, 8 insertions(+), 5 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 6ef425f5b5d9b..8f9f59a2eefe9 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8075,6 +8075,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
return replaceOperand(I, 0, X);
if (Instruction *NV = FoldOpIntoSelect(I, cast<SelectInst>(LHSI)))
return NV;
+ break;
case Instruction::FSub:
switch (Pred) {
default:
@@ -8084,21 +8085,23 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_UNE:
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
- case FCmpInst::FCMP_OLE: {
+ case FCmpInst::FCMP_OLE:
+ // fsub x, y --> isnnan(x, y) && isninf(x, y)
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)) &&
!isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)))
break;
- }
- LLVM_FALLTHROUGH;
+
+ [[fallthrough]];
case FCmpInst::FCMP_OGT:
case FCmpInst::FCMP_OLT:
case FCmpInst::FCMP_ONE:
case FCmpInst::FCMP_UEQ:
case FCmpInst::FCMP_UGE:
case FCmpInst::FCMP_ULE:
+ // fcmp pred (x - y), 0 --> fcmp pred x, y
if (match(RHSC, m_AnyZeroFP()) &&
match(LHSI, m_FSub(m_Value(X), m_Value(Y))) &&
I.getFunction()->getDenormalMode(
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index cffa31e0afbe0..1f7b3fca0b00e 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -2055,7 +2055,7 @@ define <8 x i1> @fcmp_une_fsub_const_nnan_vec(<8 x float> %x, <8 x float> %y) {
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_ugt_fsub_const_vec_denormal_positive-zero(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="positive-zero" {
+define <8 x i1> @fcmp_ugt_fsub_const_vec_denormal_positive-zero(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="positive-zero,positive-zero" {
; CHECK-LABEL: @fcmp_ugt_fsub_const_vec_denormal_positive-zero(
; CHECK-NEXT: [[FS:%.*]] = fsub <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[FS]], zeroinitializer
@@ -2077,7 +2077,7 @@ define <8 x i1> @fcmp_ogt_fsub_const_vec_denormal_dynamic(<8 x float> %x, <8 x f
ret <8 x i1> %cmp
}
-define <8 x i1> @fcmp_ogt_fsub_const_vec_denormal_preserve-sign(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="preserve-sign" {
+define <8 x i1> @fcmp_ogt_fsub_const_vec_denormal_preserve-sign(<8 x float> %x, <8 x float> %y) "denormal-fp-math"="preserve-sign,preserve-sign" {
; CHECK-LABEL: @fcmp_ogt_fsub_const_vec_denormal_preserve-sign(
; CHECK-NEXT: [[FS:%.*]] = fsub <8 x float> [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: [[CMP:%.*]] = fcmp ogt <8 x float> [[FS]], zeroinitializer
>From 60d8a18ae0caed5a3327b87932ade531cb3cba87 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Sat, 11 May 2024 11:11:10 +0530
Subject: [PATCH 08/19] fixes comment
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 8f9f59a2eefe9..4ee74e1311e06 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,7 +8086,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // fsub x, y --> isnnan(x, y) && isninf(x, y)
+ // Skip optimization: fsub x, y guaranteed isInf(x, y).
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)) &&
>From b5f9d79b21a7fc3350ffec9786ff4b1ef21451c2 Mon Sep 17 00:00:00 2001
From: Matt Arsenault <arsenm2 at gmail.com>
Date: Mon, 13 May 2024 11:48:33 +0200
Subject: [PATCH 09/19] Comment touchup
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 4ee74e1311e06..44d71c74c643d 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,7 +8086,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y guaranteed isInf(x, y).
+ // Skip optimization: fsub x, y unless guaranteed !isinf(x) && !isinf(y).
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)) &&
>From c8ab52cae0bcb272637cfc95138a685ebd5e6005 Mon Sep 17 00:00:00 2001
From: Matt Arsenault <arsenm2 at gmail.com>
Date: Mon, 13 May 2024 11:53:59 +0200
Subject: [PATCH 10/19] Fix clang-format error
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 44d71c74c643d..cc0f020232141 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,7 +8086,8 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y unless guaranteed !isinf(x) && !isinf(y).
+ // Skip optimization: fsub x, y unless guaranteed !isinf(x) &&
+ // !isinf(y).
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)) &&
>From 3a696e0cedb325ebf038c119c77190d69f9aa26b Mon Sep 17 00:00:00 2001
From: Matt Arsenault <arsenm2 at gmail.com>
Date: Mon, 13 May 2024 12:00:54 +0200
Subject: [PATCH 11/19] or not and
Co-authored-by: Jay Foad <jay.foad at gmail.com>
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index cc0f020232141..11eb28237efc3 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,7 +8086,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y unless guaranteed !isinf(x) &&
+ // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
// !isinf(y).
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
>From b888fd827e38c52c0d18dff6100827bf36ff0f60 Mon Sep 17 00:00:00 2001
From: Matt Arsenault <arsenm2 at gmail.com>
Date: Mon, 13 May 2024 12:05:13 +0200
Subject: [PATCH 12/19] whitespace
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 11eb28237efc3..87caef5ac0879 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8086,7 +8086,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
+ // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
// !isinf(y).
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
>From 15c24c6e77d39d7544c0ab3dee73f2086584e5ea Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Thu, 16 May 2024 14:25:23 +0530
Subject: [PATCH 13/19] add one use check
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 87caef5ac0879..c156c9be0d287 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8104,7 +8104,7 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_ULE:
// fcmp pred (x - y), 0 --> fcmp pred x, y
if (match(RHSC, m_AnyZeroFP()) &&
- match(LHSI, m_FSub(m_Value(X), m_Value(Y))) &&
+ match(LHSI, m_OneUse(m_FSub(m_Value(X), m_Value(Y)))) &&
I.getFunction()->getDenormalMode(
LHSI->getType()->getScalarType()->getFltSemantics()) ==
DenormalMode::getIEEE()) {
>From 70a1d95dc746161966338542ea3153cbfaf6e412 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Thu, 16 May 2024 14:35:31 +0530
Subject: [PATCH 14/19] adds negative test
---
llvm/test/Transforms/InstCombine/fcmp.ll | 15 +++++++++++++++
1 file changed, 15 insertions(+)
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index 1f7b3fca0b00e..b43479010062e 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1719,6 +1719,21 @@ define <2 x i1> @fcmp_une_sel_x_negx_with_any_fpzero_nnan_vec(<2 x i1> %cond, <2
ret <2 x i1> %icmp
}
+; negative test - extra use
+
+define i1 @fcmp_ueq_fsub_const_extra_use(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ueq_fsub_const_extra_use(
+; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: call void @use(float [[FS]])
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub float %x, %y
+ call void @use(float %fs)
+ %cmp = fcmp ueq float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
define i1 @fcmp_oeq_fsub_const(float %x, float %y) {
; CHECK-LABEL: @fcmp_oeq_fsub_const(
; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
>From d65b59fed18ea84934a36df52e2895b5a02f825c Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Fri, 17 May 2024 11:21:17 +0530
Subject: [PATCH 15/19] adds negative tests
---
.../InstCombine/InstCombineCompares.cpp | 4 +--
llvm/test/Transforms/InstCombine/fcmp.ll | 27 ++++++++++++++-----
2 files changed, 23 insertions(+), 8 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index c156c9be0d287..e5a0d6c6385c5 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8088,11 +8088,11 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OLE:
// Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
// !isinf(y).
- if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
+ if (!LHSI->hasOneUse() || (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
getSimplifyQuery().getWithInstruction(&I)) &&
!isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I)))
+ getSimplifyQuery().getWithInstruction(&I))))
break;
[[fallthrough]];
diff --git a/llvm/test/Transforms/InstCombine/fcmp.ll b/llvm/test/Transforms/InstCombine/fcmp.ll
index b43479010062e..656b3d2c49206 100644
--- a/llvm/test/Transforms/InstCombine/fcmp.ll
+++ b/llvm/test/Transforms/InstCombine/fcmp.ll
@@ -1721,16 +1721,31 @@ define <2 x i1> @fcmp_une_sel_x_negx_with_any_fpzero_nnan_vec(<2 x i1> %cond, <2
; negative test - extra use
-define i1 @fcmp_ueq_fsub_const_extra_use(float %x, float %y) {
-; CHECK-LABEL: @fcmp_ueq_fsub_const_extra_use(
-; CHECK-NEXT: [[FS:%.*]] = fsub float [[X:%.*]], [[Y:%.*]]
+define i1 @fcmp_ueq_fsub_nnan_const_extra_use(float %x, float %y) {
+; CHECK-LABEL: @fcmp_ueq_fsub_nnan_const_extra_use(
+; CHECK-NEXT: [[FS:%.*]] = fsub nnan float [[X:%.*]], [[Y:%.*]]
; CHECK-NEXT: call void @use(float [[FS]])
-; CHECK-NEXT: [[CMP:%.*]] = fcmp ueq float [[FS]], 0.000000e+00
+; CHECK-NEXT: [[CMP:%.*]] = fcmp nnan ueq float [[FS]], 0.000000e+00
; CHECK-NEXT: ret i1 [[CMP]]
;
- %fs = fsub float %x, %y
+ %fs = fsub nnan float %x, %y
call void @use(float %fs)
- %cmp = fcmp ueq float %fs, 0.000000e+00
+ %cmp = fcmp nnan ueq float %fs, 0.000000e+00
+ ret i1 %cmp
+}
+
+; negative test - extra use
+
+define i1 @fcmp_oeq_fsub_ninf_const_extra_use(float %x, float %y) {
+; CHECK-LABEL: @fcmp_oeq_fsub_ninf_const_extra_use(
+; CHECK-NEXT: [[FS:%.*]] = fsub ninf float [[X:%.*]], [[Y:%.*]]
+; CHECK-NEXT: call void @use(float [[FS]])
+; CHECK-NEXT: [[CMP:%.*]] = fcmp ninf oeq float [[FS]], 0.000000e+00
+; CHECK-NEXT: ret i1 [[CMP]]
+;
+ %fs = fsub ninf float %x, %y
+ call void @use(float %fs)
+ %cmp = fcmp ninf oeq float %fs, 0.000000e+00
ret i1 %cmp
}
>From a18a17ff36240e43f2f0a4c519b9b0f9e9da9201 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Mon, 20 May 2024 09:23:38 +0530
Subject: [PATCH 16/19] Fixes clang-format
---
.../Transforms/InstCombine/InstCombineCompares.cpp | 11 ++++++-----
1 file changed, 6 insertions(+), 5 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index e5a0d6c6385c5..47c6860c5afb6 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -8088,11 +8088,12 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
case FCmpInst::FCMP_OLE:
// Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
// !isinf(y).
- if (!LHSI->hasOneUse() || (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
- !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I)) &&
- !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I))))
+ if (!LHSI->hasOneUse() ||
+ (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
+ !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
+ getSimplifyQuery().getWithInstruction(&I)) &&
+ !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
+ getSimplifyQuery().getWithInstruction(&I))))
break;
[[fallthrough]];
>From ea3f94fe62b6851381709e6c7e22064267199eb9 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Tue, 21 May 2024 11:33:30 +0530
Subject: [PATCH 17/19] replace switch block with helper function
---
.../InstCombine/InstCombineCompares.cpp | 86 +++++++++++--------
1 file changed, 48 insertions(+), 38 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 47c6860c5afb6..709a0a515741c 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -7906,6 +7906,51 @@ static Instruction *foldFCmpFNegCommonOp(FCmpInst &I) {
return new FCmpInst(Pred, Op0, Zero, "", &I);
}
+static Instruction *foldFCmpFSubIntoFCmp(FCmpInst &I, Instruction *LHSI,
+ Constant *RHSC, InstCombinerImpl &CI) {
+ const CmpInst::Predicate Pred = I.getPredicate();
+ Value *X, *Y;
+ switch (Pred) {
+ default:
+ break;
+ case FCmpInst::FCMP_UGT:
+ case FCmpInst::FCMP_ULT:
+ case FCmpInst::FCMP_UNE:
+ case FCmpInst::FCMP_OEQ:
+ case FCmpInst::FCMP_OGE:
+ case FCmpInst::FCMP_OLE:
+ // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
+ // !isinf(y).
+ if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
+ !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
+ CI.getSimplifyQuery().getWithInstruction(&I)) &&
+ !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
+ CI.getSimplifyQuery().getWithInstruction(&I)))
+ break;
+
+ [[fallthrough]];
+ case FCmpInst::FCMP_OGT:
+ case FCmpInst::FCMP_OLT:
+ case FCmpInst::FCMP_ONE:
+ case FCmpInst::FCMP_UEQ:
+ case FCmpInst::FCMP_UGE:
+ case FCmpInst::FCMP_ULE:
+ // fcmp pred (x - y), 0 --> fcmp pred x, y
+ if (match(RHSC, m_AnyZeroFP()) &&
+ match(LHSI, m_FSub(m_Value(X), m_Value(Y))) &&
+ I.getFunction()->getDenormalMode(
+ LHSI->getType()->getScalarType()->getFltSemantics()) ==
+ DenormalMode::getIEEE()) {
+ CI.replaceOperand(I, 0, X);
+ CI.replaceOperand(I, 1, Y);
+ return &I;
+ }
+ break;
+ }
+
+ return nullptr;
+}
+
Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
bool Changed = false;
@@ -8077,44 +8122,9 @@ Instruction *InstCombinerImpl::visitFCmpInst(FCmpInst &I) {
return NV;
break;
case Instruction::FSub:
- switch (Pred) {
- default:
- break;
- case FCmpInst::FCMP_UGT:
- case FCmpInst::FCMP_ULT:
- case FCmpInst::FCMP_UNE:
- case FCmpInst::FCMP_OEQ:
- case FCmpInst::FCMP_OGE:
- case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
- // !isinf(y).
- if (!LHSI->hasOneUse() ||
- (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
- !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I)) &&
- !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
- getSimplifyQuery().getWithInstruction(&I))))
- break;
-
- [[fallthrough]];
- case FCmpInst::FCMP_OGT:
- case FCmpInst::FCMP_OLT:
- case FCmpInst::FCMP_ONE:
- case FCmpInst::FCMP_UEQ:
- case FCmpInst::FCMP_UGE:
- case FCmpInst::FCMP_ULE:
- // fcmp pred (x - y), 0 --> fcmp pred x, y
- if (match(RHSC, m_AnyZeroFP()) &&
- match(LHSI, m_OneUse(m_FSub(m_Value(X), m_Value(Y)))) &&
- I.getFunction()->getDenormalMode(
- LHSI->getType()->getScalarType()->getFltSemantics()) ==
- DenormalMode::getIEEE()) {
- replaceOperand(I, 0, X);
- replaceOperand(I, 1, Y);
- return &I;
- }
- break;
- }
+ if (LHSI->hasOneUse())
+ if (Instruction *NV = foldFCmpFSubIntoFCmp(I, LHSI, RHSC, *this))
+ return NV;
break;
case Instruction::PHI:
if (Instruction *NV = foldOpIntoPhi(I, cast<PHINode>(LHSI)))
>From 7b279699128ef99f877c10db3000fee49f5c62a0 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Wed, 12 Jun 2024 09:55:52 +0530
Subject: [PATCH 18/19] Fix minor Staylic issue
---
.../lib/Transforms/InstCombine/InstCombineCompares.cpp | 10 ++++++----
1 file changed, 6 insertions(+), 4 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 709a0a515741c..5f6945b03d9c9 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -7909,7 +7909,8 @@ static Instruction *foldFCmpFNegCommonOp(FCmpInst &I) {
static Instruction *foldFCmpFSubIntoFCmp(FCmpInst &I, Instruction *LHSI,
Constant *RHSC, InstCombinerImpl &CI) {
const CmpInst::Predicate Pred = I.getPredicate();
- Value *X, *Y;
+ Value *X = LHSI->getOperand(0);
+ Value *Y = LHSI->getOperand(1);
switch (Pred) {
default:
break;
@@ -7919,8 +7920,10 @@ static Instruction *foldFCmpFSubIntoFCmp(FCmpInst &I, Instruction *LHSI,
case FCmpInst::FCMP_OEQ:
case FCmpInst::FCMP_OGE:
case FCmpInst::FCMP_OLE:
- // Skip optimization: fsub x, y unless guaranteed !isinf(x) ||
- // !isinf(y).
+ // The optimization is not valid if X and Y are infinities of the same
+ // sign, i.e. the inf - inf = nan case. If the fsub has the ninf or nnan
+ // flag then we can assume we do not have that case. Otherwise we might be
+ // able to prove that either X or Y is not infinity.
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
!isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
CI.getSimplifyQuery().getWithInstruction(&I)) &&
@@ -7937,7 +7940,6 @@ static Instruction *foldFCmpFSubIntoFCmp(FCmpInst &I, Instruction *LHSI,
case FCmpInst::FCMP_ULE:
// fcmp pred (x - y), 0 --> fcmp pred x, y
if (match(RHSC, m_AnyZeroFP()) &&
- match(LHSI, m_FSub(m_Value(X), m_Value(Y))) &&
I.getFunction()->getDenormalMode(
LHSI->getType()->getScalarType()->getFltSemantics()) ==
DenormalMode::getIEEE()) {
>From f5b23fafd3607b296c04c5ed85304e713a7e8b65 Mon Sep 17 00:00:00 2001
From: SahilPatidar <patidarsahil2001 at gmail.com>
Date: Wed, 12 Jun 2024 14:18:21 +0530
Subject: [PATCH 19/19] replace LHSI->getOperand()
---
llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
index 5f6945b03d9c9..c7dfe78b2e013 100644
--- a/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
+++ b/llvm/lib/Transforms/InstCombine/InstCombineCompares.cpp
@@ -7925,9 +7925,9 @@ static Instruction *foldFCmpFSubIntoFCmp(FCmpInst &I, Instruction *LHSI,
// flag then we can assume we do not have that case. Otherwise we might be
// able to prove that either X or Y is not infinity.
if (!LHSI->hasNoNaNs() && !LHSI->hasNoInfs() &&
- !isKnownNeverInfinity(LHSI->getOperand(1), /*Depth=*/0,
+ !isKnownNeverInfinity(Y, /*Depth=*/0,
CI.getSimplifyQuery().getWithInstruction(&I)) &&
- !isKnownNeverInfinity(LHSI->getOperand(0), /*Depth=*/0,
+ !isKnownNeverInfinity(X, /*Depth=*/0,
CI.getSimplifyQuery().getWithInstruction(&I)))
break;
More information about the llvm-commits
mailing list