27#define DEBUG_TYPE "legalize-types"
44 RTLIB::UNKNOWN_LIBCALL;
51void DAGTypeLegalizer::SoftenFloatResult(
SDNode *
N,
unsigned ResNo) {
52 LLVM_DEBUG(
dbgs() <<
"Soften float result " << ResNo <<
": ";
N->dump(&DAG);
56 switch (
N->getOpcode()) {
59 dbgs() <<
"SoftenFloatResult #" << ResNo <<
": ";
60 N->dump(&DAG);
dbgs() <<
"\n";
70 R = SoftenFloatRes_EXTRACT_VECTOR_ELT(
N, ResNo);
break;
99 case ISD::FMA:
R = SoftenFloatRes_FMA(
N);
break;
145 R = SoftenFloatRes_VECREDUCE(
N);
149 R = SoftenFloatRes_VECREDUCE_SEQ(
N);
156 SetSoftenedFloat(
SDValue(
N, ResNo), R);
161 bool IsStrict =
N->isStrictFPOpcode();
163 unsigned Offset = IsStrict ? 1 : 0;
165 "Unexpected number of operands!");
169 EVT OpVT =
N->getOperand(0 +
Offset).getValueType();
171 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Op,
175 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
180 bool IsStrict =
N->isStrictFPOpcode();
182 unsigned Offset = IsStrict ? 1 : 0;
184 "Unexpected number of operands!");
186 GetSoftenedFloat(
N->getOperand(1 +
Offset)) };
189 EVT OpsVT[2] = {
N->getOperand(0 +
Offset).getValueType(),
190 N->getOperand(1 +
Offset).getValueType() };
192 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Ops,
196 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
201 return BitConvertToInteger(
N->getOperand(0));
207 GetSoftenedFloat(
N->getOperand(0)));
213 GetSoftenedFloat(
N->getOperand(0)));
219 SDValue Op = DisintegrateMERGE_VALUES(
N, ResNo);
220 return BitConvertToInteger(Op);
228 BitConvertToInteger(
N->getOperand(0)),
229 BitConvertToInteger(
N->getOperand(1)));
245 APInt Val(128, words);
256SDValue DAGTypeLegalizer::SoftenFloatRes_EXTRACT_VECTOR_ELT(
SDNode *
N,
unsigned ResNo) {
257 SDValue NewOp = BitConvertVectorToIntegerVector(
N->getOperand(0));
260 NewOp,
N->getOperand(1));
271 SDValue Op = GetSoftenedFloat(
N->getOperand(0));
277 return SoftenFloatRes_SELECT_CC(SelCC.getNode());
283 RTLIB::FMIN_PPCF128));
288 return SoftenFloatRes_SELECT_CC(SelCC.getNode());
294 RTLIB::FMAX_PPCF128));
303 RTLIB::ADD_PPCF128));
312 RTLIB::CBRT_PPCF128));
321 RTLIB::CEIL_PPCF128));
326 SDValue RHS = BitConvertToInteger(
N->getOperand(1));
329 EVT LVT =
LHS.getValueType();
330 EVT RVT =
RHS.getValueType();
351 }
else if (SizeDiff < 0) {
378 RTLIB::COS_PPCF128));
387 RTLIB::DIV_PPCF128));
396 RTLIB::EXP_PPCF128));
405 RTLIB::EXP2_PPCF128));
414 RTLIB::FLOOR_PPCF128));
423 RTLIB::LOG_PPCF128));
432 RTLIB::LOG2_PPCF128));
441 RTLIB::LOG10_PPCF128));
445 bool IsStrict =
N->isStrictFPOpcode();
447 unsigned Offset = IsStrict ? 1 : 0;
449 GetSoftenedFloat(
N->getOperand(1 +
Offset)),
450 GetSoftenedFloat(
N->getOperand(2 +
Offset)) };
453 EVT OpsVT[3] = {
N->getOperand(0 +
Offset).getValueType(),
454 N->getOperand(1 +
Offset).getValueType(),
455 N->getOperand(2 +
Offset).getValueType() };
457 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG,
464 NVT, Ops, CallOptions,
SDLoc(
N), Chain);
466 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
476 RTLIB::MUL_PPCF128));
481 RTLIB::NEARBYINT_F32,
482 RTLIB::NEARBYINT_F64,
483 RTLIB::NEARBYINT_F80,
484 RTLIB::NEARBYINT_F128,
485 RTLIB::NEARBYINT_PPCF128));
499 bool IsStrict =
N->isStrictFPOpcode();
506 Op = GetPromotedFloat(Op);
509 if (
Op.getValueType() ==
N->getValueType(0))
510 return BitConvertToInteger(Op);
520 Chain =
Op.getValue(1);
527 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported FP_EXTEND!");
529 EVT OpVT =
N->getOperand(IsStrict ? 1 : 0).getValueType();
531 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Op,
535 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
545 EVT OpsVT[1] = {
N->getOperand(0).getValueType() };
548 CallOptions,
SDLoc(
N)).first;
554 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported FP_EXTEND!");
559 bool IsStrict =
N->isStrictFPOpcode();
564 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported FP_ROUND!");
566 EVT OpVT =
N->getOperand(IsStrict ? 1 : 0).getValueType();
568 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Op,
572 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
582 RTLIB::POW_PPCF128));
586 bool IsStrict =
N->isStrictFPOpcode();
587 unsigned Offset = IsStrict ? 1 : 0;
590 "Unsupported power type!");
592 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unexpected fpowi.");
601 N->getOperand(1 +
Offset).getValueType().getSizeInBits()) {
613 EVT OpsVT[2] = {
N->getOperand(0 +
Offset).getValueType(),
614 N->getOperand(1 +
Offset).getValueType() };
616 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Ops,
620 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
630 RTLIB::REM_PPCF128));
639 RTLIB::RINT_PPCF128));
648 RTLIB::ROUND_PPCF128));
653 RTLIB::ROUNDEVEN_F32,
654 RTLIB::ROUNDEVEN_F64,
655 RTLIB::ROUNDEVEN_F80,
656 RTLIB::ROUNDEVEN_F128,
657 RTLIB::ROUNDEVEN_PPCF128));
666 RTLIB::SIN_PPCF128));
675 RTLIB::SQRT_PPCF128));
684 RTLIB::SUB_PPCF128));
693 RTLIB::TRUNC_PPCF128));
698 EVT VT =
N->getValueType(0);
703 L->getMemOperand()->getFlags() &
707 NewL = DAG.
getLoad(
L->getAddressingMode(),
L->getExtensionType(), NVT, dl,
708 L->getChain(),
L->getBasePtr(),
L->getOffset(),
709 L->getPointerInfo(), NVT,
L->getOriginalAlign(),
710 MMOFlags,
L->getAAInfo());
719 dl,
L->getChain(),
L->getBasePtr(),
L->getOffset(),
720 L->getPointerInfo(),
L->getMemoryVT(),
721 L->getOriginalAlign(), MMOFlags,
L->getAAInfo());
726 return BitConvertToInteger(ExtendNode);
733 LHS.getValueType(),
N->getOperand(0), LHS, RHS);
740 LHS.getValueType(),
N->getOperand(0),
741 N->getOperand(1), LHS, RHS,
N->getOperand(4));
746 N->getValueType(0)));
752 EVT VT =
N->getValueType(0);
757 NewVAARG = DAG.
getVAArg(NVT, dl, Chain,
Ptr,
N->getOperand(2),
758 N->getConstantOperandVal(3));
768 bool IsStrict =
N->isStrictFPOpcode();
771 EVT SVT =
N->getOperand(IsStrict ? 1 : 0).getValueType();
772 EVT RVT =
N->getValueType(0);
787 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported XINT_TO_FP!");
792 NVT,
N->getOperand(IsStrict ? 1 : 0));
796 std::pair<SDValue, SDValue> Tmp =
798 Op, CallOptions, dl, Chain);
801 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
811SDValue DAGTypeLegalizer::SoftenFloatRes_VECREDUCE_SEQ(
SDNode *
N) {
820bool DAGTypeLegalizer::SoftenFloatOperand(
SDNode *
N,
unsigned OpNo) {
821 LLVM_DEBUG(
dbgs() <<
"Soften float operand " << OpNo <<
": ";
N->dump(&DAG);
825 switch (
N->getOpcode()) {
828 dbgs() <<
"SoftenFloatOperand Op #" << OpNo <<
": ";
829 N->dump(&DAG);
dbgs() <<
"\n";
834 case ISD::BR_CC: Res = SoftenFloatOp_BR_CC(
N);
break;
846 Res = SoftenFloatOp_FP_TO_XINT_SAT(
N);
break;
852 case ISD::LRINT: Res = SoftenFloatOp_LRINT(
N);
break;
858 case ISD::SETCC: Res = SoftenFloatOp_SETCC(
N);
break;
859 case ISD::STORE: Res = SoftenFloatOp_STORE(
N, OpNo);
break;
864 if (!Res.getNode())
return false;
868 if (Res.getNode() ==
N)
871 assert(Res.getValueType() ==
N->getValueType(0) &&
N->getNumValues() == 1 &&
872 "Invalid operand softening");
874 ReplaceValueWith(
SDValue(
N, 0), Res);
879 SDValue Op0 = GetSoftenedFloat(
N->getOperand(0));
892 bool IsStrict =
N->isStrictFPOpcode();
894 EVT SVT =
Op.getValueType();
895 EVT RVT =
N->getValueType(0);
904 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported FP_ROUND libcall");
907 Op = GetSoftenedFloat(Op);
910 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, RVT, Op,
914 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
915 ReplaceValueWith(
SDValue(
N, 0), Tmp.first);
922 SDValue NewLHS =
N->getOperand(2), NewRHS =
N->getOperand(3);
923 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(1))->get();
926 NewLHS = GetSoftenedFloat(NewLHS);
927 NewRHS = GetSoftenedFloat(NewRHS);
929 N->getOperand(2),
N->getOperand(3));
933 if (!NewRHS.getNode()) {
956 if (Promoted.
bitsGE(RetVT))
964 bool IsStrict =
N->isStrictFPOpcode();
969 EVT SVT =
Op.getValueType();
970 EVT RVT =
N->getValueType(0);
980 "Unsupported FP_TO_XINT!");
982 Op = GetSoftenedFloat(Op);
986 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Op,
987 CallOptions, dl, Chain);
995 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
996 ReplaceValueWith(
SDValue(
N, 0), Res);
1000SDValue DAGTypeLegalizer::SoftenFloatOp_FP_TO_XINT_SAT(
SDNode *
N) {
1006 SDValue NewLHS =
N->getOperand(0), NewRHS =
N->getOperand(1);
1007 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(4))->get();
1010 NewLHS = GetSoftenedFloat(NewLHS);
1011 NewRHS = GetSoftenedFloat(NewRHS);
1013 N->getOperand(0),
N->getOperand(1));
1017 if (!NewRHS.getNode()) {
1024 N->getOperand(2),
N->getOperand(3),
1030 bool IsStrict =
N->isStrictFPOpcode();
1031 SDValue Op0 =
N->getOperand(IsStrict ? 1 : 0);
1032 SDValue Op1 =
N->getOperand(IsStrict ? 2 : 1);
1035 cast<CondCodeSDNode>(
N->getOperand(IsStrict ? 3 : 2))->get();
1038 SDValue NewLHS = GetSoftenedFloat(Op0);
1039 SDValue NewRHS = GetSoftenedFloat(Op1);
1055 "Unexpected setcc expansion!");
1058 ReplaceValueWith(
SDValue(
N, 0), NewLHS);
1059 ReplaceValueWith(
SDValue(
N, 1), Chain);
1065SDValue DAGTypeLegalizer::SoftenFloatOp_STORE(
SDNode *
N,
unsigned OpNo) {
1067 assert(OpNo == 1 &&
"Can only soften the stored value!");
1072 if (
ST->isTruncatingStore())
1074 Val = BitConvertToInteger(
1078 Val = GetSoftenedFloat(Val);
1080 return DAG.
getStore(
ST->getChain(), dl, Val,
ST->getBasePtr(),
1081 ST->getMemOperand());
1086 SDValue RHS = BitConvertToInteger(
N->getOperand(1));
1089 EVT LVT =
LHS.getValueType();
1091 EVT RVT =
RHS.getValueType();
1097 int SizeDiff = RSize - LSize;
1105 }
else if (SizeDiff < 0) {
1120 bool IsStrict =
N->isStrictFPOpcode();
1121 unsigned Offset = IsStrict ? 1 : 0;
1125 EVT OpVT =
N->getOperand(0 +
Offset).getValueType();
1127 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC, NVT, Op,
1131 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
1132 ReplaceValueWith(
SDValue(
N, 0), Tmp.first);
1140 EVT OpVT =
N->getOperand(
N->isStrictFPOpcode() ? 1 : 0).getValueType();
1146 RTLIB::LROUND_PPCF128));
1150 EVT OpVT =
N->getOperand(
N->isStrictFPOpcode() ? 1 : 0).getValueType();
1155 RTLIB::LLROUND_F128,
1156 RTLIB::LLROUND_PPCF128));
1160 EVT OpVT =
N->getOperand(
N->isStrictFPOpcode() ? 1 : 0).getValueType();
1166 RTLIB::LRINT_PPCF128));
1170 EVT OpVT =
N->getOperand(
N->isStrictFPOpcode() ? 1 : 0).getValueType();
1176 RTLIB::LLRINT_PPCF128));
1187void DAGTypeLegalizer::ExpandFloatResult(
SDNode *
N,
unsigned ResNo) {
1193 if (CustomLowerNode(
N,
N->getValueType(ResNo),
true))
1196 switch (
N->getOpcode()) {
1199 dbgs() <<
"ExpandFloatResult #" << ResNo <<
": ";
1200 N->dump(&DAG);
dbgs() <<
"\n";
1202 llvm_unreachable(
"Do not know how to expand the result of this operator!");
1289 "Do not know how to expand this float constant!");
1290 APInt C = cast<ConstantFPSDNode>(
N)->getValueAPF().bitcastToAPInt();
1293 APInt(64,
C.getRawData()[1])),
1296 APInt(64,
C.getRawData()[0])),
1302 bool IsStrict =
N->isStrictFPOpcode();
1303 unsigned Offset = IsStrict ? 1 : 0;
1307 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC,
N->getValueType(0),
1308 Op, CallOptions,
SDLoc(
N),
1311 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
1312 GetPairElements(Tmp.first,
Lo,
Hi);
1317 bool IsStrict =
N->isStrictFPOpcode();
1318 unsigned Offset = IsStrict ? 1 : 0;
1322 std::pair<SDValue, SDValue> Tmp = TLI.
makeLibCall(DAG, LC,
N->getValueType(0),
1323 Ops, CallOptions,
SDLoc(
N),
1326 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
1327 GetPairElements(Tmp.first,
Lo,
Hi);
1333 "Logic only correct for ppcf128!");
1336 GetExpandedFloat(
N->getOperand(0),
Lo, Tmp);
1347 RTLIB::FMIN_F32, RTLIB::FMIN_F64,
1348 RTLIB::FMIN_F80, RTLIB::FMIN_F128,
1349 RTLIB::FMIN_PPCF128),
Lo,
Hi);
1355 RTLIB::FMAX_F32, RTLIB::FMAX_F64,
1356 RTLIB::FMAX_F80, RTLIB::FMAX_F128,
1357 RTLIB::FMAX_PPCF128),
Lo,
Hi);
1363 RTLIB::ADD_F32, RTLIB::ADD_F64,
1364 RTLIB::ADD_F80, RTLIB::ADD_F128,
1365 RTLIB::ADD_PPCF128),
Lo,
Hi);
1370 ExpandFloatRes_Unary(
N,
GetFPLibCall(
N->getValueType(0), RTLIB::CBRT_F32,
1371 RTLIB::CBRT_F64, RTLIB::CBRT_F80,
1373 RTLIB::CBRT_PPCF128),
Lo,
Hi);
1376void DAGTypeLegalizer::ExpandFloatRes_FCEIL(
SDNode *
N,
1379 RTLIB::CEIL_F32, RTLIB::CEIL_F64,
1380 RTLIB::CEIL_F80, RTLIB::CEIL_F128,
1381 RTLIB::CEIL_PPCF128),
Lo,
Hi);
1384void DAGTypeLegalizer::ExpandFloatRes_FCOPYSIGN(
SDNode *
N,
1387 RTLIB::COPYSIGN_F32,
1388 RTLIB::COPYSIGN_F64,
1389 RTLIB::COPYSIGN_F80,
1390 RTLIB::COPYSIGN_F128,
1391 RTLIB::COPYSIGN_PPCF128),
Lo,
Hi);
1394void DAGTypeLegalizer::ExpandFloatRes_FCOS(
SDNode *
N,
1397 RTLIB::COS_F32, RTLIB::COS_F64,
1398 RTLIB::COS_F80, RTLIB::COS_F128,
1399 RTLIB::COS_PPCF128),
Lo,
Hi);
1409 RTLIB::DIV_PPCF128),
Lo,
Hi);
1412void DAGTypeLegalizer::ExpandFloatRes_FEXP(
SDNode *
N,
1415 RTLIB::EXP_F32, RTLIB::EXP_F64,
1416 RTLIB::EXP_F80, RTLIB::EXP_F128,
1417 RTLIB::EXP_PPCF128),
Lo,
Hi);
1420void DAGTypeLegalizer::ExpandFloatRes_FEXP2(
SDNode *
N,
1423 RTLIB::EXP2_F32, RTLIB::EXP2_F64,
1424 RTLIB::EXP2_F80, RTLIB::EXP2_F128,
1425 RTLIB::EXP2_PPCF128),
Lo,
Hi);
1428void DAGTypeLegalizer::ExpandFloatRes_FFLOOR(
SDNode *
N,
1431 RTLIB::FLOOR_F32, RTLIB::FLOOR_F64,
1432 RTLIB::FLOOR_F80, RTLIB::FLOOR_F128,
1433 RTLIB::FLOOR_PPCF128),
Lo,
Hi);
1436void DAGTypeLegalizer::ExpandFloatRes_FLOG(
SDNode *
N,
1439 RTLIB::LOG_F32, RTLIB::LOG_F64,
1440 RTLIB::LOG_F80, RTLIB::LOG_F128,
1441 RTLIB::LOG_PPCF128),
Lo,
Hi);
1444void DAGTypeLegalizer::ExpandFloatRes_FLOG2(
SDNode *
N,
1447 RTLIB::LOG2_F32, RTLIB::LOG2_F64,
1448 RTLIB::LOG2_F80, RTLIB::LOG2_F128,
1449 RTLIB::LOG2_PPCF128),
Lo,
Hi);
1452void DAGTypeLegalizer::ExpandFloatRes_FLOG10(
SDNode *
N,
1455 RTLIB::LOG10_F32, RTLIB::LOG10_F64,
1456 RTLIB::LOG10_F80, RTLIB::LOG10_F128,
1457 RTLIB::LOG10_PPCF128),
Lo,
Hi);
1462 bool IsStrict =
N->isStrictFPOpcode();
1463 unsigned Offset = IsStrict ? 1 : 0;
1473 RTLIB::FMA_PPCF128),
1474 N->getValueType(0), Ops, CallOptions,
1477 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
1478 GetPairElements(Tmp.first,
Lo,
Hi);
1488 RTLIB::MUL_PPCF128),
Lo,
Hi);
1491void DAGTypeLegalizer::ExpandFloatRes_FNEARBYINT(
SDNode *
N,
1494 RTLIB::NEARBYINT_F32,
1495 RTLIB::NEARBYINT_F64,
1496 RTLIB::NEARBYINT_F80,
1497 RTLIB::NEARBYINT_F128,
1498 RTLIB::NEARBYINT_PPCF128),
Lo,
Hi);
1504 GetExpandedFloat(
N->getOperand(0),
Lo,
Hi);
1513 bool IsStrict =
N->isStrictFPOpcode();
1518 if (NVT ==
N->getOperand(1).getValueType()) {
1519 Hi =
N->getOperand(1);
1520 Chain =
N->getOperand(0);
1524 {
N->getOperand(0),
N->getOperand(1) });
1525 Chain =
Hi.getValue(1);
1535 ReplaceValueWith(
SDValue(
N, 1), Chain);
1538void DAGTypeLegalizer::ExpandFloatRes_FPOW(
SDNode *
N,
1541 RTLIB::POW_F32, RTLIB::POW_F64,
1542 RTLIB::POW_F80, RTLIB::POW_F128,
1543 RTLIB::POW_PPCF128),
Lo,
Hi);
1546void DAGTypeLegalizer::ExpandFloatRes_FPOWI(
SDNode *
N,
1551void DAGTypeLegalizer::ExpandFloatRes_FREEZE(
SDNode *
N,
1554 "Logic only correct for ppcf128!");
1557 GetExpandedFloat(
N->getOperand(0),
Lo,
Hi);
1562void DAGTypeLegalizer::ExpandFloatRes_FREM(
SDNode *
N,
1565 RTLIB::REM_F32, RTLIB::REM_F64,
1566 RTLIB::REM_F80, RTLIB::REM_F128,
1567 RTLIB::REM_PPCF128),
Lo,
Hi);
1570void DAGTypeLegalizer::ExpandFloatRes_FRINT(
SDNode *
N,
1573 RTLIB::RINT_F32, RTLIB::RINT_F64,
1574 RTLIB::RINT_F80, RTLIB::RINT_F128,
1575 RTLIB::RINT_PPCF128),
Lo,
Hi);
1578void DAGTypeLegalizer::ExpandFloatRes_FROUND(
SDNode *
N,
1585 RTLIB::ROUND_PPCF128),
Lo,
Hi);
1588void DAGTypeLegalizer::ExpandFloatRes_FROUNDEVEN(
SDNode *
N,
1591 RTLIB::ROUNDEVEN_F32,
1592 RTLIB::ROUNDEVEN_F64,
1593 RTLIB::ROUNDEVEN_F80,
1594 RTLIB::ROUNDEVEN_F128,
1595 RTLIB::ROUNDEVEN_PPCF128),
Lo,
Hi);
1598void DAGTypeLegalizer::ExpandFloatRes_FSIN(
SDNode *
N,
1601 RTLIB::SIN_F32, RTLIB::SIN_F64,
1602 RTLIB::SIN_F80, RTLIB::SIN_F128,
1603 RTLIB::SIN_PPCF128),
Lo,
Hi);
1606void DAGTypeLegalizer::ExpandFloatRes_FSQRT(
SDNode *
N,
1609 RTLIB::SQRT_F32, RTLIB::SQRT_F64,
1610 RTLIB::SQRT_F80, RTLIB::SQRT_F128,
1611 RTLIB::SQRT_PPCF128),
Lo,
Hi);
1621 RTLIB::SUB_PPCF128),
Lo,
Hi);
1624void DAGTypeLegalizer::ExpandFloatRes_FTRUNC(
SDNode *
N,
1627 RTLIB::TRUNC_F32, RTLIB::TRUNC_F64,
1628 RTLIB::TRUNC_F80, RTLIB::TRUNC_F128,
1629 RTLIB::TRUNC_PPCF128),
Lo,
Hi);
1635 ExpandRes_NormalLoad(
N,
Lo,
Hi);
1647 assert(
LD->getMemoryVT().bitsLE(NVT) &&
"Float type not round?");
1650 LD->getMemoryVT(),
LD->getMemOperand());
1653 Chain =
Hi.getValue(1);
1661 ReplaceValueWith(
SDValue(LD, 1), Chain);
1667 EVT VT =
N->getValueType(0);
1669 bool Strict =
N->isStrictFPOpcode();
1670 SDValue Src =
N->getOperand(Strict ? 1 : 0);
1671 EVT SrcVT = Src.getValueType();
1679 Flags.setNoFPExcept(
N->getFlags().hasNoFPExcept());
1690 {Chain, Src}, Flags);
1691 Chain =
Hi.getValue(1);
1693 Hi = DAG.
getNode(
N->getOpcode(), dl, NVT, Src);
1699 LC = RTLIB::SINTTOFP_I64_PPCF128;
1702 LC = RTLIB::SINTTOFP_I128_PPCF128;
1704 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
"Unsupported XINT_TO_FP!");
1708 std::pair<SDValue, SDValue> Tmp =
1709 TLI.
makeLibCall(DAG, LC, VT, Src, CallOptions, dl, Chain);
1712 GetPairElements(Tmp.first,
Lo,
Hi);
1718 ReplaceValueWith(
SDValue(
N, 1), Chain);
1728 SrcVT = Src.getValueType();
1731 static const uint64_t TwoE32[] = { 0x41f0000000000000LL, 0 };
1732 static const uint64_t TwoE64[] = { 0x43f0000000000000LL, 0 };
1733 static const uint64_t TwoE128[] = { 0x47f0000000000000LL, 0 };
1755 {Chain, Hi, NewLo}, Flags);
1756 Chain =
Lo.getValue(1);
1757 ReplaceValueWith(
SDValue(
N, 1), Chain);
1762 GetPairElements(
Lo,
Lo,
Hi);
1774bool DAGTypeLegalizer::ExpandFloatOperand(
SDNode *
N,
unsigned OpNo) {
1779 if (CustomLowerNode(
N,
N->getOperand(OpNo).getValueType(),
false))
1782 switch (
N->getOpcode()) {
1785 dbgs() <<
"ExpandFloatOperand Op #" << OpNo <<
": ";
1786 N->dump(&DAG);
dbgs() <<
"\n";
1794 case ISD::BR_CC: Res = ExpandFloatOp_BR_CC(
N);
break;
1802 case ISD::LROUND: Res = ExpandFloatOp_LROUND(
N);
break;
1804 case ISD::LRINT: Res = ExpandFloatOp_LRINT(
N);
break;
1805 case ISD::LLRINT: Res = ExpandFloatOp_LLRINT(
N);
break;
1809 case ISD::SETCC: Res = ExpandFloatOp_SETCC(
N);
break;
1810 case ISD::STORE: Res = ExpandFloatOp_STORE(cast<StoreSDNode>(
N),
1815 if (!Res.getNode())
return false;
1819 if (Res.getNode() ==
N)
1822 assert(Res.getValueType() ==
N->getValueType(0) &&
N->getNumValues() == 1 &&
1823 "Invalid operand expansion");
1825 ReplaceValueWith(
SDValue(
N, 0), Res);
1831void DAGTypeLegalizer::FloatExpandSetCCOperands(
SDValue &NewLHS,
1836 SDValue LHSLo, LHSHi, RHSLo, RHSHi;
1837 GetExpandedFloat(NewLHS, LHSLo, LHSHi);
1838 GetExpandedFloat(NewRHS, RHSLo, RHSHi);
1847 SDValue Tmp1, Tmp2, Tmp3, OutputChain;
1852 RHSLo, CCCode, OutputChain, IsSignaling);
1860 RHSHi, CCCode, OutputChain, IsSignaling);
1865 Chain = OutputChain;
1869 SDValue NewLHS =
N->getOperand(2), NewRHS =
N->getOperand(3);
1870 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(1))->get();
1872 FloatExpandSetCCOperands(NewLHS, NewRHS, CCCode,
SDLoc(
N), Chain);
1884 N->getOperand(4)), 0);
1889 "Logic only correct for ppcf128!");
1891 GetExpandedFloat(
N->getOperand(1),
Lo,
Hi);
1895 N->getValueType(0),
N->getOperand(0),
Hi);
1899 bool IsStrict =
N->isStrictFPOpcode();
1901 "Logic only correct for ppcf128!");
1903 GetExpandedFloat(
N->getOperand(IsStrict ? 1 : 0),
Lo,
Hi);
1908 N->getValueType(0),
Hi,
N->getOperand(1));
1912 if (
Hi.getValueType() ==
N->getValueType(0)) {
1914 ReplaceValueWith(
SDValue(
N, 1),
N->getOperand(0));
1921 {
N->getOperand(0),
Hi,
N->getOperand(2)});
1923 ReplaceValueWith(
SDValue(
N, 0), Expansion);
1928 EVT RVT =
N->getValueType(0);
1931 bool IsStrict =
N->isStrictFPOpcode();
1934 SDValue Op =
N->getOperand(IsStrict ? 1 : 0);
1940 "Unsupported FP_TO_XINT!");
1942 std::pair<SDValue, SDValue> Tmp =
1943 TLI.
makeLibCall(DAG, LC, NVT, Op, CallOptions, dl, Chain);
1947 ReplaceValueWith(
SDValue(
N, 1), Tmp.second);
1948 ReplaceValueWith(
SDValue(
N, 0), Tmp.first);
1953 SDValue NewLHS =
N->getOperand(0), NewRHS =
N->getOperand(1);
1954 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(4))->get();
1956 FloatExpandSetCCOperands(NewLHS, NewRHS, CCCode,
SDLoc(
N), Chain);
1967 N->getOperand(2),
N->getOperand(3),
1972 bool IsStrict =
N->isStrictFPOpcode();
1973 SDValue NewLHS =
N->getOperand(IsStrict ? 1 : 0);
1974 SDValue NewRHS =
N->getOperand(IsStrict ? 2 : 1);
1977 cast<CondCodeSDNode>(
N->getOperand(IsStrict ? 3 : 2))->get();
1978 FloatExpandSetCCOperands(NewLHS, NewRHS, CCCode,
SDLoc(
N), Chain,
1984 "Unexpected setcc expansion!");
1986 ReplaceValueWith(
SDValue(
N, 0), NewLHS);
1987 ReplaceValueWith(
SDValue(
N, 1), Chain);
1993SDValue DAGTypeLegalizer::ExpandFloatOp_STORE(
SDNode *
N,
unsigned OpNo) {
1995 return ExpandOp_NormalStore(
N, OpNo);
1998 assert(OpNo == 1 &&
"Can only expand the stored value so far");
2005 ST->getValue().getValueType());
2007 assert(
ST->getMemoryVT().bitsLE(NVT) &&
"Float type not round?");
2011 GetExpandedOp(
ST->getValue(),
Lo,
Hi);
2014 ST->getMemoryVT(),
ST->getMemOperand());
2018 EVT RVT =
N->getValueType(0);
2019 EVT RetVT =
N->getOperand(0).getValueType();
2026 RTLIB::LROUND_PPCF128),
2027 RVT,
N->getOperand(0), CallOptions,
SDLoc(
N)).first;
2031 EVT RVT =
N->getValueType(0);
2032 EVT RetVT =
N->getOperand(0).getValueType();
2038 RTLIB::LLROUND_F128,
2039 RTLIB::LLROUND_PPCF128),
2040 RVT,
N->getOperand(0), CallOptions,
SDLoc(
N)).first;
2044 EVT RVT =
N->getValueType(0);
2045 EVT RetVT =
N->getOperand(0).getValueType();
2052 RTLIB::LRINT_PPCF128),
2053 RVT,
N->getOperand(0), CallOptions,
SDLoc(
N)).first;
2057 EVT RVT =
N->getValueType(0);
2058 EVT RetVT =
N->getOperand(0).getValueType();
2065 RTLIB::LLRINT_PPCF128),
2066 RVT,
N->getOperand(0), CallOptions,
SDLoc(
N)).first;
2088bool DAGTypeLegalizer::PromoteFloatOperand(
SDNode *
N,
unsigned OpNo) {
2089 LLVM_DEBUG(
dbgs() <<
"Promote float operand " << OpNo <<
": ";
N->dump(&DAG);
2093 if (CustomLowerNode(
N,
N->getOperand(OpNo).getValueType(),
false)) {
2103 switch (
N->getOpcode()) {
2106 dbgs() <<
"PromoteFloatOperand Op #" << OpNo <<
": ";
2107 N->dump(&DAG);
dbgs() <<
"\n";
2117 R = PromoteFloatOp_FP_TO_XINT_SAT(
N, OpNo);
break;
2120 case ISD::SETCC:
R = PromoteFloatOp_SETCC(
N, OpNo);
break;
2121 case ISD::STORE:
R = PromoteFloatOp_STORE(
N, OpNo);
break;
2125 ReplaceValueWith(
SDValue(
N, 0), R);
2129SDValue DAGTypeLegalizer::PromoteFloatOp_BITCAST(
SDNode *
N,
unsigned OpNo) {
2131 EVT OpVT =
Op->getValueType(0);
2133 SDValue Promoted = GetPromotedFloat(
N->getOperand(0));
2142 return DAG.
getBitcast(
N->getValueType(0), Convert);
2147SDValue DAGTypeLegalizer::PromoteFloatOp_FCOPYSIGN(
SDNode *
N,
unsigned OpNo) {
2148 assert (OpNo == 1 &&
"Only Operand 1 must need promotion here");
2149 SDValue Op1 = GetPromotedFloat(
N->getOperand(1));
2152 N->getOperand(0), Op1);
2156SDValue DAGTypeLegalizer::PromoteFloatOp_FP_TO_XINT(
SDNode *
N,
unsigned OpNo) {
2157 SDValue Op = GetPromotedFloat(
N->getOperand(0));
2161SDValue DAGTypeLegalizer::PromoteFloatOp_FP_TO_XINT_SAT(
SDNode *
N,
2163 SDValue Op = GetPromotedFloat(
N->getOperand(0));
2168SDValue DAGTypeLegalizer::PromoteFloatOp_FP_EXTEND(
SDNode *
N,
unsigned OpNo) {
2169 SDValue Op = GetPromotedFloat(
N->getOperand(0));
2170 EVT VT =
N->getValueType(0);
2173 if (VT ==
Op->getValueType(0))
2183SDValue DAGTypeLegalizer::PromoteFloatOp_SELECT_CC(
SDNode *
N,
unsigned OpNo) {
2188 LHS, RHS,
N->getOperand(2),
N->getOperand(3),
2194SDValue DAGTypeLegalizer::PromoteFloatOp_SETCC(
SDNode *
N,
unsigned OpNo) {
2195 EVT VT =
N->getValueType(0);
2196 SDValue Op0 = GetPromotedFloat(
N->getOperand(0));
2197 SDValue Op1 = GetPromotedFloat(
N->getOperand(1));
2198 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(2))->get();
2206SDValue DAGTypeLegalizer::PromoteFloatOp_STORE(
SDNode *
N,
unsigned OpNo) {
2211 SDValue Promoted = GetPromotedFloat(Val);
2212 EVT VT =
ST->getOperand(1).getValueType();
2219 return DAG.
getStore(
ST->getChain(),
DL, NewVal,
ST->getBasePtr(),
2220 ST->getMemOperand());
2227void DAGTypeLegalizer::PromoteFloatResult(
SDNode *
N,
unsigned ResNo) {
2228 LLVM_DEBUG(
dbgs() <<
"Promote float result " << ResNo <<
": ";
N->dump(&DAG);
2233 if (CustomLowerNode(
N,
N->getValueType(ResNo),
true)) {
2238 switch (
N->getOpcode()) {
2245 dbgs() <<
"PromoteFloatResult #" << ResNo <<
": ";
2246 N->dump(&DAG);
dbgs() <<
"\n";
2253 R = PromoteFloatRes_EXTRACT_VECTOR_ELT(
N);
break;
2287 case ISD::FSUB:
R = PromoteFloatRes_BinOp(
N);
break;
2290 case ISD::FMAD:
R = PromoteFloatRes_FMAD(
N);
break;
2295 case ISD::LOAD:
R = PromoteFloatRes_LOAD(
N);
break;
2307 R = PromoteFloatRes_VECREDUCE(
N);
2311 R = PromoteFloatRes_VECREDUCE_SEQ(
N);
2316 SetPromotedFloat(
SDValue(
N, ResNo), R);
2325 EVT VT =
N->getValueType(0);
2330 N->getOperand(0).getValueType().getSizeInBits());
2337 EVT VT =
N->getValueType(0);
2356SDValue DAGTypeLegalizer::PromoteFloatRes_EXTRACT_VECTOR_ELT(
SDNode *
N) {
2361 if (isa<ConstantSDNode>(
N->getOperand(1))) {
2367 uint64_t IdxVal = cast<ConstantSDNode>(
Idx)->getZExtValue();
2369 switch (getTypeAction(VecVT)) {
2372 SDValue Res = GetScalarizedVector(
N->getOperand(0));
2373 ReplaceValueWith(
SDValue(
N, 0), Res);
2377 Vec = GetWidenedVector(Vec);
2379 ReplaceValueWith(
SDValue(
N, 0), Res);
2384 GetSplitVector(Vec,
Lo,
Hi);
2386 uint64_t LoElts =
Lo.getValueType().getVectorNumElements();
2388 if (IdxVal < LoElts)
2393 Idx.getValueType()));
2394 ReplaceValueWith(
SDValue(
N, 0), Res);
2402 SDValue NewOp = BitConvertVectorToIntegerVector(
N->getOperand(0));
2407 NewOp,
N->getOperand(1));
2410 EVT VT =
N->getValueType(0);
2419 EVT VT =
N->getValueType(0);
2421 SDValue Op0 = GetPromotedFloat(
N->getOperand(0));
2432 EVT VT =
N->getValueType(0);
2434 SDValue Op = GetPromotedFloat(
N->getOperand(0));
2443 EVT VT =
N->getValueType(0);
2445 SDValue Op0 = GetPromotedFloat(
N->getOperand(0));
2446 SDValue Op1 = GetPromotedFloat(
N->getOperand(1));
2447 return DAG.
getNode(
N->getOpcode(),
SDLoc(
N), NVT, Op0, Op1,
N->getFlags());
2451 EVT VT =
N->getValueType(0);
2453 SDValue Op0 = GetPromotedFloat(
N->getOperand(0));
2454 SDValue Op1 = GetPromotedFloat(
N->getOperand(1));
2455 SDValue Op2 = GetPromotedFloat(
N->getOperand(2));
2457 return DAG.
getNode(
N->getOpcode(),
SDLoc(
N), NVT, Op0, Op1, Op2);
2462 EVT VT =
N->getValueType(0);
2464 SDValue Op0 = GetPromotedFloat(
N->getOperand(0));
2476 EVT VT =
N->getValueType(0);
2477 EVT OpVT =
Op->getValueType(0);
2489 EVT VT =
N->getValueType(0);
2494 L->getAddressingMode(),
L->getExtensionType(), IVT,
SDLoc(
N),
2495 L->getChain(),
L->getBasePtr(),
L->getOffset(),
L->getPointerInfo(), IVT,
2496 L->getOriginalAlign(),
L->getMemOperand()->getFlags(),
L->getAAInfo());
2512 N->getOperand(0), TrueVal, FalseVal);
2522 TrueVal.getNode()->getValueType(0),
N->getOperand(0),
2523 N->getOperand(1), TrueVal, FalseVal,
N->getOperand(4));
2530 EVT VT =
N->getValueType(0);
2542 N->getValueType(0)));
2554SDValue DAGTypeLegalizer::PromoteFloatRes_VECREDUCE_SEQ(
SDNode *
N) {
2560 EVT VT =
N->getValueType(0);
2571 { AM->getChain(), AM->getBasePtr(), CastVal },
2594void DAGTypeLegalizer::SoftPromoteHalfResult(
SDNode *
N,
unsigned ResNo) {
2595 LLVM_DEBUG(
dbgs() <<
"Soft promote half result " << ResNo <<
": ";
2596 N->dump(&DAG);
dbgs() <<
"\n");
2600 if (CustomLowerNode(
N,
N->getValueType(ResNo),
true)) {
2605 switch (
N->getOpcode()) {
2608 dbgs() <<
"SoftPromoteHalfResult #" << ResNo <<
": ";
2609 N->dump(&DAG);
dbgs() <<
"\n";
2611 llvm_unreachable(
"Do not know how to soft promote this operator's result!");
2616 R = SoftPromoteHalfRes_EXTRACT_VECTOR_ELT(
N);
break;
2653 case ISD::FSUB:
R = SoftPromoteHalfRes_BinOp(
N);
break;
2656 case ISD::FMAD:
R = SoftPromoteHalfRes_FMAD(
N);
break;
2658 case ISD::FPOWI:
R = SoftPromoteHalfRes_FPOWI(
N);
break;
2660 case ISD::LOAD:
R = SoftPromoteHalfRes_LOAD(
N);
break;
2665 case ISD::UNDEF:
R = SoftPromoteHalfRes_UNDEF(
N);
break;
2671 R = SoftPromoteHalfRes_VECREDUCE(
N);
2675 R = SoftPromoteHalfRes_VECREDUCE_SEQ(
N);
2680 SetSoftPromotedHalf(
SDValue(
N, ResNo), R);
2684 return BitConvertToInteger(
N->getOperand(0));
2687SDValue DAGTypeLegalizer::SoftPromoteHalfRes_ConstantFP(
SDNode *
N) {
2695SDValue DAGTypeLegalizer::SoftPromoteHalfRes_EXTRACT_VECTOR_ELT(
SDNode *
N) {
2696 SDValue NewOp = BitConvertVectorToIntegerVector(
N->getOperand(0));
2702SDValue DAGTypeLegalizer::SoftPromoteHalfRes_FCOPYSIGN(
SDNode *
N) {
2703 SDValue LHS = GetSoftPromotedHalf(
N->getOperand(0));
2704 SDValue RHS = BitConvertToInteger(
N->getOperand(1));
2707 EVT LVT =
LHS.getValueType();
2708 EVT RVT =
RHS.getValueType();
2729 }
else if (SizeDiff < 0) {
2751 EVT OVT =
N->getValueType(0);
2753 SDValue Op0 = GetSoftPromotedHalf(
N->getOperand(0));
2754 SDValue Op1 = GetSoftPromotedHalf(
N->getOperand(1));
2755 SDValue Op2 = GetSoftPromotedHalf(
N->getOperand(2));
2760 Op0 = DAG.
getNode(PromotionOpcode, dl, NVT, Op0);
2761 Op1 = DAG.
getNode(PromotionOpcode, dl, NVT, Op1);
2762 Op2 = DAG.
getNode(PromotionOpcode, dl, NVT, Op2);
2771 EVT OVT =
N->getValueType(0);
2773 SDValue Op0 = GetSoftPromotedHalf(
N->getOperand(0));
2786SDValue DAGTypeLegalizer::SoftPromoteHalfRes_FP_ROUND(
SDNode *
N) {
2787 EVT RVT =
N->getValueType(0);
2788 EVT SVT =
N->getOperand(0).getValueType();
2790 if (
N->isStrictFPOpcode()) {
2794 {
N->getOperand(0),
N->getOperand(1)});
2810 SDLoc(
N),
L->getChain(),
L->getBasePtr(),
L->getOffset(),
2811 L->getPointerInfo(),
MVT::i16,
L->getOriginalAlign(),
2812 L->getMemOperand()->getFlags(),
L->getAAInfo());
2820 SDValue Op1 = GetSoftPromotedHalf(
N->getOperand(1));
2821 SDValue Op2 = GetSoftPromotedHalf(
N->getOperand(2));
2826SDValue DAGTypeLegalizer::SoftPromoteHalfRes_SELECT_CC(
SDNode *
N) {
2827 SDValue Op2 = GetSoftPromotedHalf(
N->getOperand(2));
2828 SDValue Op3 = GetSoftPromotedHalf(
N->getOperand(3));
2830 N->getOperand(0),
N->getOperand(1), Op2, Op3,
2834SDValue DAGTypeLegalizer::SoftPromoteHalfRes_XINT_TO_FP(
SDNode *
N) {
2835 EVT OVT =
N->getValueType(0);
2850 EVT OVT =
N->getValueType(0);
2852 SDValue Op = GetSoftPromotedHalf(
N->getOperand(0));
2865 EVT OVT =
N->getValueType(0);
2867 SDValue Op0 = GetSoftPromotedHalf(
N->getOperand(0));
2868 SDValue Op1 = GetSoftPromotedHalf(
N->getOperand(1));
2873 Op0 = DAG.
getNode(PromotionOpcode, dl, NVT, Op0);
2874 Op1 = DAG.
getNode(PromotionOpcode, dl, NVT, Op1);
2882SDValue DAGTypeLegalizer::SoftPromoteHalfRes_VECREDUCE(
SDNode *
N) {
2888SDValue DAGTypeLegalizer::SoftPromoteHalfRes_VECREDUCE_SEQ(
SDNode *
N) {
2898bool DAGTypeLegalizer::SoftPromoteHalfOperand(
SDNode *
N,
unsigned OpNo) {
2899 LLVM_DEBUG(
dbgs() <<
"Soft promote half operand " << OpNo <<
": ";
2900 N->dump(&DAG);
dbgs() <<
"\n");
2903 if (CustomLowerNode(
N,
N->getOperand(OpNo).getValueType(),
false)) {
2913 switch (
N->getOpcode()) {
2916 dbgs() <<
"SoftPromoteHalfOperand Op #" << OpNo <<
": ";
2917 N->dump(&DAG);
dbgs() <<
"\n";
2919 llvm_unreachable(
"Do not know how to soft promote this operator's operand!");
2921 case ISD::BITCAST: Res = SoftPromoteHalfOp_BITCAST(
N);
break;
2922 case ISD::FCOPYSIGN: Res = SoftPromoteHalfOp_FCOPYSIGN(
N, OpNo);
break;
2927 Res = SoftPromoteHalfOp_FP_TO_XINT_SAT(
N);
break;
2930 case ISD::SELECT_CC: Res = SoftPromoteHalfOp_SELECT_CC(
N, OpNo);
break;
2931 case ISD::SETCC: Res = SoftPromoteHalfOp_SETCC(
N);
break;
2932 case ISD::STORE: Res = SoftPromoteHalfOp_STORE(
N, OpNo);
break;
2934 Res = SoftPromoteHalfOp_STACKMAP(
N, OpNo);
2937 Res = SoftPromoteHalfOp_PATCHPOINT(
N, OpNo);
2944 assert(Res.getNode() !=
N &&
"Expected a new node!");
2946 assert(Res.getValueType() ==
N->getValueType(0) &&
N->getNumValues() == 1 &&
2947 "Invalid operand expansion");
2949 ReplaceValueWith(
SDValue(
N, 0), Res);
2954 SDValue Op0 = GetSoftPromotedHalf(
N->getOperand(0));
2961 assert(OpNo == 1 &&
"Only Operand 1 must need promotion here");
2968 Op1 = GetSoftPromotedHalf(Op1);
2971 return DAG.
getNode(
N->getOpcode(), dl,
N->getValueType(0),
N->getOperand(0),
2975SDValue DAGTypeLegalizer::SoftPromoteHalfOp_FP_EXTEND(
SDNode *
N) {
2976 EVT RVT =
N->getValueType(0);
2977 bool IsStrict =
N->isStrictFPOpcode();
2978 SDValue Op =
N->getOperand(IsStrict ? 1 : 0);
2979 EVT SVT =
Op.getValueType();
2980 Op = GetSoftPromotedHalf(
N->getOperand(IsStrict ? 1 : 0));
2986 {
N->getValueType(0),
MVT::Other}, {
N->getOperand(0), Op});
2988 ReplaceValueWith(
SDValue(
N, 0), Res);
2995SDValue DAGTypeLegalizer::SoftPromoteHalfOp_FP_TO_XINT(
SDNode *
N) {
2996 EVT RVT =
N->getValueType(0);
2998 EVT SVT =
Op.getValueType();
3003 Op = GetSoftPromotedHalf(Op);
3007 return DAG.
getNode(
N->getOpcode(), dl,
N->getValueType(0), Res);
3010SDValue DAGTypeLegalizer::SoftPromoteHalfOp_FP_TO_XINT_SAT(
SDNode *
N) {
3011 EVT RVT =
N->getValueType(0);
3013 EVT SVT =
Op.getValueType();
3018 Op = GetSoftPromotedHalf(Op);
3022 return DAG.
getNode(
N->getOpcode(), dl,
N->getValueType(0), Res,
3028 assert(OpNo == 0 &&
"Can only soften the comparison values");
3036 Op0 = GetSoftPromotedHalf(Op0);
3037 Op1 = GetSoftPromotedHalf(Op1);
3041 Op0 = DAG.
getNode(PromotionOpcode, dl, NVT, Op0);
3042 Op1 = DAG.
getNode(PromotionOpcode, dl, NVT, Op1);
3045 N->getOperand(2),
N->getOperand(3),
N->getOperand(4));
3051 ISD::CondCode CCCode = cast<CondCodeSDNode>(
N->getOperand(2))->get();
3057 Op0 = GetSoftPromotedHalf(Op0);
3058 Op1 = GetSoftPromotedHalf(Op1);
3062 Op0 = DAG.
getNode(PromotionOpcode, dl, NVT, Op0);
3063 Op1 = DAG.
getNode(PromotionOpcode, dl, NVT, Op1);
3068SDValue DAGTypeLegalizer::SoftPromoteHalfOp_STORE(
SDNode *
N,
unsigned OpNo) {
3069 assert(OpNo == 1 &&
"Can only soften the stored value!");
3074 assert(!
ST->isTruncatingStore() &&
"Unexpected truncating store.");
3075 SDValue Promoted = GetSoftPromotedHalf(Val);
3076 return DAG.
getStore(
ST->getChain(), dl, Promoted,
ST->getBasePtr(),
3077 ST->getMemOperand());
3080SDValue DAGTypeLegalizer::SoftPromoteHalfOp_STACKMAP(
SDNode *
N,
unsigned OpNo) {
3084 NewOps[OpNo] = GetSoftPromotedHalf(Op);
3088 for (
unsigned ResNum = 0; ResNum <
N->getNumValues(); ResNum++)
3099 NewOps[OpNo] = GetSoftPromotedHalf(Op);
3103 for (
unsigned ResNum = 0; ResNum <
N->getNumValues(); ResNum++)
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Returns the sub type a function will return at a given Idx Should correspond to the result type of an ExtractValue instruction executed with just that one unsigned Idx
static bool isSigned(unsigned int Opcode)
static RTLIB::Libcall findFPToIntLibcall(EVT SrcVT, EVT RetVT, EVT &Promoted, bool Signed)
static RTLIB::Libcall GetFPLibCall(EVT VT, RTLIB::Libcall Call_F32, RTLIB::Libcall Call_F64, RTLIB::Libcall Call_F80, RTLIB::Libcall Call_F128, RTLIB::Libcall Call_PPCF128)
GetFPLibCall - Return the right libcall for the given floating point type.
static ISD::NodeType GetPromotionOpcode(EVT OpVT, EVT RetVT)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
APInt bitcastToAPInt() const
Class for arbitrary precision integers.
static APInt getAllOnes(unsigned numBits)
Return an APInt of a specified width with all bits set.
void clearBit(unsigned BitPosition)
Set a given bit to 0.
static APInt getSignMask(unsigned BitWidth)
Get the SignMask for a specific bit width.
const uint64_t * getRawData() const
This function returns a pointer to the internal storage of the APInt.
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
This is an SDNode representing atomic operations.
const SDValue & getVal() const
const APFloat & getValueAPF() const
@ NewNode
This is a new node, not before seen, that was created in the process of legalizing some other node.
void emitError(uint64_t LocCookie, const Twine &ErrorStr)
emitError - Emit an error message to the currently installed error handler with optional location inf...
This class is used to represent ISD::LOAD nodes.
@ FIRST_INTEGER_VALUETYPE
@ MODereferenceable
The memory access is dereferenceable (i.e., doesn't trap).
@ MOInvariant
The memory access always returns the same value (or traps).
MachineMemOperand * getMemOperand() const
Return a MachineMemOperand object describing the memory reference performed by operation.
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
Represents one node in the SelectionDAG.
unsigned getNumValues() const
Return the number of values defined/returned by this operator.
EVT getValueType(unsigned ResNo) const
Return the type of a specified result.
Unlike LLVM values, Selection DAG nodes may return multiple values as the result of a computation.
SDNode * getNode() const
get the SDNode which holds the desired result
SDValue getValue(unsigned R) const
EVT getValueType() const
Return the ValueType of the referenced return value.
SDValue getExtLoad(ISD::LoadExtType ExtType, const SDLoc &dl, EVT VT, SDValue Chain, SDValue Ptr, MachinePointerInfo PtrInfo, EVT MemVT, MaybeAlign Alignment=MaybeAlign(), MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes())
SDValue getSelect(const SDLoc &DL, EVT VT, SDValue Cond, SDValue LHS, SDValue RHS)
Helper function to make it easier to build Select's if you just have operands and don't want to check...
SDVTList getVTList(EVT VT)
Return an SDVTList that represents the list of values specified.
SDValue getSetCC(const SDLoc &DL, EVT VT, SDValue LHS, SDValue RHS, ISD::CondCode Cond, SDValue Chain=SDValue(), bool IsSignaling=false)
Helper function to make it easier to build SetCC's if you just have an ISD::CondCode instead of an SD...
SDValue getConstantFP(double Val, const SDLoc &DL, EVT VT, bool isTarget=false)
Create a ConstantFPSDNode wrapping a constant value.
SDValue getLoad(EVT VT, const SDLoc &dl, SDValue Chain, SDValue Ptr, MachinePointerInfo PtrInfo, MaybeAlign Alignment=MaybeAlign(), MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes(), const MDNode *Ranges=nullptr)
Loads are not normal binary operators: their result type is not determined by their operands,...
SDValue getAtomic(unsigned Opcode, const SDLoc &dl, EVT MemVT, SDValue Chain, SDValue Ptr, SDValue Val, MachineMemOperand *MMO)
Gets a node for an atomic op, produces result (if relevant) and chain and takes 2 operands.
SDValue getUNDEF(EVT VT)
Return an UNDEF node. UNDEF does not have a useful SDLoc.
SDValue getBitcast(EVT VT, SDValue V)
Return a bitcast using the SDLoc of the value operand, and casting to the provided type.
const DataLayout & getDataLayout() const
SDValue getConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isTarget=false, bool isOpaque=false)
Create a ConstantSDNode wrapping a constant value.
SDValue getVAArg(EVT VT, const SDLoc &dl, SDValue Chain, SDValue Ptr, SDValue SV, unsigned Align)
VAArg produces a result and token chain, and takes a pointer and a source value as input.
SDValue getTruncStore(SDValue Chain, const SDLoc &dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, EVT SVT, Align Alignment, MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes())
SDValue getStore(SDValue Chain, const SDLoc &dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, Align Alignment, MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes())
Helper function to build ISD::STORE nodes.
static const fltSemantics & EVTToAPFloatSemantics(EVT VT)
Returns an APFloat semantics tag appropriate for the given type.
SDValue getSelectCC(const SDLoc &DL, SDValue LHS, SDValue RHS, SDValue True, SDValue False, ISD::CondCode Cond)
Helper function to make it easier to build SelectCC's if you just have an ISD::CondCode instead of an...
SDValue getIntPtrConstant(uint64_t Val, const SDLoc &DL, bool isTarget=false)
SDValue getNode(unsigned Opcode, const SDLoc &DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
const TargetLibraryInfo & getLibInfo() const
SDValue getCondCode(ISD::CondCode Cond)
LLVMContext * getContext() const
SDNode * UpdateNodeOperands(SDNode *N, SDValue Op)
Mutate the specified node in-place to have the specified operands.
SDValue getEntryNode() const
Return the token chain corresponding to the entry of the function.
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
This class is used to represent ISD::STORE nodes.
unsigned getIntSize() const
Get size of a C-level int or unsigned int, in bits.
EVT getShiftAmountTy(EVT LHSTy, const DataLayout &DL, bool LegalTypes=true) const
Returns the type for the shift amount of a shift opcode.
virtual EVT getTypeToTransformTo(LLVMContext &Context, EVT VT) const
For types supported by the target, this is an identity function.
const char * getLibcallName(RTLIB::Libcall Call) const
Get the libcall routine name for the specified libcall.
void softenSetCCOperands(SelectionDAG &DAG, EVT VT, SDValue &NewLHS, SDValue &NewRHS, ISD::CondCode &CCCode, const SDLoc &DL, const SDValue OldLHS, const SDValue OldRHS) const
Soften the operands of a comparison.
std::pair< SDValue, SDValue > makeLibCall(SelectionDAG &DAG, RTLIB::Libcall LC, EVT RetVT, ArrayRef< SDValue > Ops, MakeLibCallOptions CallOptions, const SDLoc &dl, SDValue Chain=SDValue()) const
Returns a pair of (return value, chain).
SDValue expandVecReduceSeq(SDNode *Node, SelectionDAG &DAG) const
Expand a VECREDUCE_SEQ_* into an explicit ordered calculation.
SDValue expandFP_TO_INT_SAT(SDNode *N, SelectionDAG &DAG) const
Expand FP_TO_[US]INT_SAT into FP_TO_[US]INT and selects or min/max.
SDValue expandVecReduce(SDNode *Node, SelectionDAG &DAG) const
Expand a VECREDUCE_* into an explicit calculation.
SDValue createSelectForFMINNUM_FMAXNUM(SDNode *Node, SelectionDAG &DAG) const
Try to convert the fminnum/fmaxnum to a compare/select sequence.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
@ C
The default llvm calling convention, compatible with C.
NodeType
ISD::NodeType enum - This enum defines the target-independent operators for a SelectionDAG.
@ SETCC
SetCC operator - This evaluates to a true value iff the condition is true.
@ MERGE_VALUES
MERGE_VALUES - This node takes multiple discrete operands and returns them all as its individual resu...
@ STRICT_FSETCC
STRICT_FSETCC/STRICT_FSETCCS - Constrained versions of SETCC, used for floating-point operands only.
@ VECREDUCE_SEQ_FADD
Generic reduction nodes.
@ FMAD
FMAD - Perform a * b + c, while getting the same result as the separately rounded operations.
@ LOAD
LOAD and STORE have token chains as their first operand, then the same operands as an LLVM load/store...
@ ANY_EXTEND
ANY_EXTEND - Used for integer types. The high bits are undefined.
@ FMA
FMA - Perform a * b + c with no intermediate rounding step.
@ SINT_TO_FP
[SU]INT_TO_FP - These operators convert integers (whose interpreted sign depends on the first letter)...
@ VECREDUCE_FMAX
FMIN/FMAX nodes can have flags, for NaN/NoNaN variants.
@ FADD
Simple binary floating point operators.
@ FP16_TO_FP
FP16_TO_FP, FP_TO_FP16 - These operators are used to perform promotions and truncation for half-preci...
@ BITCAST
BITCAST - This operator converts between integer, vector and FP values, as if the value was stored to...
@ BUILD_PAIR
BUILD_PAIR - This is the opposite of EXTRACT_ELEMENT in some ways.
@ STRICT_FSQRT
Constrained versions of libm-equivalent floating point intrinsics.
@ SIGN_EXTEND
Conversion operators.
@ VECREDUCE_FADD
These reductions have relaxed evaluation order semantics, and have a single vector operand.
@ FNEG
Perform various unary floating-point operations inspired by libm.
@ BR_CC
BR_CC - Conditional branch.
@ FCANONICALIZE
Returns platform specific canonical encoding of a floating point number.
@ SELECT
Select(COND, TRUEVAL, FALSEVAL).
@ UNDEF
UNDEF - An undefined node.
@ EXTRACT_ELEMENT
EXTRACT_ELEMENT - This is used to get the lower or upper (determined by a Constant,...
@ ARITH_FENCE
ARITH_FENCE - This corresponds to a arithmetic fence intrinsic.
@ SHL
Shift and rotation operations.
@ EXTRACT_VECTOR_ELT
EXTRACT_VECTOR_ELT(VECTOR, IDX) - Returns a single element from VECTOR identified by the (potentially...
@ ZERO_EXTEND
ZERO_EXTEND - Used for integer types, zeroing the new bits.
@ SELECT_CC
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
@ FMINNUM
FMINNUM/FMAXNUM - Perform floating-point minimum or maximum on two values.
@ FP_EXTEND
X = FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
@ STRICT_SINT_TO_FP
STRICT_[US]INT_TO_FP - Convert a signed or unsigned integer to a floating point value.
@ BF16_TO_FP
BF16_TO_FP, FP_TO_BF16 - These operators are used to perform promotions and truncation for bfloat16.
@ STRICT_FP_ROUND
X = STRICT_FP_ROUND(Y, TRUNC) - Rounding 'Y' from a larger floating point type down to the precision ...
@ STRICT_FP_TO_SINT
STRICT_FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
@ FMINIMUM
FMINIMUM/FMAXIMUM - NaN-propagating minimum/maximum that also treat -0.0 as less than 0....
@ FP_TO_SINT
FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
@ STRICT_FP_EXTEND
X = STRICT_FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
@ AND
Bitwise operators - logical and, logical or, logical xor.
@ STRICT_FADD
Constrained versions of the binary floating point operators.
@ ATOMIC_SWAP
Val, OUTCHAIN = ATOMIC_SWAP(INCHAIN, ptr, amt) Val, OUTCHAIN = ATOMIC_LOAD_[OpName](INCHAIN,...
@ FP_ROUND
X = FP_ROUND(Y, TRUNC) - Rounding 'Y' from a larger floating point type down to the precision of the ...
@ FP_TO_SINT_SAT
FP_TO_[US]INT_SAT - Convert floating point value in operand 0 to a signed or unsigned scalar integer ...
@ TRUNCATE
TRUNCATE - Completely drop the high bits.
@ VAARG
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
@ FCOPYSIGN
FCOPYSIGN(X, Y) - Return the value of X with the sign of Y.
@ BUILD_VECTOR
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a fixed-width vector with the specified,...
bool isNormalStore(const SDNode *N)
Returns true if the specified node is a non-truncating and unindexed store.
bool isUNINDEXEDLoad(const SDNode *N)
Returns true if the specified node is an unindexed load.
bool isUNINDEXEDStore(const SDNode *N)
Returns true if the specified node is an unindexed store.
CondCode
ISD::CondCode enum - These are ordered carefully to make the bitfields below work out,...
bool isNormalLoad(const SDNode *N)
Returns true if the specified node is a non-extending and unindexed load.
Libcall getPOWI(EVT RetVT)
getPOWI - Return the POWI_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall getSINTTOFP(EVT OpVT, EVT RetVT)
getSINTTOFP - Return the SINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall getUINTTOFP(EVT OpVT, EVT RetVT)
getUINTTOFP - Return the UINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall
RTLIB::Libcall enum - This enum defines all of the runtime library calls the backend can emit.
Libcall getFPTOUINT(EVT OpVT, EVT RetVT)
getFPTOUINT - Return the FPTOUINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall getFPTOSINT(EVT OpVT, EVT RetVT)
getFPTOSINT - Return the FPTOSINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall getFPEXT(EVT OpVT, EVT RetVT)
getFPEXT - Return the FPEXT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
Libcall getFPROUND(EVT OpVT, EVT RetVT)
getFPROUND - Return the FPROUND_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
DiagnosticInfoOptimizationBase::Argument NV
This is an optimization pass for GlobalISel generic memory operations.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
static const fltSemantics & PPCDoubleDouble() LLVM_READNONE
bool isSimple() const
Test if the given EVT is simple (as opposed to being extended).
TypeSize getSizeInBits() const
Return the size of the specified value type in bits.
bool isByteSized() const
Return true if the bit size is a multiple of 8.
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
static EVT getIntegerVT(LLVMContext &Context, unsigned BitWidth)
Returns the EVT that represents an integer with the given number of bits.
bool bitsGE(EVT VT) const
Return true if this has no less bits than VT.
EVT getVectorElementType() const
Given a vector type, return the type of each element.
bool bitsLE(EVT VT) const
Return true if this has no more bits than VT.
These are IR-level optimization flags that may be propagated to SDNodes.
This structure is used to pass arguments to makeLibCall function.
MakeLibCallOptions & setSExt(bool Value=true)
MakeLibCallOptions & setTypeListBeforeSoften(ArrayRef< EVT > OpsVT, EVT RetVT, bool Value=true)