[llvm] [RISCV] Use Zfhmin for G_FPEXT from f16 to f32 (PR #227225)
via llvm-commits
llvm-commits at lists.llvm.org
Tue Sep 29 02:01:59 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-llvm-globalisel
Author: Kane Wang (ReVe1uv)
<details>
<summary>Changes</summary>
fcvt.s.h is available with Zfhmin. Use the __extendhfsf2 libcall without it.
---
Full diff: https://github.com/llvm/llvm-project/pull/227225.diff
2 Files Affected:
- (modified) llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp (+2-1)
- (modified) llvm/test/CodeGen/RISCV/GlobalISel/half-convert.ll (+82)
``````````diff
diff --git a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
index ff62ee25236f2..9566310bd9693 100644
--- a/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
+++ b/llvm/lib/Target/RISCV/GISel/RISCVLegalizerInfo.cpp
@@ -605,8 +605,9 @@ RISCVLegalizerInfo::RISCVLegalizerInfo(const RISCVSubtarget &ST)
.libcallFor(ST.is64Bit(), {{s32, s128}, {s64, s128}});
getActionDefinitionsBuilder(G_FPEXT)
.legalFor(ST.hasStdExtD(), {{s64, s32}})
- .legalFor(ST.hasStdExtZfh(), {{s32, s16}})
+ .legalFor(ST.hasStdExtZfhmin(), {{s32, s16}})
.legalFor(ST.hasStdExtZfh() && ST.hasStdExtD(), {{s64, s16}})
+ .libcallFor(!ST.hasStdExtZfhmin(), {{s32, s16}})
.libcallFor({{s64, s32}})
.libcallFor(ST.is64Bit(), {{s128, s32}, {s128, s64}});
diff --git a/llvm/test/CodeGen/RISCV/GlobalISel/half-convert.ll b/llvm/test/CodeGen/RISCV/GlobalISel/half-convert.ll
index 3338be0aad09d..36e840df39f23 100644
--- a/llvm/test/CodeGen/RISCV/GlobalISel/half-convert.ll
+++ b/llvm/test/CodeGen/RISCV/GlobalISel/half-convert.ll
@@ -3,6 +3,10 @@
; RUN: -target-abi=ilp32d < %s | FileCheck %s --check-prefixes=RV32
; RUN: llc -mtriple=riscv64 -global-isel -mattr=+f,+d,+zfh \
; RUN: -target-abi=lp64d < %s | FileCheck %s --check-prefixes=RV64
+; RUN: llc -mtriple=riscv32 -global-isel -mattr=+f,+d,+zfhmin \
+; RUN: -target-abi=ilp32d < %s | FileCheck %s --check-prefixes=RV32ZFHMIN
+; RUN: llc -mtriple=riscv64 -global-isel -mattr=+f,+d,+zfhmin \
+; RUN: -target-abi=lp64d < %s | FileCheck %s --check-prefixes=RV64ZFHMIN
; RUN: llc -mtriple=riscv32 -global-isel -mattr=+f,+d \
; RUN: -target-abi=ilp32d < %s | FileCheck %s --check-prefixes=RV32NOZFH
; RUN: llc -mtriple=riscv64 -global-isel -mattr=+f,+d \
@@ -20,6 +24,24 @@ define i64 @fptoui_i64_f16(half %x) nounwind {
; RV64-NEXT: fcvt.lu.h a0, fa0, rtz
; RV64-NEXT: ret
;
+; RV32ZFHMIN-LABEL: fptoui_i64_f16:
+; RV32ZFHMIN: # %bb.0:
+; RV32ZFHMIN-NEXT: addi sp, sp, -16
+; RV32ZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill
+; RV32ZFHMIN-NEXT: call __fixunshfdi
+; RV32ZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload
+; RV32ZFHMIN-NEXT: addi sp, sp, 16
+; RV32ZFHMIN-NEXT: ret
+;
+; RV64ZFHMIN-LABEL: fptoui_i64_f16:
+; RV64ZFHMIN: # %bb.0:
+; RV64ZFHMIN-NEXT: addi sp, sp, -16
+; RV64ZFHMIN-NEXT: sd ra, 8(sp) # 8-byte Folded Spill
+; RV64ZFHMIN-NEXT: call __fixunshfdi
+; RV64ZFHMIN-NEXT: ld ra, 8(sp) # 8-byte Folded Reload
+; RV64ZFHMIN-NEXT: addi sp, sp, 16
+; RV64ZFHMIN-NEXT: ret
+;
; RV32NOZFH-LABEL: fptoui_i64_f16:
; RV32NOZFH: # %bb.0:
; RV32NOZFH-NEXT: addi sp, sp, -16
@@ -53,6 +75,24 @@ define i64 @fptosi_i64_f16(half %x) nounwind {
; RV64-NEXT: fcvt.l.h a0, fa0, rtz
; RV64-NEXT: ret
;
+; RV32ZFHMIN-LABEL: fptosi_i64_f16:
+; RV32ZFHMIN: # %bb.0:
+; RV32ZFHMIN-NEXT: addi sp, sp, -16
+; RV32ZFHMIN-NEXT: sw ra, 12(sp) # 4-byte Folded Spill
+; RV32ZFHMIN-NEXT: call __fixhfdi
+; RV32ZFHMIN-NEXT: lw ra, 12(sp) # 4-byte Folded Reload
+; RV32ZFHMIN-NEXT: addi sp, sp, 16
+; RV32ZFHMIN-NEXT: ret
+;
+; RV64ZFHMIN-LABEL: fptosi_i64_f16:
+; RV64ZFHMIN: # %bb.0:
+; RV64ZFHMIN-NEXT: addi sp, sp, -16
+; RV64ZFHMIN-NEXT: sd ra, 8(sp) # 8-byte Folded Spill
+; RV64ZFHMIN-NEXT: call __fixhfdi
+; RV64ZFHMIN-NEXT: ld ra, 8(sp) # 8-byte Folded Reload
+; RV64ZFHMIN-NEXT: addi sp, sp, 16
+; RV64ZFHMIN-NEXT: ret
+;
; RV32NOZFH-LABEL: fptosi_i64_f16:
; RV32NOZFH: # %bb.0:
; RV32NOZFH-NEXT: addi sp, sp, -16
@@ -73,3 +113,45 @@ define i64 @fptosi_i64_f16(half %x) nounwind {
%a = fptosi half %x to i64
ret i64 %a
}
+
+define float @fpext_f16_to_f32(half %x) nounwind {
+; RV32-LABEL: fpext_f16_to_f32:
+; RV32: # %bb.0:
+; RV32-NEXT: fcvt.s.h fa0, fa0
+; RV32-NEXT: ret
+;
+; RV64-LABEL: fpext_f16_to_f32:
+; RV64: # %bb.0:
+; RV64-NEXT: fcvt.s.h fa0, fa0
+; RV64-NEXT: ret
+;
+; RV32ZFHMIN-LABEL: fpext_f16_to_f32:
+; RV32ZFHMIN: # %bb.0:
+; RV32ZFHMIN-NEXT: fcvt.s.h fa0, fa0
+; RV32ZFHMIN-NEXT: ret
+;
+; RV64ZFHMIN-LABEL: fpext_f16_to_f32:
+; RV64ZFHMIN: # %bb.0:
+; RV64ZFHMIN-NEXT: fcvt.s.h fa0, fa0
+; RV64ZFHMIN-NEXT: ret
+;
+; RV32NOZFH-LABEL: fpext_f16_to_f32:
+; RV32NOZFH: # %bb.0:
+; RV32NOZFH-NEXT: addi sp, sp, -16
+; RV32NOZFH-NEXT: sw ra, 12(sp) # 4-byte Folded Spill
+; RV32NOZFH-NEXT: call __extendhfsf2
+; RV32NOZFH-NEXT: lw ra, 12(sp) # 4-byte Folded Reload
+; RV32NOZFH-NEXT: addi sp, sp, 16
+; RV32NOZFH-NEXT: ret
+;
+; RV64NOZFH-LABEL: fpext_f16_to_f32:
+; RV64NOZFH: # %bb.0:
+; RV64NOZFH-NEXT: addi sp, sp, -16
+; RV64NOZFH-NEXT: sd ra, 8(sp) # 8-byte Folded Spill
+; RV64NOZFH-NEXT: call __extendhfsf2
+; RV64NOZFH-NEXT: ld ra, 8(sp) # 8-byte Folded Reload
+; RV64NOZFH-NEXT: addi sp, sp, 16
+; RV64NOZFH-NEXT: ret
+ %a = fpext half %x to float
+ ret float %a
+}
``````````
</details>
https://github.com/llvm/llvm-project/pull/227225
More information about the llvm-commits
mailing list