Skip to content

Commit 419f90e

Browse files
committed
[LoongArch] Support llvm.is.fpclass for f32 and f64
is_fpclass (fj, mask) -> sltu (r0, and (movfr2gr.[sd] (fclass.[sd] fj), (to_fclass_mask mask))) [1]: https://loongson.github.io/LoongArch-Documentation/LoongArch-Vol1-EN.html#_fclass_sd Reviewed By: wangleiat Differential Revision: https://reviews.llvm.org/D159183
1 parent c31dda4 commit 419f90e

File tree

7 files changed

+2270
-5
lines changed

7 files changed

+2270
-5
lines changed

llvm/lib/Target/LoongArch/LoongArchFloat32InstrInfo.td

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -153,10 +153,11 @@ def : PatFprFpr<fminnum_ieee, FMIN_S, FPR32>;
153153
def : PatFpr<fneg, FNEG_S, FPR32>;
154154
def : PatFpr<fabs, FABS_S, FPR32>;
155155
def : PatFpr<fsqrt, FSQRT_S, FPR32>;
156-
157156
def : Pat<(fdiv fpimm1, (fsqrt FPR32:$fj)), (FRSQRT_S FPR32:$fj)>;
158-
159157
def : Pat<(fcanonicalize FPR32:$fj), (FMAX_S $fj, $fj)>;
158+
def : Pat<(is_fpclass FPR32:$fj, (i32 timm:$mask)),
159+
(SLTU R0, (AND (MOVFR2GR_S (FCLASS_S FPR32:$fj)),
160+
(to_fclass_mask timm:$mask)))>;
160161

161162
/// Setcc
162163

llvm/lib/Target/LoongArch/LoongArchFloat64InstrInfo.td

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -142,15 +142,22 @@ def : PatFprFpr<fminnum_ieee, FMIN_D, FPR64>;
142142
def : PatFpr<fneg, FNEG_D, FPR64>;
143143
def : PatFpr<fabs, FABS_D, FPR64>;
144144
def : PatFpr<fsqrt, FSQRT_D, FPR64>;
145-
146145
def : Pat<(fdiv fpimm1, (fsqrt FPR64:$fj)), (FRSQRT_D FPR64:$fj)>;
147-
148146
def : Pat<(fcopysign FPR64:$fj, FPR32:$fk),
149147
(FCOPYSIGN_D FPR64:$fj, (FCVT_D_S FPR32:$fk))>;
150148
def : Pat<(fcopysign FPR32:$fj, FPR64:$fk),
151149
(FCOPYSIGN_S FPR32:$fj, (FCVT_S_D FPR64:$fk))>;
152-
153150
def : Pat<(fcanonicalize FPR64:$fj), (FMAX_D $fj, $fj)>;
151+
let Predicates = [IsLA32] in {
152+
def : Pat<(is_fpclass FPR64:$fj, (i32 timm:$mask)),
153+
(SLTU R0, (AND (MOVFR2GR_S_64 (FCLASS_D FPR64:$fj)),
154+
(to_fclass_mask timm:$mask)))>;
155+
} // Predicates = [IsLA32]
156+
let Predicates = [IsLA64] in {
157+
def : Pat<(is_fpclass FPR64:$fj, (i32 timm:$mask)),
158+
(SLTU R0, (AND (MOVFR2GR_D (FCLASS_D FPR64:$fj)),
159+
(to_fclass_mask timm:$mask)))>;
160+
} // Predicates = [IsLA64]
154161

155162
/// Setcc
156163

