diff options
author | Alex Bradbury <asb@lowrisc.org> | 2018-04-12 05:42:42 +0000 |
---|---|---|
committer | Alex Bradbury <asb@lowrisc.org> | 2018-04-12 05:42:42 +0000 |
commit | 5d0dfa5e0e758fb075b70c4686e46abf45f3c3ba (patch) | |
tree | 9159564127fd554c740c3a982bd9b18a0dc8da01 /llvm/lib/Target | |
parent | dfaa021e990238902823882858b873d96eacb4da (diff) | |
download | bcm5719-llvm-5d0dfa5e0e758fb075b70c4686e46abf45f3c3ba.tar.gz bcm5719-llvm-5d0dfa5e0e758fb075b70c4686e46abf45f3c3ba.zip |
[RISCV] Add codegen support for RV32D floating point arithmetic operations
llvm-svn: 329874
Diffstat (limited to 'llvm/lib/Target')
-rw-r--r-- | llvm/lib/Target/RISCV/RISCVISelLowering.cpp | 5 | ||||
-rw-r--r-- | llvm/lib/Target/RISCV/RISCVInstrInfoD.td | 29 |
2 files changed, 33 insertions, 1 deletions
diff --git a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp index 3457ed599df..8b006d2d321 100644 --- a/llvm/lib/Target/RISCV/RISCVISelLowering.cpp +++ b/llvm/lib/Target/RISCV/RISCVISelLowering.cpp @@ -121,8 +121,11 @@ RISCVTargetLowering::RISCVTargetLowering(const TargetMachine &TM, setOperationAction(ISD::BR_CC, MVT::f32, Expand); } - if (Subtarget.hasStdExtD()) + if (Subtarget.hasStdExtD()) { + setOperationAction(ISD::FMINNUM, MVT::f64, Legal); + setOperationAction(ISD::FMAXNUM, MVT::f64, Legal); setLoadExtAction(ISD::EXTLOAD, MVT::f64, MVT::f32, Expand); + } setOperationAction(ISD::GlobalAddress, XLenVT, Custom); setOperationAction(ISD::BlockAddress, XLenVT, Custom); diff --git a/llvm/lib/Target/RISCV/RISCVInstrInfoD.td b/llvm/lib/Target/RISCV/RISCVInstrInfoD.td index aec4ad0b262..13e8a3456d6 100644 --- a/llvm/lib/Target/RISCV/RISCVInstrInfoD.td +++ b/llvm/lib/Target/RISCV/RISCVInstrInfoD.td @@ -191,6 +191,9 @@ def : InstAlias<"fneg.d $rd, $rs", (FSGNJN_D FPR64:$rd, FPR64:$rs, FPR64:$rs)>; // Pseudo-instructions and codegen patterns //===----------------------------------------------------------------------===// +class PatFpr64Fpr64<SDPatternOperator OpNode, RVInstR Inst> + : Pat<(OpNode FPR64:$rs1, FPR64:$rs2), (Inst $rs1, $rs2)>; + class PatFpr64Fpr64DynFrm<SDPatternOperator OpNode, RVInstRFrm Inst> : Pat<(OpNode FPR64:$rs1, FPR64:$rs2), (Inst $rs1, $rs2, 0b111)>; @@ -199,6 +202,32 @@ let Predicates = [HasStdExtD] in { /// Float arithmetic operations def : PatFpr64Fpr64DynFrm<fadd, FADD_D>; +def : PatFpr64Fpr64DynFrm<fsub, FSUB_D>; +def : PatFpr64Fpr64DynFrm<fmul, FMUL_D>; +def : PatFpr64Fpr64DynFrm<fdiv, FDIV_D>; + +def : Pat<(fsqrt FPR64:$rs1), (FSQRT_D FPR64:$rs1, 0b111)>; + +def : Pat<(fneg FPR64:$rs1), (FSGNJN_D $rs1, $rs1)>; +def : Pat<(fabs FPR64:$rs1), (FSGNJX_D $rs1, $rs1)>; + +def : PatFpr64Fpr64<fcopysign, FSGNJ_D>; +def : Pat<(fcopysign FPR64:$rs1, (fneg FPR64:$rs2)), (FSGNJN_D $rs1, $rs2)>; + +// The RISC-V 2.2 user-level ISA spec defines fmin and fmax as returning the +// canonical NaN when giving a signaling NaN. This doesn't match the LLVM +// behaviour (see https://bugs.llvm.org/show_bug.cgi?id=27363). However, the +// draft 2.3 ISA spec changes the definition of fmin and fmax in a way that +// matches LLVM's fminnum and fmaxnum +// <https://github.com/riscv/riscv-isa-manual/commit/cd20cee7efd9bac7c5aa127ec3b451749d2b3cce>. +def : PatFpr64Fpr64<fminnum, FMIN_D>; +def : PatFpr64Fpr64<fmaxnum, FMAX_D>; + +/// Setcc + +def : PatFpr64Fpr64<setoeq, FEQ_D>; +def : PatFpr64Fpr64<setolt, FLT_D>; +def : PatFpr64Fpr64<setole, FLE_D>; /// Loads |