@@ -713,7 +713,8 @@ RISCVTargetLowering::RISCVTargetLowering(const TargetMachine &TM,
713
713
ISD::VP_FRINT, ISD::VP_FNEARBYINT, ISD::VP_IS_FPCLASS,
714
714
ISD::VP_FMINIMUM, ISD::VP_FMAXIMUM, ISD::VP_LRINT,
715
715
ISD::VP_LLRINT, ISD::EXPERIMENTAL_VP_REVERSE,
716
- ISD::EXPERIMENTAL_VP_SPLICE};
716
+ ISD::EXPERIMENTAL_VP_SPLICE, ISD::VP_REDUCE_FMINIMUM,
717
+ ISD::VP_REDUCE_FMAXIMUM};
717
718
718
719
static const unsigned IntegerVecReduceOps[] = {
719
720
ISD::VECREDUCE_ADD, ISD::VECREDUCE_AND, ISD::VECREDUCE_OR,
@@ -958,7 +959,7 @@ RISCVTargetLowering::RISCVTargetLowering(const TargetMachine &TM,
958
959
ISD::VP_FFLOOR, ISD::VP_FROUND, ISD::VP_FROUNDEVEN,
959
960
ISD::VP_FCOPYSIGN, ISD::VP_FROUNDTOZERO, ISD::VP_FRINT,
960
961
ISD::VP_FNEARBYINT, ISD::VP_SETCC, ISD::VP_FMINIMUM,
961
- ISD::VP_FMAXIMUM};
962
+ ISD::VP_FMAXIMUM, ISD::VP_REDUCE_FMINIMUM, ISD::VP_REDUCE_FMAXIMUM };
962
963
963
964
// Sets common operation actions on RVV floating-point vector types.
964
965
const auto SetCommonVFPActions = [&](MVT VT) {
@@ -6661,6 +6662,8 @@ SDValue RISCVTargetLowering::LowerOperation(SDValue Op,
6661
6662
case ISD::VP_REDUCE_SEQ_FADD:
6662
6663
case ISD::VP_REDUCE_FMIN:
6663
6664
case ISD::VP_REDUCE_FMAX:
6665
+ case ISD::VP_REDUCE_FMINIMUM:
6666
+ case ISD::VP_REDUCE_FMAXIMUM:
6664
6667
if (Op.getOperand(1).getValueType() == MVT::nxv32f16 &&
6665
6668
(Subtarget.hasVInstructionsF16Minimal() &&
6666
6669
!Subtarget.hasVInstructionsF16()))
@@ -9526,8 +9529,10 @@ static unsigned getRVVReductionOp(unsigned ISDOpcode) {
9526
9529
case ISD::VP_REDUCE_SEQ_FADD:
9527
9530
return RISCVISD::VECREDUCE_SEQ_FADD_VL;
9528
9531
case ISD::VP_REDUCE_FMAX:
9532
+ case ISD::VP_REDUCE_FMAXIMUM:
9529
9533
return RISCVISD::VECREDUCE_FMAX_VL;
9530
9534
case ISD::VP_REDUCE_FMIN:
9535
+ case ISD::VP_REDUCE_FMINIMUM:
9531
9536
return RISCVISD::VECREDUCE_FMIN_VL;
9532
9537
}
9533
9538
@@ -9786,16 +9791,19 @@ SDValue RISCVTargetLowering::lowerFPVECREDUCE(SDValue Op,
9786
9791
SDValue RISCVTargetLowering::lowerVPREDUCE(SDValue Op,
9787
9792
SelectionDAG &DAG) const {
9788
9793
SDLoc DL(Op);
9794
+ unsigned Opc = Op.getOpcode();
9795
+ SDValue Start = Op.getOperand(0);
9789
9796
SDValue Vec = Op.getOperand(1);
9790
9797
EVT VecEVT = Vec.getValueType();
9798
+ MVT XLenVT = Subtarget.getXLenVT();
9791
9799
9792
9800
// TODO: The type may need to be widened rather than split. Or widened before
9793
9801
// it can be split.
9794
9802
if (!isTypeLegal(VecEVT))
9795
9803
return SDValue();
9796
9804
9797
9805
MVT VecVT = VecEVT.getSimpleVT();
9798
- unsigned RVVOpcode = getRVVReductionOp(Op.getOpcode() );
9806
+ unsigned RVVOpcode = getRVVReductionOp(Opc );
9799
9807
9800
9808
if (VecVT.isFixedLengthVector()) {
9801
9809
auto ContainerVT = getContainerForFixedLengthVector(VecVT);
@@ -9804,8 +9812,30 @@ SDValue RISCVTargetLowering::lowerVPREDUCE(SDValue Op,
9804
9812
9805
9813
SDValue VL = Op.getOperand(3);
9806
9814
SDValue Mask = Op.getOperand(2);
9807
- return lowerReductionSeq(RVVOpcode, Op.getSimpleValueType(), Op.getOperand(0),
9808
- Vec, Mask, VL, DL, DAG, Subtarget);
9815
+ SDValue Res =
9816
+ lowerReductionSeq(RVVOpcode, Op.getSimpleValueType(), Op.getOperand(0),
9817
+ Vec, Mask, VL, DL, DAG, Subtarget);
9818
+ if ((Opc != ISD::VP_REDUCE_FMINIMUM && Opc != ISD::VP_REDUCE_FMAXIMUM) ||
9819
+ Op->getFlags().hasNoNaNs())
9820
+ return Res;
9821
+
9822
+ // Propagate NaNs.
9823
+ MVT PredVT = getMaskTypeFor(Vec.getSimpleValueType());
9824
+ // Check if any of the elements in Vec is NaN.
9825
+ SDValue IsNaN = DAG.getNode(
9826
+ RISCVISD::SETCC_VL, DL, PredVT,
9827
+ {Vec, Vec, DAG.getCondCode(ISD::SETNE), DAG.getUNDEF(PredVT), Mask, VL});
9828
+ SDValue VCPop = DAG.getNode(RISCVISD::VCPOP_VL, DL, XLenVT, IsNaN, Mask, VL);
9829
+ // Check if the start value is NaN.
9830
+ SDValue StartIsNaN = DAG.getSetCC(DL, XLenVT, Start, Start, ISD::SETUO);
9831
+ VCPop = DAG.getNode(ISD::OR, DL, XLenVT, VCPop, StartIsNaN);
9832
+ SDValue NoNaNs = DAG.getSetCC(DL, XLenVT, VCPop,
9833
+ DAG.getConstant(0, DL, XLenVT), ISD::SETEQ);
9834
+ MVT ResVT = Res.getSimpleValueType();
9835
+ return DAG.getSelect(
9836
+ DL, ResVT, NoNaNs, Res,
9837
+ DAG.getConstantFP(APFloat::getNaN(DAG.EVTToAPFloatSemantics(ResVT)), DL,
9838
+ ResVT));
9809
9839
}
9810
9840
9811
9841
SDValue RISCVTargetLowering::lowerINSERT_SUBVECTOR(SDValue Op,
0 commit comments