[llvm] e52a91e - [RISCV] Add f16 to isFMAFasterThanFMulAndFAdd now that the Zfh extension is supported

Craig Topper via llvm-commits llvm-commits at lists.llvm.org
Wed Dec 2 20:32:26 PST 2020


Author: Craig Topper
Date: 2020-12-02T20:31:43-08:00
New Revision: e52a91e156d7ab26989fef526434b02514428c91

URL: https://github.com/llvm/llvm-project/commit/e52a91e156d7ab26989fef526434b02514428c91
DIFF: https://github.com/llvm/llvm-project/commit/e52a91e156d7ab26989fef526434b02514428c91.diff

LOG: [RISCV] Add f16 to isFMAFasterThanFMulAndFAdd now that the Zfh extension is supported

Added: 
    

Modified: 
    llvm/lib/Target/RISCV/RISCVISelLowering.cpp
    llvm/test/CodeGen/RISCV/half-arith.ll
    llvm/test/CodeGen/RISCV/half-intrinsics.ll

Removed: 
    


################################################################################
diff  --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
index 8797e3484439..fbc9c28768f9 100644
--- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
+++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp
@@ -3499,6 +3499,8 @@ bool RISCVTargetLowering::isFMAFasterThanFMulAndFAdd(const MachineFunction &MF,
     return false;
 
   switch (VT.getSimpleVT().SimpleTy) {
+  case MVT::f16:
+    return Subtarget.hasStdExtZfh();
   case MVT::f32:
     return Subtarget.hasStdExtF();
   case MVT::f64:

diff  --git a/llvm/test/CodeGen/RISCV/half-arith.ll b/llvm/test/CodeGen/RISCV/half-arith.ll
index 6b6b1ddd907e..cc94f3e23cc7 100644
--- a/llvm/test/CodeGen/RISCV/half-arith.ll
+++ b/llvm/test/CodeGen/RISCV/half-arith.ll
@@ -321,3 +321,88 @@ define half @fnmsub_s(half %a, half %b, half %c) nounwind {
   %1 = call half @llvm.fma.f16(half %nega, half %b, half %c)
   ret half %1
 }
+
+define half @fmadd_s_contract(half %a, half %b, half %c) nounwind {
+; RV32IZFH-LABEL: fmadd_s_contract:
+; RV32IZFH:       # %bb.0:
+; RV32IZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
+; RV32IZFH-NEXT:    ret
+;
+; RV64IZFH-LABEL: fmadd_s_contract:
+; RV64IZFH:       # %bb.0:
+; RV64IZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
+; RV64IZFH-NEXT:    ret
+  %1 = fmul contract half %a, %b
+  %2 = fadd contract half %1, %c
+  ret half %2
+}
+
+define half @fmsub_s_contract(half %a, half %b, half %c) nounwind {
+; RV32IZFH-LABEL: fmsub_s_contract:
+; RV32IZFH:       # %bb.0:
+; RV32IZFH-NEXT:    fmv.h.x ft0, zero
+; RV32IZFH-NEXT:    fadd.h ft0, fa2, ft0
+; RV32IZFH-NEXT:    fmsub.h fa0, fa0, fa1, ft0
+; RV32IZFH-NEXT:    ret
+;
+; RV64IZFH-LABEL: fmsub_s_contract:
+; RV64IZFH:       # %bb.0:
+; RV64IZFH-NEXT:    fmv.h.x ft0, zero
+; RV64IZFH-NEXT:    fadd.h ft0, fa2, ft0
+; RV64IZFH-NEXT:    fmsub.h fa0, fa0, fa1, ft0
+; RV64IZFH-NEXT:    ret
+  %c_ = fadd half 0.0, %c ; avoid negation using xor
+  %1 = fmul contract half %a, %b
+  %2 = fsub contract half %1, %c_
+  ret half %2
+}
+
+define half @fnmadd_s_contract(half %a, half %b, half %c) nounwind {
+; RV32IZFH-LABEL: fnmadd_s_contract:
+; RV32IZFH:       # %bb.0:
+; RV32IZFH-NEXT:    fmv.h.x ft0, zero
+; RV32IZFH-NEXT:    fadd.h ft1, fa0, ft0
+; RV32IZFH-NEXT:    fadd.h ft2, fa1, ft0
+; RV32IZFH-NEXT:    fadd.h ft0, fa2, ft0
+; RV32IZFH-NEXT:    fnmadd.h fa0, ft1, ft2, ft0
+; RV32IZFH-NEXT:    ret
+;
+; RV64IZFH-LABEL: fnmadd_s_contract:
+; RV64IZFH:       # %bb.0:
+; RV64IZFH-NEXT:    fmv.h.x ft0, zero
+; RV64IZFH-NEXT:    fadd.h ft1, fa0, ft0
+; RV64IZFH-NEXT:    fadd.h ft2, fa1, ft0
+; RV64IZFH-NEXT:    fadd.h ft0, fa2, ft0
+; RV64IZFH-NEXT:    fnmadd.h fa0, ft1, ft2, ft0
+; RV64IZFH-NEXT:    ret
+  %a_ = fadd half 0.0, %a ; avoid negation using xor
+  %b_ = fadd half 0.0, %b ; avoid negation using xor
+  %c_ = fadd half 0.0, %c ; avoid negation using xor
+  %1 = fmul contract half %a_, %b_
+  %2 = fneg half %1
+  %3 = fsub contract half %2, %c_
+  ret half %3
+}
+
+define half @fnmsub_s_contract(half %a, half %b, half %c) nounwind {
+; RV32IZFH-LABEL: fnmsub_s_contract:
+; RV32IZFH:       # %bb.0:
+; RV32IZFH-NEXT:    fmv.h.x ft0, zero
+; RV32IZFH-NEXT:    fadd.h ft1, fa0, ft0
+; RV32IZFH-NEXT:    fadd.h ft0, fa1, ft0
+; RV32IZFH-NEXT:    fnmsub.h fa0, ft1, ft0, fa2
+; RV32IZFH-NEXT:    ret
+;
+; RV64IZFH-LABEL: fnmsub_s_contract:
+; RV64IZFH:       # %bb.0:
+; RV64IZFH-NEXT:    fmv.h.x ft0, zero
+; RV64IZFH-NEXT:    fadd.h ft1, fa0, ft0
+; RV64IZFH-NEXT:    fadd.h ft0, fa1, ft0
+; RV64IZFH-NEXT:    fnmsub.h fa0, ft1, ft0, fa2
+; RV64IZFH-NEXT:    ret
+  %a_ = fadd half 0.0, %a ; avoid negation using xor
+  %b_ = fadd half 0.0, %b ; avoid negation using xor
+  %1 = fmul contract half %a_, %b_
+  %2 = fsub contract half %c, %1
+  ret half %2
+}

diff  --git a/llvm/test/CodeGen/RISCV/half-intrinsics.ll b/llvm/test/CodeGen/RISCV/half-intrinsics.ll
index a23ac6798db3..c9a326efb99d 100644
--- a/llvm/test/CodeGen/RISCV/half-intrinsics.ll
+++ b/llvm/test/CodeGen/RISCV/half-intrinsics.ll
@@ -65,26 +65,22 @@ declare half @llvm.fmuladd.f16(half, half, half)
 define half @fmuladd_f16(half %a, half %b, half %c) nounwind {
 ; RV32IZFH-LABEL: fmuladd_f16:
 ; RV32IZFH:       # %bb.0:
-; RV32IZFH-NEXT:    fmul.h ft0, fa0, fa1
-; RV32IZFH-NEXT:    fadd.h fa0, ft0, fa2
+; RV32IZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
 ; RV32IZFH-NEXT:    ret
 ;
 ; RV32IDZFH-LABEL: fmuladd_f16:
 ; RV32IDZFH:       # %bb.0:
-; RV32IDZFH-NEXT:    fmul.h ft0, fa0, fa1
-; RV32IDZFH-NEXT:    fadd.h fa0, ft0, fa2
+; RV32IDZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
 ; RV32IDZFH-NEXT:    ret
 ;
 ; RV64IZFH-LABEL: fmuladd_f16:
 ; RV64IZFH:       # %bb.0:
-; RV64IZFH-NEXT:    fmul.h ft0, fa0, fa1
-; RV64IZFH-NEXT:    fadd.h fa0, ft0, fa2
+; RV64IZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
 ; RV64IZFH-NEXT:    ret
 ;
 ; RV64IDZFH-LABEL: fmuladd_f16:
 ; RV64IDZFH:       # %bb.0:
-; RV64IDZFH-NEXT:    fmul.h ft0, fa0, fa1
-; RV64IDZFH-NEXT:    fadd.h fa0, ft0, fa2
+; RV64IDZFH-NEXT:    fmadd.h fa0, fa0, fa1, fa2
 ; RV64IDZFH-NEXT:    ret
   %1 = call half @llvm.fmuladd.f16(half %a, half %b, half %c)
   ret half %1


        


More information about the llvm-commits mailing list