Skip to content

[RISCV][GISel] Remove s32 input support for G_SITOFP/UITOFP on RV64. #115236

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 5 commits into from
Nov 7, 2024

Conversation

topperc
Copy link
Collaborator

@topperc topperc commented Nov 6, 2024

I plan to make i32 an illegal type for RV64 to match SelectionDAG and to remove i32 from the GPR register class.

I've added a sexti32 ComplexPattern to select sext.w+fcvt.s.l as fcvt.s.w. The recently added zexti32 handles selecting and+fcvt.s.lu as fcvt.s.wu.

@llvmbot
Copy link
Member

llvmbot commented Nov 6, 2024

@llvm/pr-subscribers-backend-risc-v

Author: Craig Topper (topperc)

Changes

I plan to make i32 an illegal type for RV64 to match SelectionDAG and to remove i32 from the GPR register class.

I've added a sexti32 ComplexPattern to select sext.w+fcvt.s.l as fcvt.s.w. The recently added zexti32 handles selecting and+fcvt.s.lu as fcvt.s.wu.


Patch is 40.51 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/115236.diff

11 Files Affected:

  • (modified) llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp (+24)
  • (modified) llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp (+2-2)
  • (modified) llvm/lib/Target/RISCV/RISCVGISel.td (+3)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll (+64-28)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll (+64-28)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir (-46)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir (-92)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir (+26-31)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-rv64.mir (+52-62)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/regbankselect/itofp-f16-rv64.mir (-46)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/regbankselect/itofp-rv64.mir (-92)
