[llvm] [DAG] Fixing the non-optimal code with the following: `select i1 %0, float 1.0, float 0.0`. (PR #107732)

via llvm-commits llvm-commits at lists.llvm.org
Sat Sep 7 18:55:57 PDT 2024


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-backend-x86

Author: None (c8ef)

<details>
<summary>Changes</summary>

Fixes #<!-- -->107034.

---
Full diff: https://github.com/llvm/llvm-project/pull/107732.diff


2 Files Affected:

- (modified) llvm/lib/Target/X86/X86ISelLowering.cpp (+25) 
- (modified) llvm/test/CodeGen/X86/fp-select-cmp-and.ll (+19) 


``````````diff
diff --git a/llvm/lib/Target/X86/X86ISelLowering.cpp b/llvm/lib/Target/X86/X86ISelLowering.cpp
index 839b87dd5d4dd8..e40e28bacd4f66 100644
--- a/llvm/lib/Target/X86/X86ISelLowering.cpp
+++ b/llvm/lib/Target/X86/X86ISelLowering.cpp
@@ -45844,6 +45844,28 @@ static SDValue combineSelectOfTwoConstants(SDNode *N, SelectionDAG &DAG,
   return SDValue();
 }
 
+static SDValue combineSelectOfTwoFPConstants(SDNode *N, SelectionDAG &DAG,
+                                             const SDLoc &DL) {
+  SDValue Cond = N->getOperand(0);
+  SDValue LHS = N->getOperand(1);
+  SDValue RHS = N->getOperand(2);
+  EVT VT = N->getValueType(0);
+
+  auto *TrueC = dyn_cast<ConstantFPSDNode>(LHS);
+  auto *FalseC = dyn_cast<ConstantFPSDNode>(RHS);
+  if (!TrueC || !FalseC)
+    return SDValue();
+
+  const APFloat &TrueVal = TrueC->getValueAPF();
+  const APFloat &FalseVal = FalseC->getValueAPF();
+
+  if (TrueVal == APFloat::getOne(TrueVal.getSemantics()) && FalseVal.isZero()) {
+    return DAG.getNode(ISD::UINT_TO_FP, DL, VT, Cond);
+  }
+
+  return SDValue();
+}
+
 /// If this is a *dynamic* select (non-constant condition) and we can match
 /// this node with one of the variable blend instructions, restructure the
 /// condition so that blends can use the high (sign) bit of each element.
@@ -46336,6 +46358,9 @@ static SDValue combineSelect(SDNode *N, SelectionDAG &DAG,
   if (SDValue V = combineSelectOfTwoConstants(N, DAG, DL))
     return V;
 
+  if (SDValue V = combineSelectOfTwoFPConstants(N, DAG, DL))
+    return V;
+
   if (N->getOpcode() == ISD::SELECT && Cond.getOpcode() == ISD::SETCC &&
       Cond.hasOneUse()) {
     EVT CondVT = Cond.getValueType();
diff --git a/llvm/test/CodeGen/X86/fp-select-cmp-and.ll b/llvm/test/CodeGen/X86/fp-select-cmp-and.ll
index 0f6159d36ea818..64e6c410742754 100644
--- a/llvm/test/CodeGen/X86/fp-select-cmp-and.ll
+++ b/llvm/test/CodeGen/X86/fp-select-cmp-and.ll
@@ -213,3 +213,22 @@ define double @test18(double %a, double %b, double %c, double %eps) {
   ret double %cond
 }
 
+define float @test19(i1 %cmp) {
+; CHECK-LABEL: test19:
+; CHECK:       # %bb.0:
+; CHECK-NEXT:    andl $1, %edi
+; CHECK-NEXT:    cvtsi2ss %edi, %xmm0
+; CHECK-NEXT:    retq
+  %cond = select i1 %cmp, float 1.000000e+00, float 0.000000e+00
+  ret float %cond
+}
+
+define double @test20(i1 %cmp) {
+; CHECK-LABEL: test20:
+; CHECK:       # %bb.0:
+; CHECK-NEXT:    andl $1, %edi
+; CHECK-NEXT:    cvtsi2sd %edi, %xmm0
+; CHECK-NEXT:    retq
+  %cond = select i1 %cmp, double 1.000000e+00, double 0.000000e+00
+  ret double %cond
+}

``````````

</details>


https://github.com/llvm/llvm-project/pull/107732


More information about the llvm-commits mailing list