llvm/lib/Target/LoongArch/LoongArchISelLowering.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -170,6 +170,7 @@ LoongArchTargetLowering::LoongArchTargetLowering(const TargetMachine &TM,
170170
setOperationAction(ISD::FMAXNUM_IEEE, MVT::f32, Legal);
171171
setOperationAction(ISD::STRICT_FSETCCS, MVT::f32, Legal);
172172
setOperationAction(ISD::STRICT_FSETCC, MVT::f32, Legal);
173+
setOperationAction(ISD::IS_FPCLASS, MVT::f32, Legal);
173174
setOperationAction(ISD::FSIN, MVT::f32, Expand);
174175
setOperationAction(ISD::FCOS, MVT::f32, Expand);
175176
setOperationAction(ISD::FSINCOS, MVT::f32, Expand);
@@ -202,6 +203,7 @@ LoongArchTargetLowering::LoongArchTargetLowering(const TargetMachine &TM,
202203
setOperationAction(ISD::FMA, MVT::f64, Legal);
203204
setOperationAction(ISD::FMINNUM_IEEE, MVT::f64, Legal);
204205
setOperationAction(ISD::FMAXNUM_IEEE, MVT::f64, Legal);
206+
setOperationAction(ISD::IS_FPCLASS, MVT::f64, Legal);
205207
setOperationAction(ISD::FSIN, MVT::f64, Expand);
206208
setOperationAction(ISD::FCOS, MVT::f64, Expand);
207209
setOperationAction(ISD::FSINCOS, MVT::f64, Expand);

llvm/lib/Target/LoongArch/LoongArchInstrInfo.h

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -88,5 +88,20 @@ class LoongArchInstrInfo : public LoongArchGenInstrInfo {
8888
const LoongArchSubtarget &STI;
8989
};
9090

91+
namespace LoongArch {
92+
93+
// Mask assignments for floating-point.
94+
static constexpr unsigned FClassMaskSignalingNaN = 0x001;
95+
static constexpr unsigned FClassMaskQuietNaN = 0x002;
96+
static constexpr unsigned FClassMaskNegativeInfinity = 0x004;
97+
static constexpr unsigned FClassMaskNegativeNormal = 0x008;
98+
static constexpr unsigned FClassMaskNegativeSubnormal = 0x010;
99+
static constexpr unsigned FClassMaskNegativeZero = 0x020;
100+
static constexpr unsigned FClassMaskPositiveInfinity = 0x040;
101+
static constexpr unsigned FClassMaskPositiveNormal = 0x080;
102+
static constexpr unsigned FClassMaskPositiveSubnormal = 0x100;
103+
static constexpr unsigned FClassMaskPositiveZero = 0x200;
104+
} // namespace LoongArch
105+
91106
} // end namespace llvm
92107
#endif // LLVM_LIB_TARGET_LOONGARCH_LOONGARCHINSTRINFO_H

llvm/lib/Target/LoongArch/LoongArchInstrInfo.td

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,32 @@ def loongarch_iocsrwr_d : SDNode<"LoongArchISD::IOCSRWR_D",
143143
def loongarch_cpucfg : SDNode<"LoongArchISD::CPUCFG", SDTUnaryOp,
144144
[SDNPHasChain]>;
145145

146+
def to_fclass_mask: SDNodeXForm<timm, [{
147+
uint64_t Check = N->getZExtValue();
148+
unsigned Mask = 0;
149+
if (Check & fcSNan)
150+
Mask |= LoongArch::FClassMaskSignalingNaN;
151+
if (Check & fcQNan)
152+
Mask |= LoongArch::FClassMaskQuietNaN;
153+
if (Check & fcPosInf)
154+
Mask |= LoongArch::FClassMaskPositiveInfinity;
155+
if (Check & fcNegInf)
156+
Mask |= LoongArch::FClassMaskNegativeInfinity;
157+
if (Check & fcPosNormal)
158+
Mask |= LoongArch::FClassMaskPositiveNormal;
159+
if (Check & fcNegNormal)
160+
Mask |= LoongArch::FClassMaskNegativeNormal;
161+
if (Check & fcPosSubnormal)
162+
Mask |= LoongArch::FClassMaskPositiveSubnormal;
163+
if (Check & fcNegSubnormal)
164+
Mask |= LoongArch::FClassMaskNegativeSubnormal;
165+
if (Check & fcPosZero)
166+
Mask |= LoongArch::FClassMaskPositiveZero;
167+
if (Check & fcNegZero)
168+
Mask |= LoongArch::FClassMaskNegativeZero;
169+
return CurDAG->getTargetConstant(Mask, SDLoc(N), Subtarget->getGRLenVT());
170+
}]>;
171+
146172
//===----------------------------------------------------------------------===//
147173
// Operand and SDNode transformation definitions.
148174
//===----------------------------------------------------------------------===//

0 commit comments

Comments
 (0)