diff --git a/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp b/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
index bc718b454ffb69..02ccd7e6bd48dd 100644
--- a/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
+++ b/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
@@ -87,6 +87,12 @@ class RISCVInstructionSelector : public InstructionSelector {
   ComplexRendererFns selectShiftMask(MachineOperand &Root) const;
   ComplexRendererFns selectAddrRegImm(MachineOperand &Root) const;
 
+  ComplexRendererFns selectSExtBits(MachineOperand &Root, unsigned Bits) const;
+  template <unsigned Bits>
+  ComplexRendererFns selectSExtBits(MachineOperand &Root) const {
+    return selectSExtBits(Root, Bits);
+  }
+
   ComplexRendererFns selectZExtBits(MachineOperand &Root, unsigned Bits) const;
   template <unsigned Bits>
   ComplexRendererFns selectZExtBits(MachineOperand &Root) const {
@@ -248,6 +254,24 @@ RISCVInstructionSelector::selectShiftMask(MachineOperand &Root) const {
   return {{[=](MachineInstrBuilder &MIB) { MIB.addReg(ShAmtReg); }}};
 }
 
+InstructionSelector::ComplexRendererFns
+RISCVInstructionSelector::selectSExtBits(MachineOperand &Root,
+                                         unsigned Bits) const {
+  if (!Root.isReg())
+    return std::nullopt;
+  MachineInstr *RootDef = MRI->getVRegDef(Root.getReg());
+
+  if (RootDef->getOpcode() == TargetOpcode::G_SEXT_INREG &&
+      RootDef->getOperand(2).getImm() == Bits) {
+    return {
+        {[=](MachineInstrBuilder &MIB) { MIB.add(RootDef->getOperand(1)); }}};
+  }
+
+  // TODO: Use computeNumSignBits.
+
+  return std::nullopt;
+}
+
 InstructionSelector::ComplexRendererFns
 RISCVInstructionSelector::selectZExtBits(MachineOperand &Root,
                                          unsigned Bits) const {
diff --git a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
index 34742394a291ed..3f8b09efc0c689 100644
--- a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
+++ b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
@@ -541,9 +541,9 @@ RISCVLegalizerInfo::RISCVLegalizerInfo(const RISCVSubtarget &ST)
       .libcallFor(ST.is64Bit(), {{s128, s32}, {s128, s64}});
 
   getActionDefinitionsBuilder({G_SITOFP, G_UITOFP})
-      .legalIf(all(typeIsScalarFPArith(0, ST), typeInSet(1, {s32, sXLen})))
+      .legalIf(all(typeIsScalarFPArith(0, ST), typeInSet(1, {sXLen})))
       .widenScalarToNextPow2(1)
-      .minScalar(1, s32)
+      .minScalar(1, sXLen)
       .libcallFor({{s32, s32}, {s64, s32}, {s32, s64}, {s64, s64}})
       .libcallFor(ST.is64Bit(), {{s32, s128}, {s64, s128}});
 
diff --git a/llvm/lib/Target/RISCV/RISCVGISel.td b/llvm/lib/Target/RISCV/RISCVGISel.td
index 36881b02da2e40..57ab55169e4a68 100644
--- a/llvm/lib/Target/RISCV/RISCVGISel.td
+++ b/llvm/lib/Target/RISCV/RISCVGISel.td
@@ -96,6 +96,9 @@ def gi_sh2add_uw_op : GIComplexOperandMatcher<s32, "selectSHXADD_UWOp<2>">,
 def gi_sh3add_uw_op : GIComplexOperandMatcher<s32, "selectSHXADD_UWOp<3>">,
                       GIComplexPatternEquiv<sh3add_uw_op>;
 
+def gi_sexti32 : GIComplexOperandMatcher<s64, "selectSExtBits<32>">,
+                 GIComplexPatternEquiv<sexti32>;
+
 def gi_zexti32 : GIComplexOperandMatcher<s64, "selectZExtBits<32>">,
                  GIComplexPatternEquiv<zexti32>;
 def gi_zexti16 : GIComplexOperandMatcher<s32, "selectZExtBits<16>">,
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll b/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
index 785cc2aafde11b..203b9c53de9d25 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
@@ -78,11 +78,17 @@ define double @fcvt_d_w(i32 %a) nounwind {
 }
 
 define double @fcvt_d_w_load(ptr %p) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_load:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    lw a0, 0(a0)
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_load:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    lw a0, 0(a0)
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_load:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    lw a0, 0(a0)
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %a = load i32, ptr %p
   %1 = sitofp i32 %a to double
   ret double %1
@@ -98,11 +104,19 @@ define double @fcvt_d_wu(i32 %a) nounwind {
 }
 
 define double @fcvt_d_wu_load(ptr %p) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_load:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    lw a0, 0(a0)
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_load:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    lw a0, 0(a0)
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_load:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    lw a0, 0(a0)
+; RV64IFD-NEXT:    slli a0, a0, 32
+; RV64IFD-NEXT:    srli a0, a0, 32
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %a = load i32, ptr %p
   %1 = uitofp i32 %a to double
   ret double %1
@@ -228,37 +242,57 @@ define double @fmv_d_x(i64 %a, i64 %b) nounwind {
 }
 
 define double @fcvt_d_w_i8(i8 signext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_i8:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_i8:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_i8:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = sitofp i8 %a to double
   ret double %1
 }
 
 define double @fcvt_d_wu_i8(i8 zeroext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_i8:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_i8:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_i8:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = uitofp i8 %a to double
   ret double %1
 }
 
 define double @fcvt_d_w_i16(i16 signext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_i16:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_i16:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_i16:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = sitofp i16 %a to double
   ret double %1
 }
 
 define double @fcvt_d_wu_i16(i16 zeroext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_i16:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_i16:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_i16:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = uitofp i16 %a to double
   ret double %1
 }
@@ -274,7 +308,7 @@ define signext i32 @fcvt_d_w_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IFD-LABEL: fcvt_d_w_demanded_bits:
 ; RV64IFD:       # %bb.0:
 ; RV64IFD-NEXT:    addiw a0, a0, 1
-; RV64IFD-NEXT:    fcvt.d.w fa5, a0
+; RV64IFD-NEXT:    fcvt.d.l fa5, a0
 ; RV64IFD-NEXT:    fsd fa5, 0(a1)
 ; RV64IFD-NEXT:    ret
   %3 = add i32 %0, 1
@@ -294,7 +328,9 @@ define signext i32 @fcvt_d_wu_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IFD-LABEL: fcvt_d_wu_demanded_bits:
 ; RV64IFD:       # %bb.0:
 ; RV64IFD-NEXT:    addiw a0, a0, 1
-; RV64IFD-NEXT:    fcvt.d.wu fa5, a0
+; RV64IFD-NEXT:    slli a2, a0, 32
+; RV64IFD-NEXT:    srli a2, a2, 32
+; RV64IFD-NEXT:    fcvt.d.lu fa5, a2
 ; RV64IFD-NEXT:    fsd fa5, 0(a1)
 ; RV64IFD-NEXT:    ret
   %3 = add i32 %0, 1
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll b/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
index d6a36c5a702ac8..5d0206359af385 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
@@ -81,11 +81,17 @@ define float @fcvt_s_w(i32 %a) nounwind {
 }
 
 define float @fcvt_s_w_load(ptr %p) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_load:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    lw a0, 0(a0)
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_load:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    lw a0, 0(a0)
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_load:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    lw a0, 0(a0)
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %a = load i32, ptr %p
   %1 = sitofp i32 %a to float
   ret float %1
@@ -101,11 +107,19 @@ define float @fcvt_s_wu(i32 %a) nounwind {
 }
 
 define float @fcvt_s_wu_load(ptr %p) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_load:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    lw a0, 0(a0)
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_load:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    lw a0, 0(a0)
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_load:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    lw a0, 0(a0)
+; RV64IF-NEXT:    slli a0, a0, 32
+; RV64IF-NEXT:    srli a0, a0, 32
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %a = load i32, ptr %p
   %1 = uitofp i32 %a to float
   ret float %1
@@ -198,37 +212,57 @@ define float @fcvt_s_lu(i64 %a) nounwind {
 }
 
 define float @fcvt_s_w_i8(i8 signext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_i8:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_i8:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_i8:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %1 = sitofp i8 %a to float
   ret float %1
 }
 
 define float @fcvt_s_wu_i8(i8 zeroext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_i8:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_i8:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_i8:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %1 = uitofp i8 %a to float
   ret float %1
 }
 
 define float @fcvt_s_w_i16(i16 signext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_i16:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_i16:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_i16:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %1 = sitofp i16 %a to float
   ret float %1
 }
 
 define float @fcvt_s_wu_i16(i16 zeroext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_i16:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_i16:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_i16:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %1 = uitofp i16 %a to float
   ret float %1
 }
@@ -245,7 +279,7 @@ define signext i32 @fcvt_s_w_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IF-LABEL: fcvt_s_w_demanded_bits:
 ; RV64IF:       # %bb.0:
 ; RV64IF-NEXT:    addiw a0, a0, 1
-; RV64IF-NEXT:    fcvt.s.w fa5, a0
+; RV64IF-NEXT:    fcvt.s.l fa5, a0
 ; RV64IF-NEXT:    fsw fa5, 0(a1)
 ; RV64IF-NEXT:    ret
   %3 = add i32 %0, 1
@@ -266,7 +300,9 @@ define signext i32 @fcvt_s_wu_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IF-LABEL: fcvt_s_wu_demanded_bits:
 ; RV64IF:       # %bb.0:
 ; RV64IF-NEXT:    addiw a0, a0, 1
-; RV64IF-NEXT:    fcvt.s.wu fa5, a0
+; RV64IF-NEXT:    slli a2, a0, 32
+; RV64IF-NEXT:    srli a2, a2, 32
+; RV64IF-NEXT:    fcvt.s.lu fa5, a2
 ; RV64IF-NEXT:    fsw fa5, 0(a1)
 ; RV64IF-NEXT:    ret
   %3 = add i32 %0, 1
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
index 1afb1d9be6a099..b813a79c339ec5 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
@@ -2,52 +2,6 @@
 # RUN: llc -mtriple=riscv64 -mattr=+zfh -run-pass=instruction-select \
 # RUN:   -simplify-mir -verify-machineinstrs %s -o - | FileCheck %s
 
----
-name:            sitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_H_W:%[0-9]+]]:fpr16 = nofpexcept FCVT_H_W [[COPY]], 7
-    ; CHECK-NEXT: $f10_h = COPY [[FCVT_H_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_h
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s16) = G_SITOFP %1(s32)
-    $f10_h = COPY %2(s16)
-    PseudoRET implicit $f10_h
-
-...
----
-name:            uitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_H_WU:%[0-9]+]]:fpr16 = nofpexcept FCVT_H_WU [[COPY]], 7
-    ; CHECK-NEXT: $f10_h = COPY [[FCVT_H_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_h
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s16) = G_UITOFP %1(s32)
-    $f10_h = COPY %2(s16)
-    PseudoRET implicit $f10_h
-
-...
 ---
 name:            sitofp_s64_s64
 legalized:       true
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
index 31175d7af93f98..f99a15a850517f 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
@@ -2,52 +2,6 @@
 # RUN: llc -mtriple=riscv64 -mattr=+d -run-pass=instruction-select \
 # RUN:   -simplify-mir -verify-machineinstrs %s -o - | FileCheck %s
 
----
-name:            sitofp_s32_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s32_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_S_W:%[0-9]+]]:fpr32 = nofpexcept FCVT_S_W [[COPY]], 7
-    ; CHECK-NEXT: $f10_f = COPY [[FCVT_S_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_f
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s32) = G_SITOFP %1(s32)
-    $f10_f = COPY %2(s32)
-    PseudoRET implicit $f10_f
-
-...
----
-name:            uitofp_s32_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s32_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_S_WU:%[0-9]+]]:fpr32 = nofpexcept FCVT_S_WU [[COPY]], 7
-    ; CHECK-NEXT: $f10_f = COPY [[FCVT_S_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_f
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s32) = G_UITOFP %1(s32)
-    $f10_f = COPY %2(s32)
-    PseudoRET implicit $f10_f
-
-...
 ---
 name:            sitofp_s32_s64
 legalized:       true
@@ -91,52 +45,6 @@ body:             |
     $f10_f = COPY %1(s32)
     PseudoRET implicit $f10_f
 
-...
----
-name:            sitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_D_W:%[0-9]+]]:fpr64 = nofpexcept FCVT_D_W [[COPY]], 0
-    ; CHECK-NEXT: $f10_d = COPY [[FCVT_D_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_d
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s64) = G_SITOFP %1(s32)
-    $f10_d = COPY %2(s64)
-    PseudoRET implicit $f10_d
-
-...
----
-name:            uitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_D_WU:%[0-9]+]]:fpr64 = nofpexcept FCVT_D_WU [[COPY]], 0
-    ; CHECK-NEXT: $f10_d = COPY [[FCVT_D_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_d
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s64) = G_UITOFP %1(s32)
-    $f10_d = COPY %2(s64)
-    PseudoRET implicit $f10_d
-
 ...
 ---
 name:            sitofp_s64_s64
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
index 52c69d1acbffc7..6a70a331a02c8c 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
@@ -13,11 +13,10 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 31
-    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s32) = G_SHL [[TRUNC]], [[C]](s32)
-    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[SHL]], [[C]](s32)
-    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 63
+    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s64) = G_SHL [[COPY]], [[C]](s64)
+    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s64) = G_ASHR [[SHL]], [[C]](s64)
+    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[SITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -38,10 +37,9 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1
-    ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[TRUNC]], [[C]]
-    ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(s16) = G_UITOFP [[AND]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 1
+    ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s64) = G_AND [[COPY]], [[C]]
+    ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(s16) = G_UITOFP [[AND]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[UITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -62,11 +60,10 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 24
-    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s32) = G_SHL [[TRUNC]], [[C]](s32)
-    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[SHL]], [[C]](s32)
-    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 56
+    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s64) = G_SHL [[COPY]], [[C]](s64)
+    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s64) = G_ASHR [[SHL]], [[C]](s64)
+    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[SITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -87,10 +84,9 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)...
[truncated]

@llvmbot
Copy link
Member

llvmbot commented Nov 6, 2024

@llvm/pr-subscribers-llvm-globalisel

Author: Craig Topper (topperc)

Changes

I plan to make i32 an illegal type for RV64 to match SelectionDAG and to remove i32 from the GPR register class.

I've added a sexti32 ComplexPattern to select sext.w+fcvt.s.l as fcvt.s.w. The recently added zexti32 handles selecting and+fcvt.s.lu as fcvt.s.wu.


Patch is 40.51 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/115236.diff

11 Files Affected:

  • (modified) llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp (+24)
  • (modified) llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp (+2-2)
  • (modified) llvm/lib/Target/RISCV/RISCVGISel.td (+3)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll (+64-28)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll (+64-28)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir (-46)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir (-92)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir (+26-31)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-rv64.mir (+52-62)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/regbankselect/itofp-f16-rv64.mir (-46)
  • (modified) llvm/test/CodeGen/RISCV/GlobalISel/regbankselect/itofp-rv64.mir (-92)
diff --git a/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp b/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
index bc718b454ffb69..02ccd7e6bd48dd 100644
--- a/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
+++ b/llvm/lib/Target/RISCV/GISel/RISCVInstructionSelector.cpp
@@ -87,6 +87,12 @@ class RISCVInstructionSelector : public InstructionSelector {
   ComplexRendererFns selectShiftMask(MachineOperand &Root) const;
   ComplexRendererFns selectAddrRegImm(MachineOperand &Root) const;
 
+  ComplexRendererFns selectSExtBits(MachineOperand &Root, unsigned Bits) const;
+  template <unsigned Bits>
+  ComplexRendererFns selectSExtBits(MachineOperand &Root) const {
+    return selectSExtBits(Root, Bits);
+  }
+
   ComplexRendererFns selectZExtBits(MachineOperand &Root, unsigned Bits) const;
   template <unsigned Bits>
   ComplexRendererFns selectZExtBits(MachineOperand &Root) const {
@@ -248,6 +254,24 @@ RISCVInstructionSelector::selectShiftMask(MachineOperand &Root) const {
   return {{[=](MachineInstrBuilder &MIB) { MIB.addReg(ShAmtReg); }}};
 }
 
+InstructionSelector::ComplexRendererFns
+RISCVInstructionSelector::selectSExtBits(MachineOperand &Root,
+                                         unsigned Bits) const {
+  if (!Root.isReg())
+    return std::nullopt;
+  MachineInstr *RootDef = MRI->getVRegDef(Root.getReg());
+
+  if (RootDef->getOpcode() == TargetOpcode::G_SEXT_INREG &&
+      RootDef->getOperand(2).getImm() == Bits) {
+    return {
+        {[=](MachineInstrBuilder &MIB) { MIB.add(RootDef->getOperand(1)); }}};
+  }
+
+  // TODO: Use computeNumSignBits.
+
+  return std::nullopt;
+}
+
 InstructionSelector::ComplexRendererFns
 RISCVInstructionSelector::selectZExtBits(MachineOperand &Root,
                                          unsigned Bits) const {
diff --git a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
index 34742394a291ed..3f8b09efc0c689 100644
--- a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
+++ b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
@@ -541,9 +541,9 @@ RISCVLegalizerInfo::RISCVLegalizerInfo(const RISCVSubtarget &ST)
       .libcallFor(ST.is64Bit(), {{s128, s32}, {s128, s64}});
 
   getActionDefinitionsBuilder({G_SITOFP, G_UITOFP})
-      .legalIf(all(typeIsScalarFPArith(0, ST), typeInSet(1, {s32, sXLen})))
+      .legalIf(all(typeIsScalarFPArith(0, ST), typeInSet(1, {sXLen})))
       .widenScalarToNextPow2(1)
-      .minScalar(1, s32)
+      .minScalar(1, sXLen)
       .libcallFor({{s32, s32}, {s64, s32}, {s32, s64}, {s64, s64}})
       .libcallFor(ST.is64Bit(), {{s32, s128}, {s64, s128}});
 
diff --git a/llvm/lib/Target/RISCV/RISCVGISel.td b/llvm/lib/Target/RISCV/RISCVGISel.td
index 36881b02da2e40..57ab55169e4a68 100644
--- a/llvm/lib/Target/RISCV/RISCVGISel.td
+++ b/llvm/lib/Target/RISCV/RISCVGISel.td
@@ -96,6 +96,9 @@ def gi_sh2add_uw_op : GIComplexOperandMatcher<s32, "selectSHXADD_UWOp<2>">,
 def gi_sh3add_uw_op : GIComplexOperandMatcher<s32, "selectSHXADD_UWOp<3>">,
                       GIComplexPatternEquiv<sh3add_uw_op>;
 
+def gi_sexti32 : GIComplexOperandMatcher<s64, "selectSExtBits<32>">,
+                 GIComplexPatternEquiv<sexti32>;
+
 def gi_zexti32 : GIComplexOperandMatcher<s64, "selectZExtBits<32>">,
                  GIComplexPatternEquiv<zexti32>;
 def gi_zexti16 : GIComplexOperandMatcher<s32, "selectZExtBits<16>">,
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll b/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
index 785cc2aafde11b..203b9c53de9d25 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/double-convert.ll
@@ -78,11 +78,17 @@ define double @fcvt_d_w(i32 %a) nounwind {
 }
 
 define double @fcvt_d_w_load(ptr %p) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_load:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    lw a0, 0(a0)
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_load:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    lw a0, 0(a0)
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_load:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    lw a0, 0(a0)
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %a = load i32, ptr %p
   %1 = sitofp i32 %a to double
   ret double %1
@@ -98,11 +104,19 @@ define double @fcvt_d_wu(i32 %a) nounwind {
 }
 
 define double @fcvt_d_wu_load(ptr %p) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_load:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    lw a0, 0(a0)
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_load:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    lw a0, 0(a0)
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_load:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    lw a0, 0(a0)
+; RV64IFD-NEXT:    slli a0, a0, 32
+; RV64IFD-NEXT:    srli a0, a0, 32
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %a = load i32, ptr %p
   %1 = uitofp i32 %a to double
   ret double %1
@@ -228,37 +242,57 @@ define double @fmv_d_x(i64 %a, i64 %b) nounwind {
 }
 
 define double @fcvt_d_w_i8(i8 signext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_i8:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_i8:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_i8:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = sitofp i8 %a to double
   ret double %1
 }
 
 define double @fcvt_d_wu_i8(i8 zeroext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_i8:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_i8:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_i8:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = uitofp i8 %a to double
   ret double %1
 }
 
 define double @fcvt_d_w_i16(i16 signext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_w_i16:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.w fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_w_i16:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.w fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_w_i16:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.l fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = sitofp i16 %a to double
   ret double %1
 }
 
 define double @fcvt_d_wu_i16(i16 zeroext %a) nounwind {
-; CHECKIFD-LABEL: fcvt_d_wu_i16:
-; CHECKIFD:       # %bb.0:
-; CHECKIFD-NEXT:    fcvt.d.wu fa0, a0
-; CHECKIFD-NEXT:    ret
+; RV32IFD-LABEL: fcvt_d_wu_i16:
+; RV32IFD:       # %bb.0:
+; RV32IFD-NEXT:    fcvt.d.wu fa0, a0
+; RV32IFD-NEXT:    ret
+;
+; RV64IFD-LABEL: fcvt_d_wu_i16:
+; RV64IFD:       # %bb.0:
+; RV64IFD-NEXT:    fcvt.d.lu fa0, a0
+; RV64IFD-NEXT:    ret
   %1 = uitofp i16 %a to double
   ret double %1
 }
@@ -274,7 +308,7 @@ define signext i32 @fcvt_d_w_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IFD-LABEL: fcvt_d_w_demanded_bits:
 ; RV64IFD:       # %bb.0:
 ; RV64IFD-NEXT:    addiw a0, a0, 1
-; RV64IFD-NEXT:    fcvt.d.w fa5, a0
+; RV64IFD-NEXT:    fcvt.d.l fa5, a0
 ; RV64IFD-NEXT:    fsd fa5, 0(a1)
 ; RV64IFD-NEXT:    ret
   %3 = add i32 %0, 1
@@ -294,7 +328,9 @@ define signext i32 @fcvt_d_wu_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IFD-LABEL: fcvt_d_wu_demanded_bits:
 ; RV64IFD:       # %bb.0:
 ; RV64IFD-NEXT:    addiw a0, a0, 1
-; RV64IFD-NEXT:    fcvt.d.wu fa5, a0
+; RV64IFD-NEXT:    slli a2, a0, 32
+; RV64IFD-NEXT:    srli a2, a2, 32
+; RV64IFD-NEXT:    fcvt.d.lu fa5, a2
 ; RV64IFD-NEXT:    fsd fa5, 0(a1)
 ; RV64IFD-NEXT:    ret
   %3 = add i32 %0, 1
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll b/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
index d6a36c5a702ac8..5d0206359af385 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/float-convert.ll
@@ -81,11 +81,17 @@ define float @fcvt_s_w(i32 %a) nounwind {
 }
 
 define float @fcvt_s_w_load(ptr %p) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_load:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    lw a0, 0(a0)
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_load:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    lw a0, 0(a0)
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_load:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    lw a0, 0(a0)
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %a = load i32, ptr %p
   %1 = sitofp i32 %a to float
   ret float %1
@@ -101,11 +107,19 @@ define float @fcvt_s_wu(i32 %a) nounwind {
 }
 
 define float @fcvt_s_wu_load(ptr %p) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_load:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    lw a0, 0(a0)
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_load:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    lw a0, 0(a0)
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_load:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    lw a0, 0(a0)
+; RV64IF-NEXT:    slli a0, a0, 32
+; RV64IF-NEXT:    srli a0, a0, 32
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %a = load i32, ptr %p
   %1 = uitofp i32 %a to float
   ret float %1
@@ -198,37 +212,57 @@ define float @fcvt_s_lu(i64 %a) nounwind {
 }
 
 define float @fcvt_s_w_i8(i8 signext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_i8:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_i8:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_i8:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %1 = sitofp i8 %a to float
   ret float %1
 }
 
 define float @fcvt_s_wu_i8(i8 zeroext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_i8:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_i8:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_i8:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %1 = uitofp i8 %a to float
   ret float %1
 }
 
 define float @fcvt_s_w_i16(i16 signext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_w_i16:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.w fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_w_i16:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.w fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_w_i16:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.l fa0, a0
+; RV64IF-NEXT:    ret
   %1 = sitofp i16 %a to float
   ret float %1
 }
 
 define float @fcvt_s_wu_i16(i16 zeroext %a) nounwind {
-; CHECKIF-LABEL: fcvt_s_wu_i16:
-; CHECKIF:       # %bb.0:
-; CHECKIF-NEXT:    fcvt.s.wu fa0, a0
-; CHECKIF-NEXT:    ret
+; RV32IF-LABEL: fcvt_s_wu_i16:
+; RV32IF:       # %bb.0:
+; RV32IF-NEXT:    fcvt.s.wu fa0, a0
+; RV32IF-NEXT:    ret
+;
+; RV64IF-LABEL: fcvt_s_wu_i16:
+; RV64IF:       # %bb.0:
+; RV64IF-NEXT:    fcvt.s.lu fa0, a0
+; RV64IF-NEXT:    ret
   %1 = uitofp i16 %a to float
   ret float %1
 }
@@ -245,7 +279,7 @@ define signext i32 @fcvt_s_w_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IF-LABEL: fcvt_s_w_demanded_bits:
 ; RV64IF:       # %bb.0:
 ; RV64IF-NEXT:    addiw a0, a0, 1
-; RV64IF-NEXT:    fcvt.s.w fa5, a0
+; RV64IF-NEXT:    fcvt.s.l fa5, a0
 ; RV64IF-NEXT:    fsw fa5, 0(a1)
 ; RV64IF-NEXT:    ret
   %3 = add i32 %0, 1
@@ -266,7 +300,9 @@ define signext i32 @fcvt_s_wu_demanded_bits(i32 signext %0, ptr %1) nounwind {
 ; RV64IF-LABEL: fcvt_s_wu_demanded_bits:
 ; RV64IF:       # %bb.0:
 ; RV64IF-NEXT:    addiw a0, a0, 1
-; RV64IF-NEXT:    fcvt.s.wu fa5, a0
+; RV64IF-NEXT:    slli a2, a0, 32
+; RV64IF-NEXT:    srli a2, a2, 32
+; RV64IF-NEXT:    fcvt.s.lu fa5, a2
 ; RV64IF-NEXT:    fsw fa5, 0(a1)
 ; RV64IF-NEXT:    ret
   %3 = add i32 %0, 1
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
index 1afb1d9be6a099..b813a79c339ec5 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-f16-rv64.mir
@@ -2,52 +2,6 @@
 # RUN: llc -mtriple=riscv64 -mattr=+zfh -run-pass=instruction-select \
 # RUN:   -simplify-mir -verify-machineinstrs %s -o - | FileCheck %s
 
----
-name:            sitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_H_W:%[0-9]+]]:fpr16 = nofpexcept FCVT_H_W [[COPY]], 7
-    ; CHECK-NEXT: $f10_h = COPY [[FCVT_H_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_h
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s16) = G_SITOFP %1(s32)
-    $f10_h = COPY %2(s16)
-    PseudoRET implicit $f10_h
-
-...
----
-name:            uitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_H_WU:%[0-9]+]]:fpr16 = nofpexcept FCVT_H_WU [[COPY]], 7
-    ; CHECK-NEXT: $f10_h = COPY [[FCVT_H_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_h
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s16) = G_UITOFP %1(s32)
-    $f10_h = COPY %2(s16)
-    PseudoRET implicit $f10_h
-
-...
 ---
 name:            sitofp_s64_s64
 legalized:       true
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
index 31175d7af93f98..f99a15a850517f 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/instruction-select/itofp-rv64.mir
@@ -2,52 +2,6 @@
 # RUN: llc -mtriple=riscv64 -mattr=+d -run-pass=instruction-select \
 # RUN:   -simplify-mir -verify-machineinstrs %s -o - | FileCheck %s
 
----
-name:            sitofp_s32_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s32_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_S_W:%[0-9]+]]:fpr32 = nofpexcept FCVT_S_W [[COPY]], 7
-    ; CHECK-NEXT: $f10_f = COPY [[FCVT_S_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_f
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s32) = G_SITOFP %1(s32)
-    $f10_f = COPY %2(s32)
-    PseudoRET implicit $f10_f
-
-...
----
-name:            uitofp_s32_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s32_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_S_WU:%[0-9]+]]:fpr32 = nofpexcept FCVT_S_WU [[COPY]], 7
-    ; CHECK-NEXT: $f10_f = COPY [[FCVT_S_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_f
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s32) = G_UITOFP %1(s32)
-    $f10_f = COPY %2(s32)
-    PseudoRET implicit $f10_f
-
-...
 ---
 name:            sitofp_s32_s64
 legalized:       true
@@ -91,52 +45,6 @@ body:             |
     $f10_f = COPY %1(s32)
     PseudoRET implicit $f10_f
 
-...
----
-name:            sitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: sitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_D_W:%[0-9]+]]:fpr64 = nofpexcept FCVT_D_W [[COPY]], 0
-    ; CHECK-NEXT: $f10_d = COPY [[FCVT_D_W]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_d
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s64) = G_SITOFP %1(s32)
-    $f10_d = COPY %2(s64)
-    PseudoRET implicit $f10_d
-
-...
----
-name:            uitofp_s64_s32
-legalized:       true
-regBankSelected: true
-tracksRegLiveness: true
-body:             |
-  bb.0:
-    liveins: $x10
-
-    ; CHECK-LABEL: name: uitofp_s64_s32
-    ; CHECK: liveins: $x10
-    ; CHECK-NEXT: {{  $}}
-    ; CHECK-NEXT: [[COPY:%[0-9]+]]:gpr = COPY $x10
-    ; CHECK-NEXT: [[FCVT_D_WU:%[0-9]+]]:fpr64 = nofpexcept FCVT_D_WU [[COPY]], 0
-    ; CHECK-NEXT: $f10_d = COPY [[FCVT_D_WU]]
-    ; CHECK-NEXT: PseudoRET implicit $f10_d
-    %0:gprb(s64) = COPY $x10
-    %1:gprb(s32) = G_TRUNC %0(s64)
-    %2:fprb(s64) = G_UITOFP %1(s32)
-    $f10_d = COPY %2(s64)
-    PseudoRET implicit $f10_d
-
 ...
 ---
 name:            sitofp_s64_s64
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir b/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
index 52c69d1acbffc7..6a70a331a02c8c 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-itofp-f16-rv64.mir
@@ -13,11 +13,10 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 31
-    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s32) = G_SHL [[TRUNC]], [[C]](s32)
-    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[SHL]], [[C]](s32)
-    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 63
+    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s64) = G_SHL [[COPY]], [[C]](s64)
+    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s64) = G_ASHR [[SHL]], [[C]](s64)
+    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[SITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -38,10 +37,9 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 1
-    ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s32) = G_AND [[TRUNC]], [[C]]
-    ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(s16) = G_UITOFP [[AND]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 1
+    ; CHECK-NEXT: [[AND:%[0-9]+]]:_(s64) = G_AND [[COPY]], [[C]]
+    ; CHECK-NEXT: [[UITOFP:%[0-9]+]]:_(s16) = G_UITOFP [[AND]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[UITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -62,11 +60,10 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)
-    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 24
-    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s32) = G_SHL [[TRUNC]], [[C]](s32)
-    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[SHL]], [[C]](s32)
-    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s32)
+    ; CHECK-NEXT: [[C:%[0-9]+]]:_(s64) = G_CONSTANT i64 56
+    ; CHECK-NEXT: [[SHL:%[0-9]+]]:_(s64) = G_SHL [[COPY]], [[C]](s64)
+    ; CHECK-NEXT: [[ASHR:%[0-9]+]]:_(s64) = G_ASHR [[SHL]], [[C]](s64)
+    ; CHECK-NEXT: [[SITOFP:%[0-9]+]]:_(s16) = G_SITOFP [[ASHR]](s64)
     ; CHECK-NEXT: $f10_h = COPY [[SITOFP]](s16)
     ; CHECK-NEXT: PseudoRET implicit $f10_h
     %1:_(s64) = COPY $x10
@@ -87,10 +84,9 @@ body:             |
     ; CHECK: liveins: $x10
     ; CHECK-NEXT: {{  $}}
     ; CHECK-NEXT: [[COPY:%[0-9]+]]:_(s64) = COPY $x10
-    ; CHECK-NEXT: [[TRUNC:%[0-9]+]]:_(s32) = G_TRUNC [[COPY]](s64)...
[truncated]

Copy link
Member

@mshockwave mshockwave left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@topperc topperc merged commit ae9d062 into llvm:main Nov 7, 2024
5 of 7 checks passed
@topperc topperc deleted the pr/gisel-itofp branch November 7, 2024 21:57
Groverkss pushed a commit to iree-org/llvm-project that referenced this pull request Nov 15, 2024
…lvm#115236)

I plan to make i32 an illegal type for RV64 to match SelectionDAG and to
remove i32 from the GPR register class.

I've added a sexti32 ComplexPattern to select sext.w+fcvt.s.l as
fcvt.s.w. The recently added zexti32 handles selecting and+fcvt.s.lu as
fcvt.s.wu. There are still some regressions that suggest we should match
g_zero_extend in zexti32.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants