LLVM 24.0.0git
LegalizeIntegerTypes.cpp
Go to the documentation of this file.
1//===----- LegalizeIntegerTypes.cpp - Legalization of integer types -------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file implements integer type expansion and promotion for LegalizeTypes.
10// Promotion is the act of changing a computation in an illegal type into a
11// computation in a larger type. For example, implementing i8 arithmetic in an
12// i32 register (often needed on powerpc).
13// Expansion is the act of changing a computation in an illegal type into a
14// computation in two identical registers of a smaller type. For example,
15// implementing i64 arithmetic in two i32 registers (often needed on 32-bit
16// targets).
17//
18//===----------------------------------------------------------------------===//
19
20#include "LegalizeTypes.h"
29#include <algorithm>
30using namespace llvm;
31
32#define DEBUG_TYPE "legalize-types"
33
34//===----------------------------------------------------------------------===//
35// Integer Result Promotion
36//===----------------------------------------------------------------------===//
37
38/// PromoteIntegerResult - This method is called when a result of a node is
39/// found to be in need of promotion to a larger type. At this point, the node
40/// may also have invalid operands or may have other results that need
41/// expansion, we just know that (at least) one result needs promotion.
42void DAGTypeLegalizer::PromoteIntegerResult(SDNode *N, unsigned ResNo) {
43 LLVM_DEBUG(dbgs() << "Promote integer result: "; N->dump(&DAG));
44 SDValue Res = SDValue();
45
46 // See if the target wants to custom expand this node.
47 if (CustomLowerNode(N, N->getValueType(ResNo), true)) {
48 LLVM_DEBUG(dbgs() << "Node has been custom expanded, done\n");
49 return;
50 }
51
52 switch (N->getOpcode()) {
53 default:
54#ifndef NDEBUG
55 dbgs() << "PromoteIntegerResult #" << ResNo << ": ";
56 N->dump(&DAG); dbgs() << "\n";
57#endif
58 report_fatal_error("Do not know how to promote this operator!");
59 case ISD::MERGE_VALUES:Res = PromoteIntRes_MERGE_VALUES(N, ResNo); break;
60 case ISD::AssertSext: Res = PromoteIntRes_AssertSext(N); break;
61 case ISD::AssertZext: Res = PromoteIntRes_AssertZext(N); break;
62 case ISD::BITCAST: Res = PromoteIntRes_BITCAST(N); break;
63 case ISD::BITREVERSE: Res = PromoteIntRes_BITREVERSE(N); break;
64 case ISD::BSWAP: Res = PromoteIntRes_BSWAP(N); break;
65 case ISD::BUILD_PAIR: Res = PromoteIntRes_BUILD_PAIR(N); break;
66 case ISD::Constant: Res = PromoteIntRes_Constant(N); break;
68 case ISD::CTLZ: Res = PromoteIntRes_CTLZ(N); break;
69 case ISD::CTLS: Res = PromoteIntRes_CTLS(N); break;
70 case ISD::PARITY:
71 case ISD::CTPOP: Res = PromoteIntRes_CTPOP_PARITY(N); break;
73 case ISD::CTTZ: Res = PromoteIntRes_CTTZ(N); break;
75 case ISD::CTTZ_ELTS:
76 case ISD::VP_CTTZ_ELTS_ZERO_POISON:
77 case ISD::VP_CTTZ_ELTS:
78 Res = PromoteIntRes_VP_CttzElements(N);
79 break;
81 Res = PromoteIntRes_EXTRACT_VECTOR_ELT(N); break;
82 case ISD::LOAD: Res = PromoteIntRes_LOAD(cast<LoadSDNode>(N)); break;
83 case ISD::VP_LOAD:
84 Res = PromoteIntRes_VP_LOAD(cast<VPLoadSDNode>(N));
85 break;
86 case ISD::MLOAD: Res = PromoteIntRes_MLOAD(cast<MaskedLoadSDNode>(N));
87 break;
88 case ISD::MGATHER: Res = PromoteIntRes_MGATHER(cast<MaskedGatherSDNode>(N));
89 break;
91 Res = PromoteIntRes_VECTOR_COMPRESS(N);
92 break;
93 case ISD::SELECT:
94 case ISD::VSELECT:
95 case ISD::VP_MERGE:
96 Res = PromoteIntRes_Select(N);
97 break;
98 case ISD::SELECT_CC: Res = PromoteIntRes_SELECT_CC(N); break;
101 case ISD::SETCC: Res = PromoteIntRes_SETCC(N); break;
102 case ISD::SMIN:
103 case ISD::SMAX: Res = PromoteIntRes_SExtIntBinOp(N); break;
104 case ISD::UMIN:
105 case ISD::UMAX: Res = PromoteIntRes_UMINUMAX(N); break;
106
107 case ISD::SHL: Res = PromoteIntRes_SHL(N); break;
109 Res = PromoteIntRes_SIGN_EXTEND_INREG(N); break;
110 case ISD::SRA: Res = PromoteIntRes_SRA(N); break;
111 case ISD::SRL: Res = PromoteIntRes_SRL(N); break;
112 case ISD::TRUNCATE: Res = PromoteIntRes_TRUNCATE(N); break;
113 case ISD::POISON:
114 case ISD::UNDEF: Res = PromoteIntRes_UNDEF(N); break;
115 case ISD::VAARG: Res = PromoteIntRes_VAARG(N); break;
116 case ISD::VSCALE: Res = PromoteIntRes_VSCALE(N); break;
117
119 Res = PromoteIntRes_EXTRACT_SUBVECTOR(N); break;
121 Res = PromoteIntRes_INSERT_SUBVECTOR(N); break;
123 Res = PromoteIntRes_VECTOR_REVERSE(N); break;
125 Res = PromoteIntRes_VECTOR_SHUFFLE(N); break;
128 Res = PromoteIntRes_VECTOR_SPLICE(N);
129 break;
131 Res = PromoteIntRes_VECTOR_REPEAT(N);
132 break;
135 Res = PromoteIntRes_VECTOR_INTERLEAVE_DEINTERLEAVE(N);
136 return;
138 Res = PromoteIntRes_INSERT_VECTOR_ELT(N); break;
140 Res = PromoteIntRes_BUILD_VECTOR(N);
141 break;
144 Res = PromoteIntRes_ScalarOp(N);
145 break;
146 case ISD::STEP_VECTOR: Res = PromoteIntRes_STEP_VECTOR(N); break;
148 Res = PromoteIntRes_CONCAT_VECTORS(N); break;
149
153 Res = PromoteIntRes_EXTEND_VECTOR_INREG(N); break;
154
156 Res = PromoteIntRes_VECTOR_FIND_LAST_ACTIVE(N);
157 break;
158
160 Res = PromoteIntRes_GET_ACTIVE_LANE_MASK(N);
161 break;
163 Res = PromoteIntRes_MASK_BEFOREFIRST(N);
164 break;
166 Res = PromoteIntRes_VECTOR_MATCH(N);
167 break;
168
172 Res = PromoteIntRes_PARTIAL_REDUCE_MLA(N);
173 break;
174
175 case ISD::SIGN_EXTEND:
176 case ISD::ZERO_EXTEND:
177 case ISD::ANY_EXTEND: Res = PromoteIntRes_INT_EXTEND(N); break;
178
181 case ISD::FP_TO_SINT:
182 case ISD::FP_TO_UINT: Res = PromoteIntRes_FP_TO_XINT(N); break;
183
186 Res = PromoteIntRes_FP_TO_XINT_SAT(N); break;
187
188 case ISD::FP_TO_BF16:
189 case ISD::FP_TO_FP16:
190 Res = PromoteIntRes_FP_TO_FP16_BF16(N);
191 break;
193 Res = PromoteIntRes_CONVERT_TO_ARBITRARY_FP(N);
194 break;
197 Res = PromoteIntRes_STRICT_FP_TO_FP16_BF16(N);
198 break;
199 case ISD::GET_ROUNDING: Res = PromoteIntRes_GET_ROUNDING(N); break;
200
201 case ISD::AND:
202 case ISD::OR:
203 case ISD::XOR:
204 case ISD::ADD:
205 case ISD::SUB:
206 case ISD::MUL: Res = PromoteIntRes_SimpleIntBinOp(N); break;
207
208 case ISD::ABDS:
209 case ISD::AVGCEILS:
210 case ISD::AVGFLOORS:
211 case ISD::SDIV:
212 case ISD::SREM:
213 case ISD::VP_SDIV:
214 case ISD::VP_SREM: Res = PromoteIntRes_SExtIntBinOp(N); break;
215
216 case ISD::ABDU:
217 case ISD::AVGCEILU:
218 case ISD::AVGFLOORU:
219 case ISD::UDIV:
220 case ISD::UREM:
221 case ISD::VP_UDIV:
222 case ISD::VP_UREM: Res = PromoteIntRes_ZExtIntBinOp(N); break;
223
224 case ISD::MASKED_UDIV:
225 case ISD::MASKED_UREM:
226 Res = PromoteIntRes_ZExtMaskedIntBinOp(N);
227 break;
228 case ISD::MASKED_SDIV:
229 case ISD::MASKED_SREM:
230 Res = PromoteIntRes_SExtMaskedIntBinOp(N);
231 break;
232
233 case ISD::SADDO:
234 case ISD::SSUBO: Res = PromoteIntRes_SADDSUBO(N, ResNo); break;
235 case ISD::UADDO:
236 case ISD::USUBO: Res = PromoteIntRes_UADDSUBO(N, ResNo); break;
237 case ISD::SMULO:
238 case ISD::UMULO: Res = PromoteIntRes_XMULO(N, ResNo); break;
239
240 case ISD::ADDE:
241 case ISD::SUBE:
242 case ISD::UADDO_CARRY:
243 case ISD::USUBO_CARRY: Res = PromoteIntRes_UADDSUBO_CARRY(N, ResNo); break;
244
245 case ISD::SADDO_CARRY:
246 case ISD::SSUBO_CARRY: Res = PromoteIntRes_SADDSUBO_CARRY(N, ResNo); break;
247
248 case ISD::SADDSAT:
249 case ISD::UADDSAT:
250 case ISD::SSUBSAT:
251 case ISD::USUBSAT:
252 case ISD::SSHLSAT:
253 case ISD::USHLSAT:
254 Res = PromoteIntRes_ADDSUBSHLSAT(N);
255 break;
256
257 case ISD::SCMP:
258 case ISD::UCMP:
259 Res = PromoteIntRes_CMP(N);
260 break;
261
262 case ISD::SMULFIX:
263 case ISD::SMULFIXSAT:
264 case ISD::UMULFIX:
265 case ISD::UMULFIXSAT: Res = PromoteIntRes_MULFIX(N); break;
266
267 case ISD::SDIVFIX:
268 case ISD::SDIVFIXSAT:
269 case ISD::UDIVFIX:
270 case ISD::UDIVFIXSAT: Res = PromoteIntRes_DIVFIX(N); break;
271
272 case ISD::ABS:
274 Res = PromoteIntRes_ABS(N);
275 break;
276
277 case ISD::ATOMIC_LOAD:
278 Res = PromoteIntRes_Atomic0(cast<AtomicSDNode>(N)); break;
279
291 case ISD::ATOMIC_SWAP:
292 Res = PromoteIntRes_Atomic1(cast<AtomicSDNode>(N)); break;
293
296 Res = PromoteIntRes_AtomicCmpSwap(cast<AtomicSDNode>(N), ResNo);
297 break;
298
308 Res = PromoteIntRes_VECREDUCE(N);
309 break;
310
311 case ISD::VP_REDUCE_ADD:
312 case ISD::VP_REDUCE_MUL:
313 case ISD::VP_REDUCE_AND:
314 case ISD::VP_REDUCE_OR:
315 case ISD::VP_REDUCE_XOR:
316 case ISD::VP_REDUCE_SMAX:
317 case ISD::VP_REDUCE_SMIN:
318 case ISD::VP_REDUCE_UMAX:
319 case ISD::VP_REDUCE_UMIN:
320 Res = PromoteIntRes_VP_REDUCE(N);
321 break;
322
325 Res = PromoteIntRes_LOOP_DEPENDENCE_MASK(N);
326 break;
327
328 case ISD::FREEZE:
329 Res = PromoteIntRes_FREEZE(N);
330 break;
331
332 case ISD::ROTL:
333 case ISD::ROTR:
334 Res = PromoteIntRes_Rotate(N);
335 break;
336
337 case ISD::FSHL:
338 case ISD::FSHR:
339 Res = PromoteIntRes_FunnelShift(N);
340 break;
341
342 case ISD::CLMUL:
343 case ISD::CLMULH:
344 case ISD::CLMULR:
345 Res = PromoteIntRes_CLMUL(N);
346 break;
347
348 case ISD::PEXT:
349 Res = PromoteIntRes_PEXT(N);
350 break;
351
352 case ISD::PDEP:
353 Res = PromoteIntRes_PDEP(N);
354 break;
355
356 case ISD::MULHS:
357 case ISD::MULHU:
358 Res = PromoteIntRes_MULH(N);
359 break;
360
361 case ISD::IS_FPCLASS:
362 Res = PromoteIntRes_IS_FPCLASS(N);
363 break;
364 case ISD::FFREXP:
365 Res = PromoteIntRes_FFREXP(N);
366 break;
367
368 case ISD::LRINT:
369 case ISD::LLRINT:
370 Res = PromoteIntRes_XRINT(N);
371 break;
372
373 case ISD::PATCHPOINT:
374 Res = PromoteIntRes_PATCHPOINT(N);
375 break;
377 Res = PromoteIntRes_READ_REGISTER(N);
378 break;
379 }
380
381 // If the result is null then the sub-method took care of registering it.
382 if (Res.getNode())
383 SetPromotedInteger(SDValue(N, ResNo), Res);
384}
385
386SDValue DAGTypeLegalizer::PromoteIntRes_MERGE_VALUES(SDNode *N,
387 unsigned ResNo) {
388 SDValue Op = DisintegrateMERGE_VALUES(N, ResNo);
389 return GetPromotedInteger(Op);
390}
391
392SDValue DAGTypeLegalizer::PromoteIntRes_LOOP_DEPENDENCE_MASK(SDNode *N) {
393 EVT VT = N->getValueType(0);
394 EVT NewVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
395 return DAG.getNode(N->getOpcode(), SDLoc(N), NewVT, N->ops());
396}
397
398SDValue DAGTypeLegalizer::PromoteIntRes_AssertSext(SDNode *N) {
399 // Sign-extend the new bits, and continue the assertion.
400 SDValue Op = SExtPromotedInteger(N->getOperand(0));
401 return DAG.getNode(ISD::AssertSext, SDLoc(N),
402 Op.getValueType(), Op, N->getOperand(1));
403}
404
405SDValue DAGTypeLegalizer::PromoteIntRes_AssertZext(SDNode *N) {
406 // Zero the new bits, and continue the assertion.
407 SDValue Op = ZExtPromotedInteger(N->getOperand(0));
408 return DAG.getNode(ISD::AssertZext, SDLoc(N),
409 Op.getValueType(), Op, N->getOperand(1));
410}
411
412SDValue DAGTypeLegalizer::PromoteIntRes_Atomic0(AtomicSDNode *N) {
413 EVT ResVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
414 ISD::LoadExtType ExtType = N->getExtensionType();
415 if (ExtType == ISD::NON_EXTLOAD) {
416 switch (TLI.getExtendForAtomicOps()) {
417 case ISD::SIGN_EXTEND:
418 ExtType = ISD::SEXTLOAD;
419 break;
420 case ISD::ZERO_EXTEND:
421 ExtType = ISD::ZEXTLOAD;
422 break;
423 case ISD::ANY_EXTEND:
424 ExtType = ISD::EXTLOAD;
425 break;
426 default:
427 llvm_unreachable("Invalid atomic op extension");
428 }
429 }
430
431 SDValue Res =
432 DAG.getAtomicLoad(ExtType, SDLoc(N), N->getMemoryVT(), ResVT,
433 N->getChain(), N->getBasePtr(), N->getMemOperand());
434
435 // Legalize the chain result - switch anything that used the old chain to
436 // use the new one.
437 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
438 return Res;
439}
440
441SDValue DAGTypeLegalizer::PromoteIntRes_Atomic1(AtomicSDNode *N) {
442 SDValue Op2 = N->getOperand(2);
443 switch (TLI.getExtendForAtomicRMWArg(N->getOpcode())) {
444 case ISD::SIGN_EXTEND:
445 Op2 = SExtPromotedInteger(Op2);
446 break;
447 case ISD::ZERO_EXTEND:
448 Op2 = ZExtPromotedInteger(Op2);
449 break;
450 case ISD::ANY_EXTEND:
451 Op2 = GetPromotedInteger(Op2);
452 break;
453 default:
454 llvm_unreachable("Invalid atomic op extension");
455 }
456 SDValue Res = DAG.getAtomic(N->getOpcode(), SDLoc(N),
457 N->getMemoryVT(),
458 N->getChain(), N->getBasePtr(),
459 Op2, N->getMemOperand());
460 // Legalize the chain result - switch anything that used the old chain to
461 // use the new one.
462 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
463 return Res;
464}
465
466SDValue DAGTypeLegalizer::PromoteIntRes_AtomicCmpSwap(AtomicSDNode *N,
467 unsigned ResNo) {
468 if (ResNo == 1) {
470 EVT SVT = getSetCCResultType(N->getOperand(2).getValueType());
471 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(1));
472
473 // Only use the result of getSetCCResultType if it is legal,
474 // otherwise just use the promoted result type (NVT).
475 if (!TLI.isTypeLegal(SVT))
476 SVT = NVT;
477
478 SDVTList VTs = DAG.getVTList(N->getValueType(0), SVT, MVT::Other);
479 SDValue Res = DAG.getAtomicCmpSwap(
480 ISD::ATOMIC_CMP_SWAP_WITH_SUCCESS, SDLoc(N), N->getMemoryVT(), VTs,
481 N->getChain(), N->getBasePtr(), N->getOperand(2), N->getOperand(3),
482 N->getMemOperand());
483 ReplaceValueWith(SDValue(N, 0), Res.getValue(0));
484 ReplaceValueWith(SDValue(N, 2), Res.getValue(2));
485 return DAG.getSExtOrTrunc(Res.getValue(1), SDLoc(N), NVT);
486 }
487
488 // Op2 is used for the comparison and thus must be extended according to the
489 // target's atomic operations. Op3 is merely stored and so can be left alone.
490 SDValue Op2 = N->getOperand(2);
491 SDValue Op3 = GetPromotedInteger(N->getOperand(3));
492 switch (TLI.getExtendForAtomicCmpSwapArg()) {
493 case ISD::SIGN_EXTEND:
494 Op2 = SExtPromotedInteger(Op2);
495 break;
496 case ISD::ZERO_EXTEND:
497 Op2 = ZExtPromotedInteger(Op2);
498 break;
499 case ISD::ANY_EXTEND:
500 Op2 = GetPromotedInteger(Op2);
501 break;
502 default:
503 llvm_unreachable("Invalid atomic op extension");
504 }
505
506 SDVTList VTs =
507 DAG.getVTList(Op2.getValueType(), N->getValueType(1), MVT::Other);
508 SDValue Res = DAG.getAtomicCmpSwap(
509 N->getOpcode(), SDLoc(N), N->getMemoryVT(), VTs, N->getChain(),
510 N->getBasePtr(), Op2, Op3, N->getMemOperand());
511 // Update the use to N with the newly created Res.
512 for (unsigned i = 1, NumResults = N->getNumValues(); i < NumResults; ++i)
513 ReplaceValueWith(SDValue(N, i), Res.getValue(i));
514 return Res;
515}
516
517SDValue DAGTypeLegalizer::PromoteIntRes_BITCAST(SDNode *N) {
518 SDValue InOp = N->getOperand(0);
519 EVT InVT = InOp.getValueType();
520 EVT NInVT = TLI.getTypeToTransformTo(*DAG.getContext(), InVT);
521 EVT OutVT = N->getValueType(0);
522 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
523 SDLoc dl(N);
524
525 switch (getTypeAction(InVT)) {
527 break;
529 if (NOutVT.bitsEq(NInVT) && !NOutVT.isVector() && !NInVT.isVector())
530 // The input promotes to the same size. Convert the promoted value.
531 return DAG.getNode(ISD::BITCAST, dl, NOutVT, GetPromotedInteger(InOp));
532 break;
534 // Promote the integer operand by hand.
535 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, GetSoftenedFloat(InOp));
537 // Promote the integer operand by hand.
538 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, GetSoftPromotedHalf(InOp));
541 break;
543 // Convert the element to an integer and promote it by hand.
544 if (!NOutVT.isVector())
545 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT,
546 BitConvertToInteger(GetScalarizedVector(InOp)));
547 break;
549 report_fatal_error("scalarization of scalable vectors is not supported");
551 if (!NOutVT.isVector()) {
552 // For example, i32 = BITCAST v2i16 on alpha. Convert the split
553 // pieces of the input into integers and reassemble in the final type.
554 SDValue Lo, Hi;
555 GetSplitVector(N->getOperand(0), Lo, Hi);
556 Lo = BitConvertToInteger(Lo);
557 Hi = BitConvertToInteger(Hi);
558
559 if (DAG.getDataLayout().isBigEndian())
560 std::swap(Lo, Hi);
561
562 InOp = DAG.getNode(ISD::ANY_EXTEND, dl,
563 EVT::getIntegerVT(*DAG.getContext(),
564 NOutVT.getSizeInBits()),
565 JoinIntegers(Lo, Hi));
566 return DAG.getNode(ISD::BITCAST, dl, NOutVT, InOp);
567 }
568 break;
569 }
571 // The input is widened to the same size. Convert to the widened value.
572 // Make sure that the outgoing value is not a vector, because this would
573 // make us bitcast between two vectors which are legalized in different ways.
574 if (NOutVT.bitsEq(NInVT) && !NOutVT.isVector()) {
575 SDValue Res =
576 DAG.getNode(ISD::BITCAST, dl, NOutVT, GetWidenedVector(InOp));
577
578 // For big endian targets we need to shift the casted value or the
579 // interesting bits will end up at the wrong place.
580 if (DAG.getDataLayout().isBigEndian()) {
581 unsigned ShiftAmt = NInVT.getSizeInBits() - InVT.getSizeInBits();
582 assert(ShiftAmt < NOutVT.getSizeInBits() && "Too large shift amount!");
583 Res = DAG.getNode(ISD::SRL, dl, NOutVT, Res,
584 DAG.getShiftAmountConstant(ShiftAmt, NOutVT, dl));
585 }
586 return Res;
587 }
588 // If the output type is also a vector and widening it to the same size
589 // as the widened input type would be a legal type, we can widen the bitcast
590 // and handle the promotion after.
591 if (NOutVT.isVector()) {
592 TypeSize WidenInSize = NInVT.getSizeInBits();
593 TypeSize OutSize = OutVT.getSizeInBits();
594 if (WidenInSize.hasKnownScalarFactor(OutSize)) {
595 unsigned Scale = WidenInSize.getKnownScalarFactor(OutSize);
596 EVT WideOutVT =
597 EVT::getVectorVT(*DAG.getContext(), OutVT.getVectorElementType(),
598 OutVT.getVectorElementCount() * Scale);
599 if (isTypeLegal(WideOutVT)) {
600 InOp = DAG.getBitcast(WideOutVT, GetWidenedVector(InOp));
601 InOp = DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, OutVT, InOp,
602 DAG.getVectorIdxConstant(0, dl));
603 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, InOp);
604 }
605 }
606 }
607 }
608
609 // TODO: Handle big endian
610 if (!NOutVT.isVector() && InOp.getValueType().isVector() &&
611 DAG.getDataLayout().isLittleEndian()) {
612 // Pad the vector operand with undef and cast to a wider integer.
613 EVT EltVT = InOp.getValueType().getVectorElementType();
614 TypeSize EltSize = EltVT.getSizeInBits();
615 TypeSize OutSize = NOutVT.getSizeInBits();
616
617 if (OutSize.hasKnownScalarFactor(EltSize)) {
618 unsigned NumEltsWithPadding = OutSize.getKnownScalarFactor(EltSize);
619 EVT WideVecVT =
620 EVT::getVectorVT(*DAG.getContext(), EltVT, NumEltsWithPadding);
621
622 if (isTypeLegal(WideVecVT)) {
623 SDValue Inserted = DAG.getNode(ISD::INSERT_SUBVECTOR, dl, WideVecVT,
624 DAG.getUNDEF(WideVecVT), InOp,
625 DAG.getVectorIdxConstant(0, dl));
626
627 return DAG.getNode(ISD::BITCAST, dl, NOutVT, Inserted);
628 }
629 }
630 }
631
632 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT,
633 CreateStackStoreLoad(InOp, OutVT));
634}
635
636SDValue DAGTypeLegalizer::PromoteIntRes_FREEZE(SDNode *N) {
637 SDValue V = GetPromotedInteger(N->getOperand(0));
638 return DAG.getNode(ISD::FREEZE, SDLoc(N),
639 V.getValueType(), V);
640}
641
642SDValue DAGTypeLegalizer::PromoteIntRes_BSWAP(SDNode *N) {
643 SDValue Op = GetPromotedInteger(N->getOperand(0));
644 EVT OVT = N->getValueType(0);
645 EVT NVT = Op.getValueType();
646 SDLoc dl(N);
647
648 // If the larger BSWAP isn't supported by the target, try to expand now.
649 // If we expand later we'll end up with more operations since we lost the
650 // original type. We only do this for scalars since we have a shuffle
651 // based lowering for vectors in LegalizeVectorOps.
652 if (!OVT.isVector() &&
653 !TLI.isOperationLegalOrCustomOrPromote(ISD::BSWAP, NVT)) {
654 if (SDValue Res = TLI.expandBSWAP(N, DAG))
655 return DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Res);
656 }
657
658 unsigned DiffBits = NVT.getScalarSizeInBits() - OVT.getScalarSizeInBits();
659 SDValue ShAmt = DAG.getShiftAmountConstant(DiffBits, NVT, dl);
660 return DAG.getNode(ISD::SRL, dl, NVT, DAG.getNode(ISD::BSWAP, dl, NVT, Op),
661 ShAmt);
662}
663
664SDValue DAGTypeLegalizer::PromoteIntRes_BITREVERSE(SDNode *N) {
665 SDValue Op = GetPromotedInteger(N->getOperand(0));
666 EVT OVT = N->getValueType(0);
667 EVT NVT = Op.getValueType();
668 SDLoc dl(N);
669
670 // If the larger BITREVERSE isn't supported by the target, try to expand now.
671 // If we expand later we'll end up with more operations since we lost the
672 // original type. We only do this for scalars since we have a shuffle
673 // based lowering for vectors in LegalizeVectorOps.
674 if (!OVT.isVector() && OVT.isSimple() &&
675 !TLI.isOperationLegalOrCustomOrPromote(ISD::BITREVERSE, NVT)) {
676 if (SDValue Res = TLI.expandBITREVERSE(N, DAG))
677 return DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Res);
678 }
679
680 unsigned DiffBits = NVT.getScalarSizeInBits() - OVT.getScalarSizeInBits();
681 SDValue ShAmt = DAG.getShiftAmountConstant(DiffBits, NVT, dl);
682 return DAG.getNode(ISD::SRL, dl, NVT,
683 DAG.getNode(ISD::BITREVERSE, dl, NVT, Op), ShAmt);
684}
685
686SDValue DAGTypeLegalizer::PromoteIntRes_BUILD_PAIR(SDNode *N) {
687 // The pair element type may be legal, or may not promote to the same type as
688 // the result, for example i14 = BUILD_PAIR (i7, i7). Handle all cases.
689 return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N),
690 TLI.getTypeToTransformTo(*DAG.getContext(),
691 N->getValueType(0)), JoinIntegers(N->getOperand(0),
692 N->getOperand(1)));
693}
694
695SDValue DAGTypeLegalizer::PromoteIntRes_Constant(SDNode *N) {
696 EVT VT = N->getValueType(0);
697 // FIXME there is no actual debug info here
698 SDLoc dl(N);
699 // Zero extend things like i1, sign extend everything else. It shouldn't
700 // matter in theory which one we pick, but this tends to give better code?
702 SDValue Result = DAG.getNode(Opc, dl,
703 TLI.getTypeToTransformTo(*DAG.getContext(), VT),
704 SDValue(N, 0));
705 assert(isa<ConstantSDNode>(Result) && "Didn't constant fold ext?");
706 return Result;
707}
708
709SDValue DAGTypeLegalizer::PromoteIntRes_CTLZ(SDNode *N) {
710 EVT OVT = N->getValueType(0);
711 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), OVT);
712 SDLoc dl(N);
713
714 // If the larger CTLZ isn't supported by the target, try to expand now.
715 // If we expand later we'll end up with more operations since we lost the
716 // original type.
717 if (!OVT.isVector() && TLI.isTypeLegal(NVT) &&
718 !TLI.isOperationLegalOrCustomOrPromote(ISD::CTLZ, NVT) &&
719 !TLI.isOperationLegalOrCustomOrPromote(ISD::CTLZ_ZERO_POISON, NVT)) {
720 if (SDValue Result = TLI.expandCTLZ(N, DAG)) {
721 Result = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Result);
722 return Result;
723 }
724 }
725
726 unsigned CtlzOpcode = N->getOpcode();
727 if (CtlzOpcode == ISD::CTLZ) {
728 // Subtract off the extra leading bits in the bigger type.
729 SDValue ExtractLeadingBits = DAG.getConstant(
730 NVT.getScalarSizeInBits() - OVT.getScalarSizeInBits(), dl, NVT);
731 // Zero extend to the promoted type and do the count there.
732 SDValue Op = ZExtPromotedInteger(N->getOperand(0));
733
734 // At this stage SUB is guaranteed to be positive no-wrap,
735 // that to be used in further KnownBits optimizations.
736 return DAG.getNode(ISD::SUB, dl, NVT,
737 DAG.getNode(N->getOpcode(), dl, NVT, Op),
738 ExtractLeadingBits, SDNodeFlags::NoUnsignedWrap);
739 }
740 if (CtlzOpcode == ISD::CTLZ_ZERO_POISON) {
741 // Any Extend the argument
742 SDValue Op = GetPromotedInteger(N->getOperand(0));
743 // Op = Op << (sizeinbits(NVT) - sizeinbits(Old VT))
744 unsigned SHLAmount = NVT.getScalarSizeInBits() - OVT.getScalarSizeInBits();
745 auto ShiftConst =
746 DAG.getShiftAmountConstant(SHLAmount, Op.getValueType(), dl);
747 Op = DAG.getNode(ISD::SHL, dl, NVT, Op, ShiftConst);
748 return DAG.getNode(CtlzOpcode, dl, NVT, Op);
749 }
750 llvm_unreachable("Invalid CTLZ Opcode");
751}
752
753SDValue DAGTypeLegalizer::PromoteIntRes_CTLS(SDNode *N) {
754 EVT OVT = N->getValueType(0);
755 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), OVT);
756 SDLoc dl(N);
757
758 SDValue ExtractLeadingBits = DAG.getConstant(
759 NVT.getScalarSizeInBits() - OVT.getScalarSizeInBits(), dl, NVT);
760
761 SDValue Op = SExtPromotedInteger(N->getOperand(0));
762 return DAG.getNode(ISD::SUB, dl, NVT, DAG.getNode(ISD::CTLS, dl, NVT, Op),
763 ExtractLeadingBits);
764}
765
766SDValue DAGTypeLegalizer::PromoteIntRes_CTPOP_PARITY(SDNode *N) {
767 EVT OVT = N->getValueType(0);
768 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), OVT);
769
770 // If the larger CTPOP isn't supported by the target, try to expand now.
771 // If we expand later we'll end up with more operations since we lost the
772 // original type.
773 // TODO: Expand ISD::PARITY. Need to move ExpandPARITY from LegalizeDAG to
774 // TargetLowering.
775 if (N->getOpcode() == ISD::CTPOP && !OVT.isVector() && TLI.isTypeLegal(NVT) &&
776 !TLI.isOperationLegalOrCustomOrPromote(ISD::CTPOP, NVT)) {
777 if (SDValue Result = TLI.expandCTPOP(N, DAG)) {
778 Result = DAG.getNode(ISD::ANY_EXTEND, SDLoc(N), NVT, Result);
779 return Result;
780 }
781 }
782
783 // Zero extend to the promoted type and do the count or parity there.
784 SDValue Op = ZExtPromotedInteger(N->getOperand(0));
785 return DAG.getNode(N->getOpcode(), SDLoc(N), Op.getValueType(), Op);
786}
787
788SDValue DAGTypeLegalizer::PromoteIntRes_CTTZ(SDNode *N) {
789 SDValue Op = GetPromotedInteger(N->getOperand(0));
790 EVT OVT = N->getValueType(0);
791 EVT NVT = Op.getValueType();
792 SDLoc dl(N);
793
794 // If the larger CTTZ isn't supported by the target, try to expand now.
795 // If we expand later we'll end up with more operations since we lost the
796 // original type. Don't expand if we can use CTPOP or CTLZ expansion on the
797 // larger type.
798 if (!OVT.isVector() && TLI.isTypeLegal(NVT) &&
799 !TLI.isOperationLegalOrCustomOrPromote(ISD::CTTZ, NVT) &&
800 !TLI.isOperationLegalOrCustomOrPromote(ISD::CTTZ_ZERO_POISON, NVT) &&
801 !TLI.isOperationLegal(ISD::CTPOP, NVT) &&
802 !TLI.isOperationLegal(ISD::CTLZ, NVT)) {
803 if (SDValue Result = TLI.expandCTTZ(N, DAG)) {
804 Result = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Result);
805 return Result;
806 }
807 }
808
809 unsigned NewOpc = N->getOpcode();
810 if (NewOpc == ISD::CTTZ) {
811 // The count is the same in the promoted type except if the original
812 // value was zero. This can be handled by setting the bit just off
813 // the top of the original type.
814 auto TopBit = APInt::getOneBitSet(NVT.getScalarSizeInBits(),
815 OVT.getScalarSizeInBits());
816 Op = DAG.getNode(ISD::OR, dl, NVT, Op, DAG.getConstant(TopBit, dl, NVT));
817 NewOpc = ISD::CTTZ_ZERO_POISON;
818 }
819 return DAG.getNode(NewOpc, dl, NVT, Op);
820}
821
822SDValue DAGTypeLegalizer::PromoteIntRes_VP_CttzElements(SDNode *N) {
823 SDLoc DL(N);
824 EVT NewVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
825 return DAG.getNode(N->getOpcode(), DL, NewVT, N->ops());
826}
827
828SDValue DAGTypeLegalizer::PromoteIntRes_EXTRACT_VECTOR_ELT(SDNode *N) {
829 SDLoc dl(N);
830 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
831
832 SDValue Op0 = N->getOperand(0);
833 SDValue Op1 = N->getOperand(1);
834
835 // If the input also needs to be promoted, do that first so we can get a
836 // get a good idea for the output type.
837 if (TLI.getTypeAction(*DAG.getContext(), Op0.getValueType())
839 SDValue In = GetPromotedInteger(Op0);
840
841 // If the new type is larger than NVT, use it. We probably won't need to
842 // promote it again.
843 EVT SVT = In.getValueType().getScalarType();
844 if (SVT.bitsGE(NVT)) {
845 SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, SVT, In, Op1);
846 return DAG.getAnyExtOrTrunc(Ext, dl, NVT);
847 }
848 }
849
850 return DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, NVT, Op0, Op1);
851}
852
853SDValue DAGTypeLegalizer::PromoteIntRes_FP_TO_XINT(SDNode *N) {
854 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
855 unsigned NewOpc =
856 TLI.getPreferredFPToIntOpcode(N->getOpcode(), N->getValueType(0), NVT);
857 SDLoc dl(N);
858
859 SDValue Res;
860 if (N->isStrictFPOpcode()) {
861 Res = DAG.getNode(NewOpc, dl, {NVT, MVT::Other},
862 {N->getOperand(0), N->getOperand(1)});
863 // Legalize the chain result - switch anything that used the old chain to
864 // use the new one.
865 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
866 } else {
867 Res = DAG.getNode(NewOpc, dl, NVT, N->getOperand(0));
868 }
869
870 // Assert that the converted value fits in the original type. If it doesn't
871 // (eg: because the value being converted is too big), then the result of the
872 // original operation was undefined anyway, so the assert is still correct.
873 //
874 // NOTE: fp-to-uint to fp-to-sint promotion guarantees zero extend. For example:
875 // before legalization: fp-to-uint16, 65534. -> 0xfffe
876 // after legalization: fp-to-sint32, 65534. -> 0x0000fffe
877 return DAG.getNode((N->getOpcode() == ISD::FP_TO_UINT ||
878 N->getOpcode() == ISD::STRICT_FP_TO_UINT)
881 dl, NVT, Res,
882 DAG.getValueType(N->getValueType(0).getScalarType()));
883}
884
885SDValue DAGTypeLegalizer::PromoteIntRes_FP_TO_XINT_SAT(SDNode *N) {
886 // Promote the result type, while keeping the original width in Op1.
887 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
888 SDLoc dl(N);
889 return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0),
890 N->getOperand(1));
891}
892
893SDValue DAGTypeLegalizer::PromoteIntRes_FP_TO_FP16_BF16(SDNode *N) {
894 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
895 SDLoc dl(N);
896
897 return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
898}
899
900// TODO: CONVERT_TO_ARBITRARY_FP also needs an ExpandIntegerResult handler for
901// wider arbitrary FP formats whose integer result requires expansion.
902SDValue DAGTypeLegalizer::PromoteIntRes_CONVERT_TO_ARBITRARY_FP(SDNode *N) {
903 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
904 SDLoc dl(N);
905
906 return DAG.getNode(ISD::CONVERT_TO_ARBITRARY_FP, dl, NVT, N->getOperand(0),
907 N->getOperand(1), N->getOperand(2), N->getOperand(3));
908}
909
910SDValue DAGTypeLegalizer::PromoteIntRes_STRICT_FP_TO_FP16_BF16(SDNode *N) {
911 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
912 SDLoc dl(N);
913
914 SDValue Res = DAG.getNode(N->getOpcode(), dl, DAG.getVTList(NVT, MVT::Other),
915 N->getOperand(0), N->getOperand(1));
916 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
917 return Res;
918}
919
920SDValue DAGTypeLegalizer::PromoteIntRes_XRINT(SDNode *N) {
921 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
922 SDLoc dl(N);
923 return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
924}
925
926SDValue DAGTypeLegalizer::PromoteIntRes_GET_ROUNDING(SDNode *N) {
927 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
928 SDLoc dl(N);
929
930 SDValue Res =
931 DAG.getNode(N->getOpcode(), dl, {NVT, MVT::Other}, N->getOperand(0));
932
933 // Legalize the chain result - switch anything that used the old chain to
934 // use the new one.
935 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
936 return Res;
937}
938
939SDValue DAGTypeLegalizer::PromoteIntRes_INT_EXTEND(SDNode *N) {
940 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
941 SDLoc dl(N);
942
943 if (getTypeAction(N->getOperand(0).getValueType())
945 SDValue Res = GetPromotedInteger(N->getOperand(0));
946 assert(Res.getValueType().bitsLE(NVT) && "Extension doesn't make sense!");
947
948 // If the result and operand types are the same after promotion, simplify
949 // to an in-register extension. Unless this is a VP_*_EXTEND.
950 if (NVT == Res.getValueType() && N->getNumOperands() == 1) {
951 // The high bits are not guaranteed to be anything. Insert an extend.
952 if (N->getOpcode() == ISD::SIGN_EXTEND)
953 return DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, NVT, Res,
954 DAG.getValueType(N->getOperand(0).getValueType()));
955 if (N->getOpcode() == ISD::ZERO_EXTEND)
956 return DAG.getZeroExtendInReg(Res, dl, N->getOperand(0).getValueType());
957 assert(N->getOpcode() == ISD::ANY_EXTEND && "Unknown integer extension!");
958 return Res;
959 }
960 }
961
962 // Otherwise, just extend the original operand all the way to the larger type.
963 return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
964}
965
966SDValue DAGTypeLegalizer::PromoteIntRes_LOAD(LoadSDNode *N) {
967 assert(ISD::isUNINDEXEDLoad(N) && "Indexed load during type legalization!");
968 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
969 ISD::LoadExtType ExtType =
970 ISD::isNON_EXTLoad(N) ? ISD::EXTLOAD : N->getExtensionType();
971 SDLoc dl(N);
972 SDValue Res = DAG.getExtLoad(ExtType, dl, NVT, N->getChain(), N->getBasePtr(),
973 N->getMemoryVT(), N->getMemOperand());
974
975 // Legalize the chain result - switch anything that used the old chain to
976 // use the new one.
977 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
978 return Res;
979}
980
981SDValue DAGTypeLegalizer::PromoteIntRes_VP_LOAD(VPLoadSDNode *N) {
982 assert(!N->isIndexed() && "Indexed vp_load during type legalization!");
983 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
984 ISD::LoadExtType ExtType = (N->getExtensionType() == ISD::NON_EXTLOAD)
986 : N->getExtensionType();
987 SDLoc dl(N);
988 SDValue Res =
989 DAG.getExtLoadVP(ExtType, dl, NVT, N->getChain(), N->getBasePtr(),
990 N->getMask(), N->getVectorLength(), N->getMemoryVT(),
991 N->getMemOperand(), N->isExpandingLoad());
992 // Legalize the chain result - switch anything that used the old chain to
993 // use the new one.
994 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
995 return Res;
996}
997
998SDValue DAGTypeLegalizer::PromoteIntRes_MLOAD(MaskedLoadSDNode *N) {
999 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1000 SDValue ExtPassThru = GetPromotedInteger(N->getPassThru());
1001
1002 ISD::LoadExtType ExtType = N->getExtensionType();
1003 if (ExtType == ISD::NON_EXTLOAD)
1004 ExtType = ISD::EXTLOAD;
1005
1006 SDLoc dl(N);
1007 SDValue Res = DAG.getMaskedLoad(NVT, dl, N->getChain(), N->getBasePtr(),
1008 N->getOffset(), N->getMask(), ExtPassThru,
1009 N->getMemoryVT(), N->getMemOperand(),
1010 N->getAddressingMode(), ExtType,
1011 N->isExpandingLoad());
1012 // Legalize the chain result - switch anything that used the old chain to
1013 // use the new one.
1014 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
1015 return Res;
1016}
1017
1018SDValue DAGTypeLegalizer::PromoteIntRes_MGATHER(MaskedGatherSDNode *N) {
1019 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1020 SDValue ExtPassThru = GetPromotedInteger(N->getPassThru());
1021 assert(NVT == ExtPassThru.getValueType() &&
1022 "Gather result type and the passThru argument type should be the same");
1023
1024 ISD::LoadExtType ExtType = N->getExtensionType();
1025 if (ExtType == ISD::NON_EXTLOAD)
1026 ExtType = ISD::EXTLOAD;
1027
1028 SDLoc dl(N);
1029 SDValue Ops[] = {N->getChain(), ExtPassThru, N->getMask(), N->getBasePtr(),
1030 N->getIndex(), N->getScale() };
1031 SDValue Res = DAG.getMaskedGather(DAG.getVTList(NVT, MVT::Other),
1032 N->getMemoryVT(), dl, Ops,
1033 N->getMemOperand(), N->getIndexType(),
1034 ExtType);
1035 // Legalize the chain result - switch anything that used the old chain to
1036 // use the new one.
1037 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
1038 return Res;
1039}
1040
1041SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_COMPRESS(SDNode *N) {
1042 SDValue Vec = GetPromotedInteger(N->getOperand(0));
1043 SDValue Passthru = GetPromotedInteger(N->getOperand(2));
1044 return DAG.getNode(ISD::VECTOR_COMPRESS, SDLoc(N), Vec.getValueType(), Vec,
1045 N->getOperand(1), Passthru);
1046}
1047
1048/// Promote the overflow flag of an overflowing arithmetic node.
1049SDValue DAGTypeLegalizer::PromoteIntRes_Overflow(SDNode *N) {
1050 // Change the return type of the boolean result while obeying
1051 // getSetCCResultType.
1052 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(1));
1053 EVT VT = N->getValueType(0);
1054 EVT SVT = getSetCCResultType(VT);
1055 SDValue Ops[3] = { N->getOperand(0), N->getOperand(1) };
1056 unsigned NumOps = N->getNumOperands();
1057 assert(NumOps <= 3 && "Too many operands");
1058 if (NumOps == 3)
1059 Ops[2] = PromoteTargetBoolean(N->getOperand(2), VT);
1060
1061 SDLoc dl(N);
1062 SDValue Res = DAG.getNode(N->getOpcode(), dl, DAG.getVTList(VT, SVT),
1063 ArrayRef(Ops, NumOps));
1064
1065 // Modified the sum result - switch anything that used the old sum to use
1066 // the new one.
1067 ReplaceValueWith(SDValue(N, 0), Res);
1068
1069 // Convert to the expected type.
1070 return DAG.getBoolExtOrTrunc(Res.getValue(1), dl, NVT, VT);
1071}
1072
1073SDValue DAGTypeLegalizer::PromoteIntRes_ADDSUBSHLSAT(SDNode *N) {
1074 // If the promoted type is legal, we can convert this to:
1075 // 1. ANY_EXTEND iN to iM
1076 // 2. SHL by M-N
1077 // 3. [US][ADD|SUB|SHL]SAT
1078 // 4. L/ASHR by M-N
1079 // Else it is more efficient to convert this to a min and a max
1080 // operation in the higher precision arithmetic.
1081 SDLoc dl(N);
1082 SDValue Op1 = N->getOperand(0);
1083 SDValue Op2 = N->getOperand(1);
1084
1085 unsigned Opcode = N->getOpcode();
1086 unsigned OldBits = Op1.getScalarValueSizeInBits();
1087
1088 // USUBSAT can always be promoted as long as we have zero/sign-extended the
1089 // args.
1090 if (Opcode == ISD::USUBSAT) {
1091 SExtOrZExtPromotedOperands(Op1, Op2);
1092 return DAG.getNode(ISD::USUBSAT, dl, Op1.getValueType(), Op1, Op2);
1093 }
1094
1095 if (Opcode == ISD::UADDSAT) {
1096 EVT OVT = Op1.getValueType();
1097 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), OVT);
1098 // We can promote if we use sign-extend. Do this if the target prefers.
1099 if (TLI.isSExtCheaperThanZExt(OVT, NVT)) {
1100 Op1 = SExtPromotedInteger(Op1);
1101 Op2 = SExtPromotedInteger(Op2);
1102 return DAG.getNode(ISD::UADDSAT, dl, NVT, Op1, Op2);
1103 }
1104
1105 Op1 = ZExtPromotedInteger(Op1);
1106 Op2 = ZExtPromotedInteger(Op2);
1107 unsigned NewBits = NVT.getScalarSizeInBits();
1108 APInt MaxVal = APInt::getLowBitsSet(NewBits, OldBits);
1109 SDValue SatMax = DAG.getConstant(MaxVal, dl, NVT);
1110 SDValue Add = DAG.getNode(ISD::ADD, dl, NVT, Op1, Op2);
1111 return DAG.getNode(ISD::UMIN, dl, NVT, Add, SatMax);
1112 }
1113
1114 bool IsShift = Opcode == ISD::USHLSAT || Opcode == ISD::SSHLSAT;
1115
1116 // FIXME: We need vp-aware PromotedInteger functions.
1117 if (IsShift) {
1118 Op1 = GetPromotedInteger(Op1);
1119 if (getTypeAction(Op2.getValueType()) == TargetLowering::TypePromoteInteger)
1120 Op2 = ZExtPromotedInteger(Op2);
1121 } else {
1122 Op1 = SExtPromotedInteger(Op1);
1123 Op2 = SExtPromotedInteger(Op2);
1124 }
1125 EVT PromotedType = Op1.getValueType();
1126 unsigned NewBits = PromotedType.getScalarSizeInBits();
1127
1128 // Shift cannot use a min/max expansion, we can't detect overflow if all of
1129 // the bits have been shifted out.
1130 if (IsShift || TLI.isOperationLegal(Opcode, PromotedType)) {
1131 unsigned ShiftOp;
1132 switch (Opcode) {
1133 case ISD::SADDSAT:
1134 case ISD::SSUBSAT:
1135 case ISD::SSHLSAT:
1136 ShiftOp = ISD::SRA;
1137 break;
1138 case ISD::USHLSAT:
1139 ShiftOp = ISD::SRL;
1140 break;
1141 default:
1142 llvm_unreachable("Expected opcode to be signed or unsigned saturation "
1143 "addition, subtraction or left shift");
1144 }
1145
1146 unsigned SHLAmount = NewBits - OldBits;
1147 SDValue ShiftAmount =
1148 DAG.getShiftAmountConstant(SHLAmount, PromotedType, dl);
1149 Op1 = DAG.getNode(ISD::SHL, dl, PromotedType, Op1, ShiftAmount);
1150 if (!IsShift)
1151 Op2 = DAG.getNode(ISD::SHL, dl, PromotedType, Op2, ShiftAmount);
1152
1153 SDValue Result = DAG.getNode(Opcode, dl, PromotedType, Op1, Op2);
1154 return DAG.getNode(ShiftOp, dl, PromotedType, Result, ShiftAmount);
1155 }
1156
1157 unsigned AddOp = Opcode == ISD::SADDSAT ? ISD::ADD : ISD::SUB;
1158 APInt MinVal = APInt::getSignedMinValue(OldBits).sext(NewBits);
1159 APInt MaxVal = APInt::getSignedMaxValue(OldBits).sext(NewBits);
1160 SDValue SatMin = DAG.getConstant(MinVal, dl, PromotedType);
1161 SDValue SatMax = DAG.getConstant(MaxVal, dl, PromotedType);
1162 SDValue Result = DAG.getNode(AddOp, dl, PromotedType, Op1, Op2);
1163 Result = DAG.getNode(ISD::SMIN, dl, PromotedType, Result, SatMax);
1164 Result = DAG.getNode(ISD::SMAX, dl, PromotedType, Result, SatMin);
1165 return Result;
1166}
1167
1168SDValue DAGTypeLegalizer::PromoteIntRes_MULFIX(SDNode *N) {
1169 // Can just promote the operands then continue with operation.
1170 SDLoc dl(N);
1171 SDValue Op1Promoted, Op2Promoted;
1172 bool Signed =
1173 N->getOpcode() == ISD::SMULFIX || N->getOpcode() == ISD::SMULFIXSAT;
1174 bool Saturating =
1175 N->getOpcode() == ISD::SMULFIXSAT || N->getOpcode() == ISD::UMULFIXSAT;
1176 if (Signed) {
1177 Op1Promoted = SExtPromotedInteger(N->getOperand(0));
1178 Op2Promoted = SExtPromotedInteger(N->getOperand(1));
1179 } else {
1180 Op1Promoted = ZExtPromotedInteger(N->getOperand(0));
1181 Op2Promoted = ZExtPromotedInteger(N->getOperand(1));
1182 }
1183 EVT OldType = N->getOperand(0).getValueType();
1184 EVT PromotedType = Op1Promoted.getValueType();
1185 unsigned DiffSize =
1186 PromotedType.getScalarSizeInBits() - OldType.getScalarSizeInBits();
1187
1188 if (Saturating) {
1189 // Promoting the operand and result values changes the saturation width,
1190 // which is extends the values that we clamp to on saturation. This could be
1191 // resolved by shifting one of the operands the same amount, which would
1192 // also shift the result we compare against, then shifting back.
1193 Op1Promoted =
1194 DAG.getNode(ISD::SHL, dl, PromotedType, Op1Promoted,
1195 DAG.getShiftAmountConstant(DiffSize, PromotedType, dl));
1196 SDValue Result = DAG.getNode(N->getOpcode(), dl, PromotedType, Op1Promoted,
1197 Op2Promoted, N->getOperand(2));
1198 unsigned ShiftOp = Signed ? ISD::SRA : ISD::SRL;
1199 return DAG.getNode(ShiftOp, dl, PromotedType, Result,
1200 DAG.getShiftAmountConstant(DiffSize, PromotedType, dl));
1201 }
1202 return DAG.getNode(N->getOpcode(), dl, PromotedType, Op1Promoted, Op2Promoted,
1203 N->getOperand(2));
1204}
1205
1207 unsigned SatW, bool Signed,
1208 const TargetLowering &TLI,
1209 SelectionDAG &DAG) {
1210 EVT VT = V.getValueType();
1211 unsigned VTW = VT.getScalarSizeInBits();
1212
1213 if (!Signed) {
1214 // Saturate to the unsigned maximum by getting the minimum of V and the
1215 // maximum.
1216 return DAG.getNode(ISD::UMIN, dl, VT, V,
1217 DAG.getConstant(APInt::getLowBitsSet(VTW, SatW),
1218 dl, VT));
1219 }
1220
1221 // Saturate to the signed maximum (the low SatW - 1 bits) by taking the
1222 // signed minimum of it and V.
1223 V = DAG.getNode(ISD::SMIN, dl, VT, V,
1224 DAG.getConstant(APInt::getLowBitsSet(VTW, SatW - 1),
1225 dl, VT));
1226 // Saturate to the signed minimum (the high SatW + 1 bits) by taking the
1227 // signed maximum of it and V.
1228 V = DAG.getNode(ISD::SMAX, dl, VT, V,
1229 DAG.getConstant(APInt::getHighBitsSet(VTW, VTW - SatW + 1),
1230 dl, VT));
1231 return V;
1232}
1233
1235 unsigned Scale, const TargetLowering &TLI,
1236 SelectionDAG &DAG, unsigned SatW = 0) {
1237 EVT VT = LHS.getValueType();
1238 unsigned VTSize = VT.getScalarSizeInBits();
1239 bool Signed = N->getOpcode() == ISD::SDIVFIX ||
1240 N->getOpcode() == ISD::SDIVFIXSAT;
1241 bool Saturating = N->getOpcode() == ISD::SDIVFIXSAT ||
1242 N->getOpcode() == ISD::UDIVFIXSAT;
1243
1244 SDLoc dl(N);
1245 // Widen the types by a factor of two. This is guaranteed to expand, since it
1246 // will always have enough high bits in the LHS to shift into.
1247 EVT WideVT = VT.changeElementType(
1248 *DAG.getContext(), EVT::getIntegerVT(*DAG.getContext(), VTSize * 2));
1249 LHS = DAG.getExtOrTrunc(Signed, LHS, dl, WideVT);
1250 RHS = DAG.getExtOrTrunc(Signed, RHS, dl, WideVT);
1251 SDValue Res = TLI.expandFixedPointDiv(N->getOpcode(), dl, LHS, RHS, Scale,
1252 DAG);
1253 assert(Res && "Expanding DIVFIX with wide type failed?");
1254 if (Saturating) {
1255 // If the caller has told us to saturate at something less, use that width
1256 // instead of the type before doubling. However, it cannot be more than
1257 // what we just widened!
1258 assert(SatW <= VTSize &&
1259 "Tried to saturate to more than the original type?");
1260 Res = SaturateWidenedDIVFIX(Res, dl, SatW == 0 ? VTSize : SatW, Signed,
1261 TLI, DAG);
1262 }
1263 return DAG.getZExtOrTrunc(Res, dl, VT);
1264}
1265
1266SDValue DAGTypeLegalizer::PromoteIntRes_DIVFIX(SDNode *N) {
1267 SDLoc dl(N);
1268 SDValue Op1Promoted, Op2Promoted;
1269 bool Signed = N->getOpcode() == ISD::SDIVFIX ||
1270 N->getOpcode() == ISD::SDIVFIXSAT;
1271 bool Saturating = N->getOpcode() == ISD::SDIVFIXSAT ||
1272 N->getOpcode() == ISD::UDIVFIXSAT;
1273 if (Signed) {
1274 Op1Promoted = SExtPromotedInteger(N->getOperand(0));
1275 Op2Promoted = SExtPromotedInteger(N->getOperand(1));
1276 } else {
1277 Op1Promoted = ZExtPromotedInteger(N->getOperand(0));
1278 Op2Promoted = ZExtPromotedInteger(N->getOperand(1));
1279 }
1280 EVT PromotedType = Op1Promoted.getValueType();
1281 unsigned Scale = N->getConstantOperandVal(2);
1282
1283 // If the type is already legal and the operation is legal in that type, we
1284 // should not early expand.
1285 if (TLI.isTypeLegal(PromotedType)) {
1287 TLI.getFixedPointOperationAction(N->getOpcode(), PromotedType, Scale);
1288 if (Action == TargetLowering::Legal || Action == TargetLowering::Custom) {
1289 unsigned Diff = PromotedType.getScalarSizeInBits() -
1290 N->getValueType(0).getScalarSizeInBits();
1291 if (Saturating)
1292 Op1Promoted =
1293 DAG.getNode(ISD::SHL, dl, PromotedType, Op1Promoted,
1294 DAG.getShiftAmountConstant(Diff, PromotedType, dl));
1295 SDValue Res = DAG.getNode(N->getOpcode(), dl, PromotedType, Op1Promoted,
1296 Op2Promoted, N->getOperand(2));
1297 if (Saturating)
1298 Res = DAG.getNode(Signed ? ISD::SRA : ISD::SRL, dl, PromotedType, Res,
1299 DAG.getShiftAmountConstant(Diff, PromotedType, dl));
1300 return Res;
1301 }
1302 }
1303
1304 // See if we can perform the division in this type without expanding.
1305 if (SDValue Res = TLI.expandFixedPointDiv(N->getOpcode(), dl, Op1Promoted,
1306 Op2Promoted, Scale, DAG)) {
1307 if (Saturating)
1308 Res = SaturateWidenedDIVFIX(Res, dl,
1309 N->getValueType(0).getScalarSizeInBits(),
1310 Signed, TLI, DAG);
1311 return Res;
1312 }
1313 // If we cannot, expand it to twice the type width. If we are saturating, give
1314 // it the original width as a saturating width so we don't need to emit
1315 // two saturations.
1316 return earlyExpandDIVFIX(N, Op1Promoted, Op2Promoted, Scale, TLI, DAG,
1317 N->getValueType(0).getScalarSizeInBits());
1318}
1319
1320SDValue DAGTypeLegalizer::PromoteIntRes_SADDSUBO(SDNode *N, unsigned ResNo) {
1321 if (ResNo == 1)
1322 return PromoteIntRes_Overflow(N);
1323
1324 // The operation overflowed iff the result in the larger type is not the
1325 // sign extension of its truncation to the original type.
1326 SDValue LHS = SExtPromotedInteger(N->getOperand(0));
1327 SDValue RHS = SExtPromotedInteger(N->getOperand(1));
1328 EVT OVT = N->getOperand(0).getValueType();
1329 EVT NVT = LHS.getValueType();
1330 SDLoc dl(N);
1331
1332 // Do the arithmetic in the larger type.
1333 unsigned Opcode = N->getOpcode() == ISD::SADDO ? ISD::ADD : ISD::SUB;
1334 SDValue Res = DAG.getNode(Opcode, dl, NVT, LHS, RHS);
1335
1336 // Calculate the overflow flag: sign extend the arithmetic result from
1337 // the original type.
1338 SDValue Ofl = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, NVT, Res,
1339 DAG.getValueType(OVT));
1340 // Overflowed if and only if this is not equal to Res.
1341 Ofl = DAG.getSetCC(dl, N->getValueType(1), Ofl, Res, ISD::SETNE);
1342
1343 // Use the calculated overflow everywhere.
1344 ReplaceValueWith(SDValue(N, 1), Ofl);
1345
1346 return Res;
1347}
1348
1349SDValue DAGTypeLegalizer::PromoteIntRes_CMP(SDNode *N) {
1350 EVT PromotedResultTy =
1351 TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1352 return DAG.getNode(N->getOpcode(), SDLoc(N), PromotedResultTy,
1353 N->getOperand(0), N->getOperand(1));
1354}
1355
1356SDValue DAGTypeLegalizer::PromoteIntRes_Select(SDNode *N) {
1357 SDValue Mask = N->getOperand(0);
1358
1359 SDValue LHS = GetPromotedInteger(N->getOperand(1));
1360 SDValue RHS = GetPromotedInteger(N->getOperand(2));
1361
1362 unsigned Opcode = N->getOpcode();
1363 if (Opcode == ISD::VP_MERGE)
1364 return DAG.getNode(Opcode, SDLoc(N), LHS.getValueType(), Mask, LHS, RHS,
1365 N->getOperand(3));
1366 return DAG.getNode(Opcode, SDLoc(N), LHS.getValueType(), Mask, LHS, RHS);
1367}
1368
1369SDValue DAGTypeLegalizer::PromoteIntRes_SELECT_CC(SDNode *N) {
1370 SDValue LHS = GetPromotedInteger(N->getOperand(2));
1371 SDValue RHS = GetPromotedInteger(N->getOperand(3));
1372 return DAG.getNode(ISD::SELECT_CC, SDLoc(N),
1373 LHS.getValueType(), N->getOperand(0),
1374 N->getOperand(1), LHS, RHS, N->getOperand(4));
1375}
1376
1377SDValue DAGTypeLegalizer::PromoteIntRes_SETCC(SDNode *N) {
1378 unsigned OpNo = N->isStrictFPOpcode() ? 1 : 0;
1379 EVT InVT = N->getOperand(OpNo).getValueType();
1380 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1381
1382 EVT SVT = getSetCCResultType(InVT);
1383
1384 // If we got back a type that needs to be promoted, this likely means the
1385 // the input type also needs to be promoted. So get the promoted type for
1386 // the input and try the query again.
1387 if (getTypeAction(SVT) == TargetLowering::TypePromoteInteger) {
1388 if (getTypeAction(InVT) == TargetLowering::TypePromoteInteger) {
1389 InVT = TLI.getTypeToTransformTo(*DAG.getContext(), InVT);
1390 SVT = getSetCCResultType(InVT);
1391 } else {
1392 // Input type isn't promoted, just use the default promoted type.
1393 SVT = NVT;
1394 }
1395 }
1396
1397 SDLoc dl(N);
1398 assert(SVT.isVector() == N->getOperand(OpNo).getValueType().isVector() &&
1399 "Vector compare must return a vector result!");
1400
1401 // Get the SETCC result using the canonical SETCC type.
1402 SDValue SetCC;
1403 if (N->isStrictFPOpcode()) {
1404 SDVTList VTs = DAG.getVTList({SVT, MVT::Other});
1405 SDValue Opers[] = {N->getOperand(0), N->getOperand(1),
1406 N->getOperand(2), N->getOperand(3)};
1407 SetCC = DAG.getNode(N->getOpcode(), dl, VTs, Opers, N->getFlags());
1408 // Legalize the chain result - switch anything that used the old chain to
1409 // use the new one.
1410 ReplaceValueWith(SDValue(N, 1), SetCC.getValue(1));
1411 } else
1412 SetCC = DAG.getNode(N->getOpcode(), dl, SVT, N->getOperand(0),
1413 N->getOperand(1), N->getOperand(2), N->getFlags());
1414
1415 // Convert to the expected type.
1416 return DAG.getSExtOrTrunc(SetCC, dl, NVT);
1417}
1418
1419SDValue DAGTypeLegalizer::PromoteIntRes_IS_FPCLASS(SDNode *N) {
1420 SDLoc DL(N);
1421 SDValue Arg = N->getOperand(0);
1422 SDValue Test = N->getOperand(1);
1423 EVT NResVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1424 return DAG.getNode(ISD::IS_FPCLASS, DL, NResVT, Arg, Test);
1425}
1426
1427SDValue DAGTypeLegalizer::PromoteIntRes_FFREXP(SDNode *N) {
1428 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(1));
1429 EVT VT = N->getValueType(0);
1430
1431 SDLoc dl(N);
1432 SDValue Res =
1433 DAG.getNode(N->getOpcode(), dl, DAG.getVTList(VT, NVT), N->getOperand(0));
1434
1435 ReplaceValueWith(SDValue(N, 0), Res);
1436 return Res.getValue(1);
1437}
1438
1439SDValue DAGTypeLegalizer::PromoteIntRes_SHL(SDNode *N) {
1440 SDValue LHS = GetPromotedInteger(N->getOperand(0));
1441 SDValue RHS = N->getOperand(1);
1442 if (getTypeAction(RHS.getValueType()) == TargetLowering::TypePromoteInteger)
1443 RHS = ZExtPromotedInteger(RHS);
1444 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1445}
1446
1447SDValue DAGTypeLegalizer::PromoteIntRes_SIGN_EXTEND_INREG(SDNode *N) {
1448 SDValue Op = GetPromotedInteger(N->getOperand(0));
1449 return DAG.getNode(ISD::SIGN_EXTEND_INREG, SDLoc(N),
1450 Op.getValueType(), Op, N->getOperand(1));
1451}
1452
1453SDValue DAGTypeLegalizer::PromoteIntRes_SimpleIntBinOp(SDNode *N) {
1454 // The input may have strange things in the top bits of the registers, but
1455 // these operations don't care. They may have weird bits going out, but
1456 // that too is okay if they are integer operations.
1457 SDValue LHS = GetPromotedInteger(N->getOperand(0));
1458 SDValue RHS = GetPromotedInteger(N->getOperand(1));
1459 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1460}
1461
1462SDValue DAGTypeLegalizer::PromoteIntRes_SExtIntBinOp(SDNode *N) {
1463 // Sign extend the input.
1464 SDValue LHS = SExtPromotedInteger(N->getOperand(0));
1465 SDValue RHS = SExtPromotedInteger(N->getOperand(1));
1466 if (N->getNumOperands() == 2)
1467 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1468 assert(N->getNumOperands() == 4 && "Unexpected number of operands!");
1469 assert((N->getOpcode() == ISD::VP_SDIV || N->getOpcode() == ISD::VP_SREM) &&
1470 "Expected VP opcode");
1471 SDValue Mask = N->getOperand(2);
1472 SDValue EVL = N->getOperand(3);
1473 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS,
1474 Mask, EVL);
1475}
1476
1477SDValue DAGTypeLegalizer::PromoteIntRes_ZExtIntBinOp(SDNode *N) {
1478 // Zero extend the input.
1479 SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
1480 SDValue RHS = ZExtPromotedInteger(N->getOperand(1));
1481 if (N->getNumOperands() == 2)
1482 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1483 assert(N->getNumOperands() == 4 && "Unexpected number of operands!");
1484 assert((N->getOpcode() == ISD::VP_UDIV || N->getOpcode() == ISD::VP_UREM) &&
1485 "Expected VP opcode");
1486 // Zero extend the input.
1487 SDValue Mask = N->getOperand(2);
1488 SDValue EVL = N->getOperand(3);
1489 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS,
1490 Mask, EVL);
1491}
1492
1493SDValue DAGTypeLegalizer::PromoteIntRes_ZExtMaskedIntBinOp(SDNode *N) {
1494 SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
1495 SDValue RHS = ZExtPromotedInteger(N->getOperand(1));
1496 SDValue Mask = N->getOperand(2);
1497 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS,
1498 Mask);
1499}
1500
1501SDValue DAGTypeLegalizer::PromoteIntRes_SExtMaskedIntBinOp(SDNode *N) {
1502 SDValue LHS = SExtPromotedInteger(N->getOperand(0));
1503 SDValue RHS = SExtPromotedInteger(N->getOperand(1));
1504 SDValue Mask = N->getOperand(2);
1505 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS,
1506 Mask);
1507}
1508
1509SDValue DAGTypeLegalizer::PromoteIntRes_UMINUMAX(SDNode *N) {
1510 SDValue LHS = N->getOperand(0);
1511 SDValue RHS = N->getOperand(1);
1512
1513 // It doesn't matter if we sign extend or zero extend in the inputs. So do
1514 // whatever is best for the target and the promoted operands.
1515 SExtOrZExtPromotedOperands(LHS, RHS);
1516
1517 return DAG.getNode(N->getOpcode(), SDLoc(N),
1518 LHS.getValueType(), LHS, RHS);
1519}
1520
1521SDValue DAGTypeLegalizer::PromoteIntRes_SRA(SDNode *N) {
1522 // The input value must be properly sign extended.
1523 SDValue LHS = SExtPromotedInteger(N->getOperand(0));
1524 SDValue RHS = N->getOperand(1);
1525 if (getTypeAction(RHS.getValueType()) == TargetLowering::TypePromoteInteger)
1526 RHS = ZExtPromotedInteger(RHS);
1527 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1528}
1529
1530SDValue DAGTypeLegalizer::PromoteIntRes_SRL(SDNode *N) {
1531 SDValue RHS = N->getOperand(1);
1532 // The input value must be properly zero extended.
1533 SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
1534 if (getTypeAction(RHS.getValueType()) == TargetLowering::TypePromoteInteger)
1535 RHS = ZExtPromotedInteger(RHS);
1536 return DAG.getNode(N->getOpcode(), SDLoc(N), LHS.getValueType(), LHS, RHS);
1537}
1538
1539SDValue DAGTypeLegalizer::PromoteIntRes_Rotate(SDNode *N) {
1540 EVT OldVT = N->getValueType(0);
1541 EVT VT = TLI.getTypeToTransformTo(*DAG.getContext(), OldVT);
1542 SDValue Amt = N->getOperand(1);
1543 unsigned Opcode = N->getOpcode();
1544 unsigned OldBits = OldVT.getScalarSizeInBits();
1545 unsigned NewBits = VT.getScalarSizeInBits();
1546
1547 // If the promoted type is twice the size (or more), then we can concatenate
1548 // the value with itself and treat this similar to a funnel shift. This isn't
1549 // necessary if the rotate amount is constant or if shl/srl of the original
1550 // type are custom lowered.
1551 // rotl(x,amt) -> (((aext(x) << bw) | zext(x)) << (amt % bw)) >> bw.
1552 // rotr(x,amt) -> (((aext(x) << bw) | zext(x)) >> (amt % bw)).
1553 if (NewBits >= (2 * OldBits) && !isa<ConstantSDNode>(Amt) &&
1554 !TLI.isOperationLegalOrCustom(Opcode, VT) &&
1555 TLI.getOperationAction(ISD::SHL, OldVT) != TargetLowering::Custom &&
1556 TLI.getOperationAction(ISD::SRL, OldVT) != TargetLowering::Custom) {
1557 SDValue Op0 = GetPromotedInteger(N->getOperand(0));
1558 if (getTypeAction(Amt.getValueType()) == TargetLowering::TypePromoteInteger)
1559 Amt = ZExtPromotedInteger(Amt);
1560 EVT AmtVT = Amt.getValueType();
1561
1562 SDLoc DL(N);
1563 // Amount has to be interpreted modulo the old bit width.
1564 Amt = DAG.getNode(ISD::UREM, DL, AmtVT, Amt,
1565 DAG.getConstant(OldBits, DL, AmtVT));
1566 SDValue HiShift = DAG.getShiftAmountConstant(OldBits, VT, DL);
1567 SDValue Hi = DAG.getNode(ISD::SHL, DL, VT, Op0, HiShift);
1568 SDValue Lo = DAG.getZeroExtendInReg(Op0, DL, OldVT);
1569 SDValue Res = DAG.getNode(ISD::OR, DL, VT, Hi, Lo);
1570 bool IsROTR = N->getOpcode() == ISD::ROTR;
1571 Res = DAG.getNode(IsROTR ? ISD::SRL : ISD::SHL, DL, VT, Res, Amt);
1572 // FIXME: We can avoid this by using ROTL when the promoted type is exactly
1573 // twice the size.
1574 if (!IsROTR)
1575 Res = DAG.getNode(ISD::SRL, DL, VT, Res, HiShift);
1576 return Res;
1577 }
1578
1579 // Lower the rotate to shifts and ORs which can be promoted.
1580 SDValue Res = TLI.expandROT(N, true /*AllowVectorOps*/, DAG);
1581 ReplaceValueWith(SDValue(N, 0), Res);
1582 return SDValue();
1583}
1584
1585SDValue DAGTypeLegalizer::PromoteIntRes_FunnelShift(SDNode *N) {
1586 SDValue Hi = GetPromotedInteger(N->getOperand(0));
1587 SDValue Lo = GetPromotedInteger(N->getOperand(1));
1588 SDValue Amt = N->getOperand(2);
1589 if (getTypeAction(Amt.getValueType()) == TargetLowering::TypePromoteInteger)
1590 Amt = ZExtPromotedInteger(Amt);
1591 EVT AmtVT = Amt.getValueType();
1592
1593 SDLoc DL(N);
1594 EVT OldVT = N->getOperand(0).getValueType();
1595 EVT VT = Lo.getValueType();
1596 unsigned Opcode = N->getOpcode();
1597 bool IsFSHR = Opcode == ISD::FSHR;
1598 unsigned OldBits = OldVT.getScalarSizeInBits();
1599 unsigned NewBits = VT.getScalarSizeInBits();
1600
1601 // Amount has to be interpreted modulo the old bit width.
1602 Amt = DAG.getNode(ISD::UREM, DL, AmtVT, Amt,
1603 DAG.getConstant(OldBits, DL, AmtVT));
1604
1605 // If the promoted type is twice the size (or more), then we use the
1606 // traditional funnel 'double' shift codegen. This isn't necessary if the
1607 // shift amount is constant.
1608 // fshl(x,y,z) -> (((aext(x) << bw) | zext(y)) << (z % bw)) >> bw.
1609 // fshr(x,y,z) -> (((aext(x) << bw) | zext(y)) >> (z % bw)).
1610 if (NewBits >= (2 * OldBits) && !isa<ConstantSDNode>(Amt) &&
1611 !TLI.isOperationLegalOrCustom(Opcode, VT)) {
1612 SDValue HiShift = DAG.getShiftAmountConstant(OldBits, VT, DL);
1613 Hi = DAG.getNode(ISD::SHL, DL, VT, Hi, HiShift);
1614 Lo = DAG.getZeroExtendInReg(Lo, DL, OldVT);
1615 SDValue Res = DAG.getNode(ISD::OR, DL, VT, Hi, Lo);
1616 Res = DAG.getNode(IsFSHR ? ISD::SRL : ISD::SHL, DL, VT, Res, Amt);
1617 if (!IsFSHR)
1618 Res = DAG.getNode(ISD::SRL, DL, VT, Res, HiShift);
1619 return Res;
1620 }
1621
1622 // Shift Lo up to occupy the upper bits of the promoted type.
1623 Lo = DAG.getNode(ISD::SHL, DL, VT, Lo,
1624 DAG.getShiftAmountConstant(NewBits - OldBits, VT, DL));
1625
1626 // Increase Amount to shift the result into the lower bits of the promoted
1627 // type.
1628 if (IsFSHR)
1629 Amt = DAG.getNode(ISD::ADD, DL, AmtVT, Amt,
1630 DAG.getConstant(NewBits - OldBits, DL, AmtVT));
1631
1632 return DAG.getNode(Opcode, DL, VT, Hi, Lo, Amt);
1633}
1634
1635SDValue DAGTypeLegalizer::PromoteIntRes_CLMUL(SDNode *N) {
1636 unsigned Opcode = N->getOpcode();
1637
1638 SDLoc DL(N);
1639 EVT OldVT = N->getOperand(0).getValueType();
1640 EVT VT = TLI.getTypeToTransformTo(*DAG.getContext(), OldVT);
1641
1642 if (Opcode == ISD::CLMUL) {
1643 // Avoid the generic expansion if the cross-product expansion in
1644 // ExpandIntRes_CLMUL would produce a better result.
1645 if (!TLI.isOperationLegalOrCustomOrPromote(ISD::CLMUL, VT) &&
1646 !(getTypeAction(VT) == TargetLowering::TypeExpandInteger &&
1647 TLI.isOperationLegalOrCustom(
1648 ISD::CLMUL, TLI.getRegisterType(*DAG.getContext(), VT)))) {
1649 if (SDValue Res = TLI.expandCLMUL(N, DAG))
1650 return DAG.getNode(ISD::ANY_EXTEND, DL, VT, Res);
1651 }
1652 SDValue X = GetPromotedInteger(N->getOperand(0));
1653 SDValue Y = GetPromotedInteger(N->getOperand(1));
1654 return DAG.getNode(ISD::CLMUL, DL, VT, X, Y);
1655 }
1656
1657 SDValue X = ZExtPromotedInteger(N->getOperand(0));
1658 SDValue Y = ZExtPromotedInteger(N->getOperand(1));
1659
1660 unsigned OldBits = OldVT.getScalarSizeInBits();
1661 unsigned NewBits = VT.getScalarSizeInBits();
1662 if (NewBits < 2 * OldBits) {
1663 SDValue Clmul = DAG.getNode(ISD::CLMUL, DL, VT, X, Y);
1664 unsigned ShAmt = Opcode == ISD::CLMULH ? OldBits : OldBits - 1;
1665 SDValue Lo = DAG.getNode(ISD::SRL, DL, VT, Clmul,
1666 DAG.getShiftAmountConstant(ShAmt, VT, DL));
1667 SDValue Clmulh = DAG.getNode(ISD::CLMULH, DL, VT, X, Y);
1668 ShAmt = Opcode == ISD::CLMULH ? NewBits - OldBits : NewBits - OldBits + 1;
1669 SDValue Hi = DAG.getNode(ISD::SHL, DL, VT, Clmulh,
1670 DAG.getShiftAmountConstant(ShAmt, VT, DL));
1671 return DAG.getNode(ISD::OR, DL, VT, Lo, Hi);
1672 }
1673
1674 SDValue Clmul = DAG.getNode(ISD::CLMUL, DL, VT, X, Y);
1675 unsigned ShAmt = Opcode == ISD::CLMULH ? OldBits : OldBits - 1;
1676 return DAG.getNode(ISD::SRL, DL, VT, Clmul,
1677 DAG.getShiftAmountConstant(ShAmt, VT, DL));
1678}
1679
1680SDValue DAGTypeLegalizer::PromoteIntRes_PEXT(SDNode *N) {
1681 SDLoc DL(N);
1682 EVT VT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1683 if (!TLI.isOperationLegalOrCustomOrPromote(ISD::PEXT, VT)) {
1684 if (SDValue Res = TLI.expandPEXT(N, DAG))
1685 return DAG.getNode(ISD::ANY_EXTEND, DL, VT, Res);
1686 }
1687 // Only the mask operand needs zero-extension because the implicit AND from
1688 // masking clears the corresponding bits in X anyway.
1689 SDValue X = GetPromotedInteger(N->getOperand(0));
1690 SDValue Y = ZExtPromotedInteger(N->getOperand(1));
1691 return DAG.getNode(ISD::PEXT, DL, VT, X, Y);
1692}
1693
1694SDValue DAGTypeLegalizer::PromoteIntRes_PDEP(SDNode *N) {
1695 SDLoc DL(N);
1696 EVT VT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1697 if (!TLI.isOperationLegalOrCustomOrPromote(ISD::PDEP, VT)) {
1698 if (SDValue Res = TLI.expandPDEP(N, DAG))
1699 return DAG.getNode(ISD::ANY_EXTEND, DL, VT, Res);
1700 }
1701 // Neither operand needs zero-extension because the upper operand bits could
1702 // only result in depositing result bits that will be discarded.
1703 SDValue X = GetPromotedInteger(N->getOperand(0));
1704 SDValue Y = GetPromotedInteger(N->getOperand(1));
1705 return DAG.getNode(ISD::PDEP, DL, VT, X, Y);
1706}
1707
1708SDValue DAGTypeLegalizer::PromoteIntRes_MULH(SDNode *N) {
1709 SDLoc dl(N);
1710 EVT VT = N->getValueType(0);
1711 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
1712 bool IsSigned = N->getOpcode() == ISD::MULHS;
1713 unsigned BW = VT.getScalarSizeInBits();
1714 unsigned NBW = NVT.getScalarSizeInBits();
1715
1716 SDValue LHS, RHS;
1717 if (IsSigned) {
1718 LHS = SExtPromotedInteger(N->getOperand(0));
1719 RHS = SExtPromotedInteger(N->getOperand(1));
1720 } else {
1721 LHS = ZExtPromotedInteger(N->getOperand(0));
1722 RHS = ZExtPromotedInteger(N->getOperand(1));
1723 }
1724
1725 // If the promoted type is already wide enough, emit a MUL.
1726 if (NBW >= 2 * BW)
1727 return DAG.getNode(IsSigned ? ISD::SRA : ISD::SRL, dl, NVT,
1728 DAG.getNode(ISD::MUL, dl, NVT, LHS, RHS),
1729 DAG.getShiftAmountConstant(BW, NVT, dl));
1730
1731 // Otherwise, align an operand with a left-shift and emit a MULH.
1732 LHS = DAG.getNode(ISD::SHL, dl, NVT, LHS,
1733 DAG.getShiftAmountConstant(NBW - BW, NVT, dl));
1734 return DAG.getNode(N->getOpcode(), dl, NVT, LHS, RHS);
1735}
1736
1737SDValue DAGTypeLegalizer::PromoteIntRes_TRUNCATE(SDNode *N) {
1738 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1739 SDValue Res;
1740 SDValue InOp = N->getOperand(0);
1741 SDLoc dl(N);
1742
1743 switch (getTypeAction(InOp.getValueType())) {
1744 default: llvm_unreachable("Unknown type action!");
1747 Res = InOp;
1748 break;
1750 Res = GetPromotedInteger(InOp);
1751 break;
1753 EVT InVT = InOp.getValueType();
1754 assert(InVT.isVector() && "Cannot split scalar types");
1755 ElementCount NumElts = InVT.getVectorElementCount();
1756 assert(NumElts == NVT.getVectorElementCount() &&
1757 "Dst and Src must have the same number of elements");
1759 "Promoted vector type must be a power of two");
1760
1761 SDValue EOp1, EOp2;
1762 GetSplitVector(InOp, EOp1, EOp2);
1763
1764 EVT HalfNVT = EVT::getVectorVT(*DAG.getContext(), NVT.getScalarType(),
1765 NumElts.divideCoefficientBy(2));
1766 EOp1 = DAG.getNode(ISD::TRUNCATE, dl, HalfNVT, EOp1);
1767 EOp2 = DAG.getNode(ISD::TRUNCATE, dl, HalfNVT, EOp2);
1768 return DAG.getNode(ISD::CONCAT_VECTORS, dl, NVT, EOp1, EOp2);
1769 }
1771 SDValue WideInOp = GetWidenedVector(InOp);
1772
1773 // Truncate widened InOp.
1774 unsigned NumElem = WideInOp.getValueType().getVectorNumElements();
1775 EVT TruncVT = EVT::getVectorVT(*DAG.getContext(),
1776 N->getValueType(0).getScalarType(), NumElem);
1777 SDValue WideTrunc = DAG.getNode(ISD::TRUNCATE, dl, TruncVT, WideInOp);
1778
1779 // Zero extend so that the elements are of same type as those of NVT
1780 EVT ExtVT = EVT::getVectorVT(*DAG.getContext(), NVT.getVectorElementType(),
1781 NumElem);
1782 SDValue WideExt = DAG.getNode(ISD::ZERO_EXTEND, dl, ExtVT, WideTrunc);
1783
1784 // Extract the low NVT subvector.
1785 SDValue ZeroIdx = DAG.getVectorIdxConstant(0, dl);
1786 return DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, NVT, WideExt, ZeroIdx);
1787 }
1788 }
1789
1790 // Truncate to NVT instead of VT
1791 return DAG.getNode(ISD::TRUNCATE, dl, NVT, Res);
1792}
1793
1794SDValue DAGTypeLegalizer::PromoteIntRes_UADDSUBO(SDNode *N, unsigned ResNo) {
1795 if (ResNo == 1)
1796 return PromoteIntRes_Overflow(N);
1797
1798 // The operation overflowed iff the result in the larger type is not the
1799 // zero extension of its truncation to the original type.
1800 SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
1801 SDValue RHS = ZExtPromotedInteger(N->getOperand(1));
1802 EVT OVT = N->getOperand(0).getValueType();
1803 EVT NVT = LHS.getValueType();
1804 SDLoc dl(N);
1805
1806 // Do the arithmetic in the larger type.
1807 unsigned Opcode = N->getOpcode() == ISD::UADDO ? ISD::ADD : ISD::SUB;
1808 SDValue Res = DAG.getNode(Opcode, dl, NVT, LHS, RHS);
1809
1810 // Calculate the overflow flag: zero extend the arithmetic result from
1811 // the original type.
1812 SDValue Ofl = DAG.getZeroExtendInReg(Res, dl, OVT);
1813 // Overflowed if and only if this is not equal to Res.
1814 Ofl = DAG.getSetCC(dl, N->getValueType(1), Ofl, Res, ISD::SETNE);
1815
1816 // Use the calculated overflow everywhere.
1817 ReplaceValueWith(SDValue(N, 1), Ofl);
1818
1819 return Res;
1820}
1821
1822// Handle promotion for the ADDE/SUBE/UADDO_CARRY/USUBO_CARRY nodes. Notice that
1823// the third operand of ADDE/SUBE nodes is carry flag, which differs from
1824// the UADDO_CARRY/USUBO_CARRY nodes in that the third operand is carry Boolean.
1825SDValue DAGTypeLegalizer::PromoteIntRes_UADDSUBO_CARRY(SDNode *N,
1826 unsigned ResNo) {
1827 if (ResNo == 1)
1828 return PromoteIntRes_Overflow(N);
1829
1830 // We need to sign-extend the operands so the carry value computed by the
1831 // wide operation will be equivalent to the carry value computed by the
1832 // narrow operation.
1833 // An UADDO_CARRY can generate carry only if any of the operands has its
1834 // most significant bit set. Sign extension propagates the most significant
1835 // bit into the higher bits which means the extra bit that the narrow
1836 // addition would need (i.e. the carry) will be propagated through the higher
1837 // bits of the wide addition.
1838 // A USUBO_CARRY can generate borrow only if LHS < RHS and this property will
1839 // be preserved by sign extension.
1840 SDValue LHS = SExtPromotedInteger(N->getOperand(0));
1841 SDValue RHS = SExtPromotedInteger(N->getOperand(1));
1842
1843 EVT ValueVTs[] = {LHS.getValueType(), N->getValueType(1)};
1844
1845 // Do the arithmetic in the wide type.
1846 SDValue Res = DAG.getNode(N->getOpcode(), SDLoc(N), DAG.getVTList(ValueVTs),
1847 LHS, RHS, N->getOperand(2));
1848
1849 // Update the users of the original carry/borrow value.
1850 ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
1851
1852 return SDValue(Res.getNode(), 0);
1853}
1854
1855SDValue DAGTypeLegalizer::PromoteIntRes_SADDSUBO_CARRY(SDNode *N,
1856 unsigned ResNo) {
1857 assert(ResNo == 1 && "Don't know how to promote other results yet.");
1858 return PromoteIntRes_Overflow(N);
1859}
1860
1861SDValue DAGTypeLegalizer::PromoteIntRes_ABS(SDNode *N) {
1862 EVT OVT = N->getValueType(0);
1863 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), OVT);
1864
1865 // If a larger ABS or SMAX isn't supported by the target, try to expand now.
1866 // If we expand later we'll end up sign extending more than just the sra input
1867 // in sra+xor+sub expansion.
1868 if (!OVT.isVector() &&
1869 !TLI.isOperationLegalOrCustomOrPromote(ISD::ABS, NVT) &&
1870 !TLI.isOperationLegalOrCustomOrPromote(ISD::ABS_MIN_POISON, NVT) &&
1871 !TLI.isOperationLegal(ISD::SMAX, NVT)) {
1872 if (SDValue Res = TLI.expandABS(N, DAG))
1873 return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N), NVT, Res);
1874 }
1875
1876 SDValue Op0 = SExtPromotedInteger(N->getOperand(0));
1877 return DAG.getNode(ISD::ABS_MIN_POISON, SDLoc(N), Op0.getValueType(), Op0);
1878}
1879
1880SDValue DAGTypeLegalizer::PromoteIntRes_XMULO(SDNode *N, unsigned ResNo) {
1881 // Promote the overflow bit trivially.
1882 if (ResNo == 1)
1883 return PromoteIntRes_Overflow(N);
1884
1885 SDValue LHS = N->getOperand(0), RHS = N->getOperand(1);
1886 SDLoc DL(N);
1887 EVT SmallVT = LHS.getValueType();
1888
1889 // To determine if the result overflowed in a larger type, we extend the
1890 // input to the larger type, do the multiply (checking if it overflows),
1891 // then also check the high bits of the result to see if overflow happened
1892 // there.
1893 if (N->getOpcode() == ISD::SMULO) {
1894 LHS = SExtPromotedInteger(LHS);
1895 RHS = SExtPromotedInteger(RHS);
1896 } else {
1897 LHS = ZExtPromotedInteger(LHS);
1898 RHS = ZExtPromotedInteger(RHS);
1899 }
1900 SDVTList VTs = DAG.getVTList(LHS.getValueType(), N->getValueType(1));
1901 SDValue Mul = DAG.getNode(N->getOpcode(), DL, VTs, LHS, RHS);
1902
1903 // Overflow occurred if it occurred in the larger type, or if the high part
1904 // of the result does not zero/sign-extend the low part. Check this second
1905 // possibility first.
1906 SDValue Overflow;
1907 if (N->getOpcode() == ISD::UMULO) {
1908 // Unsigned overflow occurred if the high part is non-zero.
1909 unsigned Shift = SmallVT.getScalarSizeInBits();
1910 SDValue Hi =
1911 DAG.getNode(ISD::SRL, DL, Mul.getValueType(), Mul,
1912 DAG.getShiftAmountConstant(Shift, Mul.getValueType(), DL));
1913 Overflow = DAG.getSetCC(DL, N->getValueType(1), Hi,
1914 DAG.getConstant(0, DL, Hi.getValueType()),
1915 ISD::SETNE);
1916 } else {
1917 // Signed overflow occurred if the high part does not sign extend the low.
1918 SDValue SExt = DAG.getNode(ISD::SIGN_EXTEND_INREG, DL, Mul.getValueType(),
1919 Mul, DAG.getValueType(SmallVT));
1920 Overflow = DAG.getSetCC(DL, N->getValueType(1), SExt, Mul, ISD::SETNE);
1921 }
1922
1923 // The only other way for overflow to occur is if the multiplication in the
1924 // larger type itself overflowed.
1925 Overflow = DAG.getNode(ISD::OR, DL, N->getValueType(1), Overflow,
1926 SDValue(Mul.getNode(), 1));
1927
1928 // Use the calculated overflow everywhere.
1929 ReplaceValueWith(SDValue(N, 1), Overflow);
1930 return Mul;
1931}
1932
1933SDValue DAGTypeLegalizer::PromoteIntRes_UNDEF(SDNode *N) {
1934 return DAG.getUNDEF(TLI.getTypeToTransformTo(*DAG.getContext(),
1935 N->getValueType(0)));
1936}
1937
1938SDValue DAGTypeLegalizer::PromoteIntRes_VSCALE(SDNode *N) {
1939 EVT VT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1940
1941 const APInt &MulImm = N->getConstantOperandAPInt(0);
1942 return DAG.getVScale(SDLoc(N), VT, MulImm.sext(VT.getSizeInBits()));
1943}
1944
1945SDValue DAGTypeLegalizer::PromoteIntRes_VAARG(SDNode *N) {
1946 SDValue Chain = N->getOperand(0); // Get the chain.
1947 SDValue Ptr = N->getOperand(1); // Get the pointer.
1948 EVT VT = N->getValueType(0);
1949 SDLoc dl(N);
1950
1951 MVT RegVT = TLI.getRegisterType(*DAG.getContext(), VT);
1952 unsigned NumRegs = TLI.getNumRegisters(*DAG.getContext(), VT);
1953 // The argument is passed as NumRegs registers of type RegVT.
1954
1955 SmallVector<SDValue, 8> Parts(NumRegs);
1956 for (unsigned i = 0; i < NumRegs; ++i) {
1957 Parts[i] = DAG.getVAArg(RegVT, dl, Chain, Ptr, N->getOperand(2),
1958 N->getConstantOperandVal(3));
1959 Chain = Parts[i].getValue(1);
1960 }
1961
1962 // Handle endianness of the load.
1963 if (DAG.getDataLayout().isBigEndian())
1964 std::reverse(Parts.begin(), Parts.end());
1965
1966 // Assemble the parts in the promoted type.
1967 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1968 SDValue Res = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Parts[0]);
1969 for (unsigned i = 1; i < NumRegs; ++i) {
1970 SDValue Part = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Parts[i]);
1971 // Shift it to the right position and "or" it in.
1972 Part = DAG.getNode(
1973 ISD::SHL, dl, NVT, Part,
1974 DAG.getShiftAmountConstant(i * RegVT.getSizeInBits(), NVT, dl));
1975 Res = DAG.getNode(ISD::OR, dl, NVT, Res, Part);
1976 }
1977
1978 // Modified the chain result - switch anything that used the old chain to
1979 // use the new one.
1980 ReplaceValueWith(SDValue(N, 1), Chain);
1981
1982 return Res;
1983}
1984
1985//===----------------------------------------------------------------------===//
1986// Integer Operand Promotion
1987//===----------------------------------------------------------------------===//
1988
1989/// PromoteIntegerOperand - This method is called when the specified operand of
1990/// the specified node is found to need promotion. At this point, all of the
1991/// result types of the node are known to be legal, but other operands of the
1992/// node may need promotion or expansion as well as the specified one.
1993bool DAGTypeLegalizer::PromoteIntegerOperand(SDNode *N, unsigned OpNo) {
1994 LLVM_DEBUG(dbgs() << "Promote integer operand: "; N->dump(&DAG));
1995 SDValue Res = SDValue();
1996 if (CustomLowerNode(N, N->getOperand(OpNo).getValueType(), false)) {
1997 LLVM_DEBUG(dbgs() << "Node has been custom lowered, done\n");
1998 return false;
1999 }
2000
2001 switch (N->getOpcode()) {
2002 default:
2003 #ifndef NDEBUG
2004 dbgs() << "PromoteIntegerOperand Op #" << OpNo << ": ";
2005 N->dump(&DAG); dbgs() << "\n";
2006 #endif
2007 report_fatal_error("Do not know how to promote this operator's operand!");
2008
2009 case ISD::ANY_EXTEND: Res = PromoteIntOp_ANY_EXTEND(N); break;
2011 Res = PromoteIntOp_ANY_EXTEND_VECTOR_INREG(N);
2012 break;
2013 case ISD::ATOMIC_STORE:
2014 Res = PromoteIntOp_ATOMIC_STORE(cast<AtomicSDNode>(N));
2015 break;
2016 case ISD::BITCAST: Res = PromoteIntOp_BITCAST(N); break;
2017 case ISD::BR_CC: Res = PromoteIntOp_BR_CC(N, OpNo); break;
2018 case ISD::BRCOND: Res = PromoteIntOp_BRCOND(N, OpNo); break;
2019 case ISD::BUILD_PAIR: Res = PromoteIntOp_BUILD_PAIR(N); break;
2020 case ISD::BUILD_VECTOR: Res = PromoteIntOp_BUILD_VECTOR(N); break;
2021 case ISD::CONCAT_VECTORS: Res = PromoteIntOp_CONCAT_VECTORS(N); break;
2022 case ISD::COND_LOOP:
2023 Res = PromoteIntOp_COND_LOOP(N, OpNo);
2024 break;
2025 case ISD::EXTRACT_VECTOR_ELT: Res = PromoteIntOp_EXTRACT_VECTOR_ELT(N); break;
2026 case ISD::FAKE_USE:
2027 Res = PromoteIntOp_FAKE_USE(N);
2028 break;
2030 Res = PromoteIntOp_INSERT_VECTOR_ELT(N, OpNo);
2031 break;
2032 case ISD::SPLAT_VECTOR:
2034 Res = PromoteIntOp_ScalarOp(N);
2035 break;
2036 case ISD::VSELECT:
2037 case ISD::SELECT: Res = PromoteIntOp_SELECT(N, OpNo); break;
2038 case ISD::SELECT_CC: Res = PromoteIntOp_SELECT_CC(N, OpNo); break;
2039 case ISD::SETCC: Res = PromoteIntOp_SETCC(N, OpNo); break;
2040 case ISD::SIGN_EXTEND: Res = PromoteIntOp_SIGN_EXTEND(N); break;
2041 case ISD::SINT_TO_FP: Res = PromoteIntOp_SINT_TO_FP(N); break;
2042 case ISD::STRICT_SINT_TO_FP: Res = PromoteIntOp_STRICT_SINT_TO_FP(N); break;
2043 case ISD::STORE: Res = PromoteIntOp_STORE(cast<StoreSDNode>(N),
2044 OpNo); break;
2045 case ISD::VP_STORE:
2046 Res = PromoteIntOp_VP_STORE(cast<VPStoreSDNode>(N), OpNo);
2047 break;
2048 case ISD::MSTORE: Res = PromoteIntOp_MSTORE(cast<MaskedStoreSDNode>(N),
2049 OpNo); break;
2050 case ISD::MLOAD: Res = PromoteIntOp_MLOAD(cast<MaskedLoadSDNode>(N),
2051 OpNo); break;
2052 case ISD::MGATHER: Res = PromoteIntOp_MGATHER(cast<MaskedGatherSDNode>(N),
2053 OpNo); break;
2054 case ISD::MSCATTER: Res = PromoteIntOp_MSCATTER(cast<MaskedScatterSDNode>(N),
2055 OpNo); break;
2057 Res = PromoteIntOp_VECTOR_COMPRESS(N, OpNo);
2058 break;
2059 case ISD::TRUNCATE: Res = PromoteIntOp_TRUNCATE(N); break;
2060 case ISD::BF16_TO_FP:
2061 case ISD::FP16_TO_FP:
2062 case ISD::UINT_TO_FP: Res = PromoteIntOp_UINT_TO_FP(N); break;
2064 Res = PromoteIntOp_CONVERT_FROM_ARBITRARY_FP(N);
2065 break;
2067 case ISD::STRICT_UINT_TO_FP: Res = PromoteIntOp_STRICT_UINT_TO_FP(N); break;
2068 case ISD::ZERO_EXTEND: Res = PromoteIntOp_ZERO_EXTEND(N); break;
2069 case ISD::EXTRACT_SUBVECTOR: Res = PromoteIntOp_EXTRACT_SUBVECTOR(N); break;
2070 case ISD::INSERT_SUBVECTOR: Res = PromoteIntOp_INSERT_SUBVECTOR(N); break;
2071
2072 case ISD::SHL:
2073 case ISD::SRA:
2074 case ISD::SRL:
2075 case ISD::ROTL:
2076 case ISD::ROTR:
2077 case ISD::SSHLSAT:
2078 case ISD::USHLSAT:
2079 Res = PromoteIntOp_Shift(N);
2080 break;
2081
2082 case ISD::SCMP:
2083 case ISD::UCMP: Res = PromoteIntOp_CMP(N); break;
2084
2085 case ISD::FSHL:
2086 case ISD::FSHR: Res = PromoteIntOp_FunnelShift(N); break;
2087
2088 case ISD::FRAMEADDR:
2089 case ISD::RETURNADDR: Res = PromoteIntOp_FRAMERETURNADDR(N); break;
2090
2091 case ISD::SMULFIX:
2092 case ISD::SMULFIXSAT:
2093 case ISD::UMULFIX:
2094 case ISD::UMULFIXSAT:
2095 case ISD::SDIVFIX:
2096 case ISD::SDIVFIXSAT:
2097 case ISD::UDIVFIX:
2098 case ISD::UDIVFIXSAT: Res = PromoteIntOp_FIX(N); break;
2099 case ISD::FPOWI:
2100 case ISD::STRICT_FPOWI:
2101 case ISD::FLDEXP:
2102 case ISD::STRICT_FLDEXP: Res = PromoteIntOp_ExpOp(N); break;
2103 case ISD::VECREDUCE_ADD:
2104 case ISD::VECREDUCE_MUL:
2105 case ISD::VECREDUCE_AND:
2106 case ISD::VECREDUCE_OR:
2107 case ISD::VECREDUCE_XOR:
2111 case ISD::VECREDUCE_UMIN: Res = PromoteIntOp_VECREDUCE(N); break;
2112 case ISD::VP_REDUCE_ADD:
2113 case ISD::VP_REDUCE_MUL:
2114 case ISD::VP_REDUCE_AND:
2115 case ISD::VP_REDUCE_OR:
2116 case ISD::VP_REDUCE_XOR:
2117 case ISD::VP_REDUCE_SMAX:
2118 case ISD::VP_REDUCE_SMIN:
2119 case ISD::VP_REDUCE_UMAX:
2120 case ISD::VP_REDUCE_UMIN:
2121 Res = PromoteIntOp_VP_REDUCE(N, OpNo);
2122 break;
2123
2124 case ISD::SET_ROUNDING: Res = PromoteIntOp_SET_ROUNDING(N); break;
2125 case ISD::STACKMAP:
2126 Res = PromoteIntOp_STACKMAP(N, OpNo);
2127 break;
2128 case ISD::PATCHPOINT:
2129 Res = PromoteIntOp_PATCHPOINT(N, OpNo);
2130 break;
2132 Res = PromoteIntOp_WRITE_REGISTER(N, OpNo);
2133 break;
2134 case ISD::EXPERIMENTAL_VP_STRIDED_LOAD:
2135 case ISD::EXPERIMENTAL_VP_STRIDED_STORE:
2136 Res = PromoteIntOp_VP_STRIDED(N, OpNo);
2137 break;
2138 case ISD::EXPERIMENTAL_VP_SPLICE:
2139 Res = PromoteIntOp_VP_SPLICE(N, OpNo);
2140 break;
2142 Res = PromoteIntOp_VECTOR_HISTOGRAM(N, OpNo);
2143 break;
2145 case ISD::CTTZ_ELTS:
2147 Res = PromoteIntOp_UnaryBooleanVectorOp(N, OpNo);
2148 break;
2150 Res = PromoteIntOp_GET_ACTIVE_LANE_MASK(N);
2151 break;
2152 case ISD::VECTOR_MATCH:
2153 Res = PromoteIntOp_VECTOR_MATCH(N, OpNo);
2154 break;
2155 case ISD::MASKED_UDIV:
2156 case ISD::MASKED_SDIV:
2157 case ISD::MASKED_UREM:
2158 case ISD::MASKED_SREM:
2159 Res = PromoteIntOp_MaskedBinOp(N, OpNo);
2160 break;
2164 Res = PromoteIntOp_PARTIAL_REDUCE_MLA(N);
2165 break;
2166 case ISD::VECTOR_REPEAT:
2167 Res = PromoteIntOp_VECTOR_REPEAT(N);
2168 break;
2171 Res = PromoteIntOp_LOOP_DEPENDENCE_MASK(N);
2172 break;
2173 }
2174
2175 // If the result is null, the sub-method took care of registering results etc.
2176 if (!Res.getNode()) return false;
2177
2178 // If the result is N, the sub-method updated N in place. Tell the legalizer
2179 // core about this.
2180 if (Res.getNode() == N)
2181 return true;
2182
2183 const bool IsStrictFp = N->isStrictFPOpcode();
2184 assert(Res.getValueType() == N->getValueType(0) &&
2185 N->getNumValues() == (IsStrictFp ? 2 : 1) &&
2186 "Invalid operand expansion");
2187 LLVM_DEBUG(dbgs() << "Replacing: "; N->dump(&DAG); dbgs() << " with: ";
2188 Res.dump());
2189
2190 ReplaceValueWith(SDValue(N, 0), Res);
2191 if (IsStrictFp)
2192 ReplaceValueWith(SDValue(N, 1), SDValue(Res.getNode(), 1));
2193
2194 return false;
2195}
2196
2197// These operands can be either sign extended or zero extended as long as we
2198// treat them the same. If an extension is free, choose that. Otherwise, follow
2199// target preference.
2200void DAGTypeLegalizer::SExtOrZExtPromotedOperands(SDValue &LHS, SDValue &RHS) {
2201 SDValue OpL = GetPromotedInteger(LHS);
2202 SDValue OpR = GetPromotedInteger(RHS);
2203
2204 if (TLI.isSExtCheaperThanZExt(LHS.getValueType(), OpL.getValueType())) {
2205 // The target would prefer to promote the comparison operand with sign
2206 // extension. Honor that unless the promoted values are already zero
2207 // extended.
2208 unsigned OpLEffectiveBits =
2209 DAG.computeKnownBits(OpL).countMaxActiveBits();
2210 unsigned OpREffectiveBits =
2211 DAG.computeKnownBits(OpR).countMaxActiveBits();
2212 if (OpLEffectiveBits <= LHS.getScalarValueSizeInBits() &&
2213 OpREffectiveBits <= RHS.getScalarValueSizeInBits()) {
2214 LHS = OpL;
2215 RHS = OpR;
2216 return;
2217 }
2218
2219 // The promoted values aren't zero extended, use a sext_inreg.
2220 LHS = SExtPromotedInteger(LHS);
2221 RHS = SExtPromotedInteger(RHS);
2222 return;
2223 }
2224
2225 // Prefer to promote the comparison operand with zero extension.
2226
2227 // If the width of OpL/OpR excluding the duplicated sign bits is no greater
2228 // than the width of LHS/RHS, we can avoid inserting a zext_inreg operation
2229 // that we might not be able to remove.
2230 unsigned OpLEffectiveBits = DAG.ComputeMaxSignificantBits(OpL);
2231 unsigned OpREffectiveBits = DAG.ComputeMaxSignificantBits(OpR);
2232 if (OpLEffectiveBits <= LHS.getScalarValueSizeInBits() &&
2233 OpREffectiveBits <= RHS.getScalarValueSizeInBits()) {
2234 LHS = OpL;
2235 RHS = OpR;
2236 return;
2237 }
2238
2239 // Otherwise, use zext_inreg.
2240 LHS = ZExtPromotedInteger(LHS);
2241 RHS = ZExtPromotedInteger(RHS);
2242}
2243
2244/// PromoteSetCCOperands - Promote the operands of a comparison. This code is
2245/// shared among BR_CC, SELECT_CC, and SETCC handlers.
2246void DAGTypeLegalizer::PromoteSetCCOperands(SDValue &LHS, SDValue &RHS,
2247 ISD::CondCode CCCode) {
2248 // We have to insert explicit sign or zero extends. Note that we could
2249 // insert sign extends for ALL conditions. For those operations where either
2250 // zero or sign extension would be valid, we ask the target which extension
2251 // it would prefer.
2252
2253 // Signed comparisons always require sign extension.
2254 if (ISD::isSignedIntSetCC(CCCode)) {
2255 LHS = SExtPromotedInteger(LHS);
2256 RHS = SExtPromotedInteger(RHS);
2257 return;
2258 }
2259
2261 "Unknown integer comparison!");
2262
2263 SExtOrZExtPromotedOperands(LHS, RHS);
2264}
2265
2266SDValue DAGTypeLegalizer::PromoteIntOp_ANY_EXTEND(SDNode *N) {
2267 SDValue Op = GetPromotedInteger(N->getOperand(0));
2268 return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N), N->getValueType(0), Op);
2269}
2270
2271SDValue DAGTypeLegalizer::PromoteIntOp_ANY_EXTEND_VECTOR_INREG(SDNode *N) {
2272 SDValue Op = GetPromotedInteger(N->getOperand(0));
2273 EVT ResVT = N->getValueType(0);
2274 EVT OpVT = Op.getValueType();
2275 EVT NewVT = EVT::getVectorVT(*DAG.getContext(), OpVT.getScalarType(),
2276 ResVT.getVectorNumElements());
2277 Op = DAG.getExtractSubvector(SDLoc(Op), NewVT, Op, 0);
2278 return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N), ResVT, Op);
2279}
2280
2281SDValue DAGTypeLegalizer::PromoteIntOp_ATOMIC_STORE(AtomicSDNode *N) {
2282 SDValue Op1 = GetPromotedInteger(N->getOperand(1));
2283 return DAG.getAtomic(N->getOpcode(), SDLoc(N), N->getMemoryVT(),
2284 N->getChain(), Op1, N->getBasePtr(), N->getMemOperand());
2285}
2286
2287SDValue DAGTypeLegalizer::PromoteIntOp_BITCAST(SDNode *N) {
2288 EVT OutVT = N->getValueType(0);
2289 SDValue InOp = N->getOperand(0);
2290 EVT InVT = InOp.getValueType();
2291 EVT NInVT = TLI.getTypeToTransformTo(*DAG.getContext(), InVT);
2292 SDLoc dl(N);
2293
2294 switch (getTypeAction(InVT)) {
2296 // TODO: Handle big endian & vector input type.
2297 if (OutVT.isVector() && !InVT.isVector() &&
2298 DAG.getDataLayout().isLittleEndian()) {
2299 EVT EltVT = OutVT.getVectorElementType();
2300 TypeSize EltSize = EltVT.getSizeInBits();
2301 TypeSize NInSize = NInVT.getSizeInBits();
2302
2303 if (NInSize.hasKnownScalarFactor(EltSize)) {
2304 unsigned NumEltsWithPadding = NInSize.getKnownScalarFactor(EltSize);
2305 EVT WideVecVT =
2306 EVT::getVectorVT(*DAG.getContext(), EltVT, NumEltsWithPadding);
2307
2308 if (isTypeLegal(WideVecVT)) {
2309 SDValue Promoted = GetPromotedInteger(InOp);
2310 SDValue Cast = DAG.getNode(ISD::BITCAST, dl, WideVecVT, Promoted);
2311 return DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, OutVT, Cast,
2312 DAG.getVectorIdxConstant(0, dl));
2313 }
2314 }
2315 }
2316
2317 break;
2318 }
2319 default:
2320 break;
2321 }
2322
2323 // This should only occur in unusual situations like bitcasting to an
2324 // x86_fp80, so just turn it into a store+load
2325 return CreateStackStoreLoad(InOp, OutVT);
2326}
2327
2328SDValue DAGTypeLegalizer::PromoteIntOp_BR_CC(SDNode *N, unsigned OpNo) {
2329 assert(OpNo == 2 && "Don't know how to promote this operand!");
2330
2331 SDValue LHS = N->getOperand(2);
2332 SDValue RHS = N->getOperand(3);
2333 PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(1))->get());
2334
2335 // The chain (Op#0), CC (#1) and basic block destination (Op#4) are always
2336 // legal types.
2337 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2338 N->getOperand(1), LHS, RHS, N->getOperand(4)),
2339 0);
2340}
2341
2342SDValue DAGTypeLegalizer::PromoteIntOp_BRCOND(SDNode *N, unsigned OpNo) {
2343 assert(OpNo == 1 && "only know how to promote condition");
2344
2345 // Promote all the way up to the canonical SetCC type.
2346 SDValue Cond = PromoteTargetBoolean(N->getOperand(1), MVT::Other);
2347
2348 // The chain (Op#0) and basic block destination (Op#2) are always legal types.
2349 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Cond,
2350 N->getOperand(2)), 0);
2351}
2352
2353SDValue DAGTypeLegalizer::PromoteIntOp_COND_LOOP(SDNode *N, unsigned OpNo) {
2354 assert(OpNo == 1 && "only know how to promote condition");
2355
2356 // Promote all the way up to the canonical SetCC type.
2357 SDValue Cond = PromoteTargetBoolean(N->getOperand(1), MVT::Other);
2358
2359 // The chain (Op#0) is always a legal type.
2360 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Cond), 0);
2361}
2362
2363SDValue DAGTypeLegalizer::PromoteIntOp_BUILD_PAIR(SDNode *N) {
2364 // Since the result type is legal, the operands must promote to it.
2365 EVT OVT = N->getOperand(0).getValueType();
2366 SDValue Lo = ZExtPromotedInteger(N->getOperand(0));
2367 SDValue Hi = GetPromotedInteger(N->getOperand(1));
2368 assert(Lo.getValueType() == N->getValueType(0) && "Operand over promoted?");
2369 SDLoc dl(N);
2370
2371 Hi = DAG.getNode(
2372 ISD::SHL, dl, N->getValueType(0), Hi,
2373 DAG.getShiftAmountConstant(OVT.getSizeInBits(), N->getValueType(0), dl));
2374 return DAG.getNode(ISD::OR, dl, N->getValueType(0), Lo, Hi);
2375}
2376
2377SDValue DAGTypeLegalizer::PromoteIntOp_BUILD_VECTOR(SDNode *N) {
2378 // The vector type is legal but the element type is not. This implies
2379 // that the vector is a power-of-two in length and that the element
2380 // type does not have a strange size (eg: it is not i1).
2381 EVT VecVT = N->getValueType(0);
2382 unsigned NumElts = VecVT.getVectorNumElements();
2383 assert(!((NumElts & 1) && (!TLI.isTypeLegal(VecVT))) &&
2384 "Legal vector of one illegal element?");
2385
2386 // Promote the inserted value. The type does not need to match the
2387 // vector element type. Check that any extra bits introduced will be
2388 // truncated away.
2389 assert(N->getOperand(0).getValueSizeInBits() >=
2390 N->getValueType(0).getScalarSizeInBits() &&
2391 "Type of inserted value narrower than vector element type!");
2392
2394 for (unsigned i = 0; i < NumElts; ++i)
2395 NewOps.push_back(GetPromotedInteger(N->getOperand(i)));
2396
2397 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2398}
2399
2400SDValue DAGTypeLegalizer::PromoteIntOp_INSERT_VECTOR_ELT(SDNode *N,
2401 unsigned OpNo) {
2402 if (OpNo == 1) {
2403 // Promote the inserted value. This is valid because the type does not
2404 // have to match the vector element type.
2405
2406 // Check that any extra bits introduced will be truncated away.
2407 assert(N->getOperand(1).getValueSizeInBits() >=
2408 N->getValueType(0).getScalarSizeInBits() &&
2409 "Type of inserted value narrower than vector element type!");
2410 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2411 GetPromotedInteger(N->getOperand(1)),
2412 N->getOperand(2)),
2413 0);
2414 }
2415
2416 assert(OpNo == 2 && "Different operand and result vector types?");
2417
2418 // Promote the index.
2419 SDValue Idx = DAG.getZExtOrTrunc(N->getOperand(2), SDLoc(N),
2420 TLI.getVectorIdxTy(DAG.getDataLayout()));
2421 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2422 N->getOperand(1), Idx), 0);
2423}
2424
2425SDValue DAGTypeLegalizer::PromoteIntOp_ScalarOp(SDNode *N) {
2426 SDValue Op = GetPromotedInteger(N->getOperand(0));
2427
2428 // Integer SPLAT_VECTOR/SCALAR_TO_VECTOR operands are implicitly truncated,
2429 // so just promote the operand in place.
2430 return SDValue(DAG.UpdateNodeOperands(N, Op), 0);
2431}
2432
2433SDValue DAGTypeLegalizer::PromoteIntOp_SELECT(SDNode *N, unsigned OpNo) {
2434 assert(OpNo == 0 && "Only know how to promote the condition!");
2435 SDValue Cond = N->getOperand(0);
2436 EVT OpTy = N->getOperand(1).getValueType();
2437
2438 if (N->getOpcode() == ISD::VSELECT)
2439 if (SDValue Res = WidenVSELECTMask(N))
2440 return DAG.getNode(N->getOpcode(), SDLoc(N), N->getValueType(0),
2441 Res, N->getOperand(1), N->getOperand(2));
2442
2443 // Promote all the way up to the canonical SetCC type.
2444 EVT OpVT = N->getOpcode() == ISD::SELECT ? OpTy.getScalarType() : OpTy;
2445 Cond = PromoteTargetBoolean(Cond, OpVT);
2446
2447 return SDValue(DAG.UpdateNodeOperands(N, Cond, N->getOperand(1),
2448 N->getOperand(2)), 0);
2449}
2450
2451SDValue DAGTypeLegalizer::PromoteIntOp_SELECT_CC(SDNode *N, unsigned OpNo) {
2452 assert(OpNo == 0 && "Don't know how to promote this operand!");
2453
2454 SDValue LHS = N->getOperand(0);
2455 SDValue RHS = N->getOperand(1);
2456 PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(4))->get());
2457
2458 // The CC (#4) and the possible return values (#2 and #3) have legal types.
2459 return SDValue(DAG.UpdateNodeOperands(N, LHS, RHS, N->getOperand(2),
2460 N->getOperand(3), N->getOperand(4)), 0);
2461}
2462
2463SDValue DAGTypeLegalizer::PromoteIntOp_SETCC(SDNode *N, unsigned OpNo) {
2464 assert(OpNo == 0 && "Don't know how to promote this operand!");
2465
2466 SDValue LHS = N->getOperand(0);
2467 SDValue RHS = N->getOperand(1);
2468 PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(2))->get());
2469
2470 // The CC (#2) is always legal.
2471 return SDValue(DAG.UpdateNodeOperands(N, LHS, RHS, N->getOperand(2)), 0);
2472}
2473
2474SDValue DAGTypeLegalizer::PromoteIntOp_Shift(SDNode *N) {
2475 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2476 ZExtPromotedInteger(N->getOperand(1))), 0);
2477}
2478
2479SDValue DAGTypeLegalizer::PromoteIntOp_CMP(SDNode *N) {
2480 SDValue LHS = N->getOperand(0);
2481 SDValue RHS = N->getOperand(1);
2482
2483 if (N->getOpcode() == ISD::SCMP) {
2484 LHS = SExtPromotedInteger(LHS);
2485 RHS = SExtPromotedInteger(RHS);
2486 } else {
2487 SExtOrZExtPromotedOperands(LHS, RHS);
2488 }
2489
2490 return SDValue(DAG.UpdateNodeOperands(N, LHS, RHS), 0);
2491}
2492
2493SDValue DAGTypeLegalizer::PromoteIntOp_FunnelShift(SDNode *N) {
2494 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), N->getOperand(1),
2495 ZExtPromotedInteger(N->getOperand(2))), 0);
2496}
2497
2498SDValue DAGTypeLegalizer::PromoteIntOp_SIGN_EXTEND(SDNode *N) {
2499 SDValue Op = GetPromotedInteger(N->getOperand(0));
2500 SDLoc dl(N);
2501 Op = DAG.getNode(ISD::ANY_EXTEND, dl, N->getValueType(0), Op);
2502 return DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Op.getValueType(),
2503 Op, DAG.getValueType(N->getOperand(0).getValueType()));
2504}
2505
2506SDValue DAGTypeLegalizer::PromoteIntOp_SINT_TO_FP(SDNode *N) {
2507 return SDValue(DAG.UpdateNodeOperands(N,
2508 SExtPromotedInteger(N->getOperand(0))), 0);
2509}
2510
2511SDValue DAGTypeLegalizer::PromoteIntOp_STRICT_SINT_TO_FP(SDNode *N) {
2512 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2513 SExtPromotedInteger(N->getOperand(1))), 0);
2514}
2515
2516SDValue DAGTypeLegalizer::PromoteIntOp_STORE(StoreSDNode *N, unsigned OpNo){
2517 assert(ISD::isUNINDEXEDStore(N) && "Indexed store during type legalization!");
2518 SDValue Ch = N->getChain(), Ptr = N->getBasePtr();
2519 SDLoc dl(N);
2520
2521 SDValue Val = GetPromotedInteger(N->getValue()); // Get promoted value.
2522
2523 // Truncate the value and store the result.
2524 return DAG.getTruncStore(Ch, dl, Val, Ptr,
2525 N->getMemoryVT(), N->getMemOperand());
2526}
2527
2528SDValue DAGTypeLegalizer::PromoteIntOp_VP_STORE(VPStoreSDNode *N,
2529 unsigned OpNo) {
2530
2531 assert(OpNo == 1 && "Unexpected operand for promotion");
2532 assert(!N->isIndexed() && "expecting unindexed vp_store!");
2533
2534 SDValue DataOp = GetPromotedInteger(N->getValue());
2535 return DAG.getTruncStoreVP(N->getChain(), SDLoc(N), DataOp, N->getBasePtr(),
2536 N->getMask(), N->getVectorLength(),
2537 N->getMemoryVT(), N->getMemOperand(),
2538 N->isCompressingStore());
2539}
2540
2541SDValue DAGTypeLegalizer::PromoteIntOp_MSTORE(MaskedStoreSDNode *N,
2542 unsigned OpNo) {
2543 SDValue DataOp = N->getValue();
2544 SDValue Mask = N->getMask();
2545
2546 if (OpNo == 4) {
2547 // The Mask. Update in place.
2548 EVT DataVT = DataOp.getValueType();
2549 Mask = PromoteTargetBoolean(Mask, DataVT);
2550 SmallVector<SDValue, 4> NewOps(N->ops());
2551 NewOps[4] = Mask;
2552 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2553 }
2554
2555 assert(OpNo == 1 && "Unexpected operand for promotion");
2556 DataOp = GetPromotedInteger(DataOp);
2557
2558 return DAG.getMaskedStore(N->getChain(), SDLoc(N), DataOp, N->getBasePtr(),
2559 N->getOffset(), Mask, N->getMemoryVT(),
2560 N->getMemOperand(), N->getAddressingMode(),
2561 /*IsTruncating*/ true, N->isCompressingStore());
2562}
2563
2564SDValue DAGTypeLegalizer::PromoteIntOp_MLOAD(MaskedLoadSDNode *N,
2565 unsigned OpNo) {
2566 assert(OpNo == 3 && "Only know how to promote the mask!");
2567 EVT DataVT = N->getValueType(0);
2568 SDValue Mask = PromoteTargetBoolean(N->getOperand(OpNo), DataVT);
2569 SmallVector<SDValue, 4> NewOps(N->ops());
2570 NewOps[OpNo] = Mask;
2571 SDNode *Res = DAG.UpdateNodeOperands(N, NewOps);
2572 if (Res == N)
2573 return SDValue(Res, 0);
2574
2575 // Update triggered CSE, do our own replacement since caller can't.
2576 ReplaceValueWith(SDValue(N, 0), SDValue(Res, 0));
2577 ReplaceValueWith(SDValue(N, 1), SDValue(Res, 1));
2578 return SDValue();
2579}
2580
2581SDValue DAGTypeLegalizer::PromoteIntOp_MGATHER(MaskedGatherSDNode *N,
2582 unsigned OpNo) {
2583 SmallVector<SDValue, 5> NewOps(N->ops());
2584
2585 if (OpNo == 2) {
2586 // The Mask
2587 EVT DataVT = N->getValueType(0);
2588 NewOps[OpNo] = PromoteTargetBoolean(N->getOperand(OpNo), DataVT);
2589 } else if (OpNo == 4) {
2590 // The Index
2591 if (N->isIndexSigned())
2592 // Need to sign extend the index since the bits will likely be used.
2593 NewOps[OpNo] = SExtPromotedInteger(N->getOperand(OpNo));
2594 else
2595 NewOps[OpNo] = ZExtPromotedInteger(N->getOperand(OpNo));
2596 } else
2597 NewOps[OpNo] = GetPromotedInteger(N->getOperand(OpNo));
2598
2599 SDNode *Res = DAG.UpdateNodeOperands(N, NewOps);
2600 if (Res == N)
2601 return SDValue(Res, 0);
2602
2603 // Update triggered CSE, do our own replacement since caller can't.
2604 ReplaceValueWith(SDValue(N, 0), SDValue(Res, 0));
2605 ReplaceValueWith(SDValue(N, 1), SDValue(Res, 1));
2606 return SDValue();
2607}
2608
2609SDValue DAGTypeLegalizer::PromoteIntOp_MSCATTER(MaskedScatterSDNode *N,
2610 unsigned OpNo) {
2611 bool TruncateStore = N->isTruncatingStore();
2612 SmallVector<SDValue, 5> NewOps(N->ops());
2613
2614 if (OpNo == 2) {
2615 // The Mask
2616 EVT DataVT = N->getValue().getValueType();
2617 NewOps[OpNo] = PromoteTargetBoolean(N->getOperand(OpNo), DataVT);
2618 } else if (OpNo == 4) {
2619 // The Index
2620 if (N->isIndexSigned())
2621 // Need to sign extend the index since the bits will likely be used.
2622 NewOps[OpNo] = SExtPromotedInteger(N->getOperand(OpNo));
2623 else
2624 NewOps[OpNo] = ZExtPromotedInteger(N->getOperand(OpNo));
2625 } else {
2626 NewOps[OpNo] = GetPromotedInteger(N->getOperand(OpNo));
2627 TruncateStore = true;
2628 }
2629
2630 return DAG.getMaskedScatter(DAG.getVTList(MVT::Other), N->getMemoryVT(),
2631 SDLoc(N), NewOps, N->getMemOperand(),
2632 N->getIndexType(), TruncateStore);
2633}
2634
2635SDValue DAGTypeLegalizer::PromoteIntOp_VECTOR_COMPRESS(SDNode *N,
2636 unsigned OpNo) {
2637 assert(OpNo == 1 && "Can only promote VECTOR_COMPRESS mask.");
2638 SDValue Vec = N->getOperand(0);
2639 EVT VT = Vec.getValueType();
2640 SDValue Passthru = N->getOperand(2);
2641 SDValue Mask = PromoteTargetBoolean(N->getOperand(1), VT);
2642 return DAG.getNode(ISD::VECTOR_COMPRESS, SDLoc(N), VT, Vec, Mask, Passthru);
2643}
2644
2645SDValue DAGTypeLegalizer::PromoteIntOp_TRUNCATE(SDNode *N) {
2646 SDValue Op = GetPromotedInteger(N->getOperand(0));
2647 return DAG.getNode(ISD::TRUNCATE, SDLoc(N), N->getValueType(0), Op);
2648}
2649
2650SDValue DAGTypeLegalizer::PromoteIntOp_UINT_TO_FP(SDNode *N) {
2651 return SDValue(DAG.UpdateNodeOperands(N,
2652 ZExtPromotedInteger(N->getOperand(0))), 0);
2653}
2654
2655SDValue DAGTypeLegalizer::PromoteIntOp_CONVERT_FROM_ARBITRARY_FP(SDNode *N) {
2656 return SDValue(DAG.UpdateNodeOperands(N, GetPromotedInteger(N->getOperand(0)),
2657 N->getOperand(1)),
2658 0);
2659}
2660
2661SDValue DAGTypeLegalizer::PromoteIntOp_STRICT_UINT_TO_FP(SDNode *N) {
2662 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
2663 ZExtPromotedInteger(N->getOperand(1))), 0);
2664}
2665
2666SDValue DAGTypeLegalizer::PromoteIntOp_ZERO_EXTEND(SDNode *N) {
2667 SDLoc dl(N);
2668 SDValue Src = N->getOperand(0);
2669 SDValue Op = GetPromotedInteger(Src);
2670 EVT VT = N->getValueType(0);
2671
2672 // If this zext has the nneg flag and the target prefers sext, see if the
2673 // promoted input is already sign extended.
2674 // TODO: Should we have some way to set nneg on ISD::AND instead?
2675 if (N->getFlags().hasNonNeg() && Op.getValueType() == VT &&
2676 TLI.isSExtCheaperThanZExt(Src.getValueType(), VT)) {
2677 unsigned OpEffectiveBits = DAG.ComputeMaxSignificantBits(Op);
2678 if (OpEffectiveBits <= Src.getScalarValueSizeInBits())
2679 return Op;
2680 }
2681
2682 Op = DAG.getNode(ISD::ANY_EXTEND, dl, VT, Op);
2683 return DAG.getZeroExtendInReg(Op, dl, Src.getValueType());
2684}
2685
2686SDValue DAGTypeLegalizer::PromoteIntOp_FIX(SDNode *N) {
2687 SDValue Op2 = ZExtPromotedInteger(N->getOperand(2));
2688 return SDValue(
2689 DAG.UpdateNodeOperands(N, N->getOperand(0), N->getOperand(1), Op2), 0);
2690}
2691
2692SDValue DAGTypeLegalizer::PromoteIntOp_FRAMERETURNADDR(SDNode *N) {
2693 // Promote the RETURNADDR/FRAMEADDR argument to a supported integer width.
2694 SDValue Op = ZExtPromotedInteger(N->getOperand(0));
2695 return SDValue(DAG.UpdateNodeOperands(N, Op), 0);
2696}
2697
2698SDValue DAGTypeLegalizer::PromoteIntOp_ExpOp(SDNode *N) {
2699 bool IsStrict = N->isStrictFPOpcode();
2700 SDValue Chain = IsStrict ? N->getOperand(0) : SDValue();
2701
2702 bool IsPowI =
2703 N->getOpcode() == ISD::FPOWI || N->getOpcode() == ISD::STRICT_FPOWI;
2704 unsigned OpOffset = IsStrict ? 1 : 0;
2705
2706 // The integer operand is the last operand in FPOWI (or FLDEXP) (so the result
2707 // and floating point operand is already type legalized).
2708 RTLIB::Libcall LC = IsPowI ? RTLIB::getPOWI(N->getValueType(0))
2709 : RTLIB::getLDEXP(N->getValueType(0));
2710
2711 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
2712 if (LCImpl == RTLIB::Unsupported) {
2713 // Scalarize vector FPOWI instead of promoting the type. This allows the
2714 // scalar FPOWIs to be visited and converted to libcalls before promoting
2715 // the type.
2716 // FIXME: This should be done in LegalizeVectorOps/LegalizeDAG, but call
2717 // lowering needs the unpromoted EVT.
2718 if (IsPowI && N->getValueType(0).isVector())
2719 return DAG.UnrollVectorOp(N);
2720 SmallVector<SDValue, 3> NewOps(N->ops());
2721 NewOps[1 + OpOffset] = SExtPromotedInteger(N->getOperand(1 + OpOffset));
2722 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2723 }
2724
2725 // We can't just promote the exponent type in FPOWI, since we want to lower
2726 // the node to a libcall and we if we promote to a type larger than
2727 // sizeof(int) the libcall might not be according to the targets ABI. Instead
2728 // we rewrite to a libcall here directly, letting makeLibCall handle promotion
2729 // if the target accepts it according to shouldSignExtendTypeInLibCall.
2730
2731 // A wider-than-int exponent can't be passed in an int (there's no wider
2732 // libcall), so bail like the soften/expand paths. A narrower one is
2733 // sign-extended to int by the makeLibCall below.
2734 if (N->getOperand(1 + OpOffset).getScalarValueSizeInBits() >
2735 DAG.getLibInfo().getIntSize()) {
2736 const Function &Fn = DAG.getMachineFunction().getFunction();
2737 Fn.getContext().diagnose(DiagnosticInfoLegalizationFailure(
2738 Twine(IsPowI ? "powi" : "ldexp") +
2739 " exponent does not match sizeof(int)",
2740 Fn, N->getDebugLoc()));
2741 if (IsStrict)
2742 ReplaceValueWith(SDValue(N, 1), Chain);
2743 ReplaceValueWith(SDValue(N, 0), DAG.getPOISON(N->getValueType(0)));
2744 return SDValue();
2745 }
2746
2747 TargetLowering::MakeLibCallOptions CallOptions;
2748 CallOptions.setIsSigned(true);
2749 SDValue Ops[2] = {N->getOperand(0 + OpOffset), N->getOperand(1 + OpOffset)};
2750 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(
2751 DAG, LCImpl, N->getValueType(0), Ops, CallOptions, SDLoc(N), Chain);
2752 ReplaceValueWith(SDValue(N, 0), Tmp.first);
2753 if (IsStrict)
2754 ReplaceValueWith(SDValue(N, 1), Tmp.second);
2755 return SDValue();
2756}
2757
2759 switch (N->getOpcode()) {
2760 default:
2761 llvm_unreachable("Expected integer vector reduction");
2762 case ISD::VECREDUCE_ADD:
2763 case ISD::VECREDUCE_MUL:
2764 case ISD::VECREDUCE_AND:
2765 case ISD::VECREDUCE_OR:
2766 case ISD::VECREDUCE_XOR:
2767 case ISD::VP_REDUCE_ADD:
2768 case ISD::VP_REDUCE_MUL:
2769 case ISD::VP_REDUCE_AND:
2770 case ISD::VP_REDUCE_OR:
2771 case ISD::VP_REDUCE_XOR:
2772 return ISD::ANY_EXTEND;
2775 case ISD::VP_REDUCE_SMAX:
2776 case ISD::VP_REDUCE_SMIN:
2777 return ISD::SIGN_EXTEND;
2780 case ISD::VP_REDUCE_UMAX:
2781 case ISD::VP_REDUCE_UMIN:
2782 return ISD::ZERO_EXTEND;
2783 }
2784}
2785
2786SDValue DAGTypeLegalizer::PromoteIntOpVectorReduction(SDNode *N, SDValue V) {
2787 switch (getExtendForIntVecReduction(N)) {
2788 default:
2789 llvm_unreachable("Impossible extension kind for integer reduction");
2790 case ISD::ANY_EXTEND:
2791 return GetPromotedInteger(V);
2792 case ISD::SIGN_EXTEND:
2793 return SExtPromotedInteger(V);
2794 case ISD::ZERO_EXTEND:
2795 return ZExtPromotedInteger(V);
2796 }
2797}
2798
2799SDValue DAGTypeLegalizer::PromoteIntOp_VECREDUCE(SDNode *N) {
2800 SDLoc dl(N);
2801 SDValue Op = PromoteIntOpVectorReduction(N, N->getOperand(0));
2802
2803 EVT OrigEltVT = N->getOperand(0).getValueType().getVectorElementType();
2804 EVT InVT = Op.getValueType();
2805 EVT EltVT = InVT.getVectorElementType();
2806 EVT ResVT = N->getValueType(0);
2807 unsigned Opcode = N->getOpcode();
2808
2809 // An i1 vecreduce_xor is equivalent to vecreduce_add, use that instead if
2810 // vecreduce_xor is not legal
2811 if (Opcode == ISD::VECREDUCE_XOR && OrigEltVT == MVT::i1 &&
2812 !TLI.isOperationLegalOrCustom(ISD::VECREDUCE_XOR, InVT) &&
2813 TLI.isOperationLegalOrCustom(ISD::VECREDUCE_ADD, InVT))
2814 Opcode = ISD::VECREDUCE_ADD;
2815
2816 // An i1 vecreduce_or is equivalent to vecreduce_umax, use that instead if
2817 // vecreduce_or is not legal
2818 else if (Opcode == ISD::VECREDUCE_OR && OrigEltVT == MVT::i1 &&
2819 !TLI.isOperationLegalOrCustom(ISD::VECREDUCE_OR, InVT) &&
2820 TLI.isOperationLegalOrCustom(ISD::VECREDUCE_UMAX, InVT)) {
2821 Opcode = ISD::VECREDUCE_UMAX;
2822 // Can't use promoteTargetBoolean here because we still need
2823 // to either sign_ext or zero_ext in the undefined case.
2824 switch (TLI.getBooleanContents(InVT)) {
2827 Op = ZExtPromotedInteger(N->getOperand(0));
2828 break;
2830 Op = SExtPromotedInteger(N->getOperand(0));
2831 break;
2832 }
2833 }
2834
2835 // An i1 vecreduce_and is equivalent to vecreduce_umin, use that instead if
2836 // vecreduce_and is not legal
2837 else if (Opcode == ISD::VECREDUCE_AND && OrigEltVT == MVT::i1 &&
2838 !TLI.isOperationLegalOrCustom(ISD::VECREDUCE_AND, InVT) &&
2839 TLI.isOperationLegalOrCustom(ISD::VECREDUCE_UMIN, InVT)) {
2840 Opcode = ISD::VECREDUCE_UMIN;
2841 // Can't use promoteTargetBoolean here because we still need
2842 // to either sign_ext or zero_ext in the undefined case.
2843 switch (TLI.getBooleanContents(InVT)) {
2846 Op = ZExtPromotedInteger(N->getOperand(0));
2847 break;
2849 Op = SExtPromotedInteger(N->getOperand(0));
2850 break;
2851 }
2852 }
2853
2854 if (ResVT.bitsGE(EltVT))
2855 return DAG.getNode(Opcode, SDLoc(N), ResVT, Op);
2856
2857 // Result size must be >= element size. If this is not the case after
2858 // promotion, also promote the result type and then truncate.
2859 SDValue Reduce = DAG.getNode(Opcode, dl, EltVT, Op);
2860 return DAG.getNode(ISD::TRUNCATE, dl, ResVT, Reduce);
2861}
2862
2863SDValue DAGTypeLegalizer::PromoteIntOp_VP_REDUCE(SDNode *N, unsigned OpNo) {
2864 SDLoc DL(N);
2865 SDValue Op = N->getOperand(OpNo);
2866 SmallVector<SDValue, 4> NewOps(N->ops());
2867
2868 if (OpNo == 2) { // Mask
2869 // Update in place.
2870 NewOps[2] = PromoteTargetBoolean(Op, N->getOperand(1).getValueType());
2871 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2872 }
2873
2874 assert(OpNo == 1 && "Unexpected operand for promotion");
2875
2876 Op = PromoteIntOpVectorReduction(N, Op);
2877
2878 NewOps[OpNo] = Op;
2879
2880 EVT VT = N->getValueType(0);
2881 EVT EltVT = Op.getValueType().getScalarType();
2882
2883 if (VT.bitsGE(EltVT))
2884 return DAG.getNode(N->getOpcode(), SDLoc(N), VT, NewOps);
2885
2886 // Result size must be >= element/start-value size. If this is not the case
2887 // after promotion, also promote both the start value and result type and
2888 // then truncate.
2889 NewOps[0] =
2890 DAG.getNode(getExtendForIntVecReduction(N), DL, EltVT, N->getOperand(0));
2891 SDValue Reduce = DAG.getNode(N->getOpcode(), DL, EltVT, NewOps);
2892 return DAG.getNode(ISD::TRUNCATE, DL, VT, Reduce);
2893}
2894
2895SDValue DAGTypeLegalizer::PromoteIntOp_SET_ROUNDING(SDNode *N) {
2896 SDValue Op = ZExtPromotedInteger(N->getOperand(1));
2897 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Op), 0);
2898}
2899
2900SDValue DAGTypeLegalizer::PromoteIntOp_STACKMAP(SDNode *N, unsigned OpNo) {
2901 assert(OpNo > 1); // Because the first two arguments are guaranteed legal.
2902 SmallVector<SDValue> NewOps(N->ops());
2903 NewOps[OpNo] = GetPromotedInteger(NewOps[OpNo]);
2904 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2905}
2906
2907SDValue DAGTypeLegalizer::PromoteIntOp_PATCHPOINT(SDNode *N, unsigned OpNo) {
2908 assert(OpNo >= 7);
2909 SmallVector<SDValue> NewOps(N->ops());
2910 NewOps[OpNo] = GetPromotedInteger(NewOps[OpNo]);
2911 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2912}
2913
2914SDValue DAGTypeLegalizer::PromoteIntOp_WRITE_REGISTER(SDNode *N,
2915 unsigned OpNo) {
2916 const Function &Fn = DAG.getMachineFunction().getFunction();
2917 Fn.getContext().diagnose(DiagnosticInfoLegalizationFailure(
2918 "cannot use llvm.write_register with illegal type", Fn,
2919 N->getDebugLoc()));
2920 return N->getOperand(0);
2921}
2922
2923SDValue DAGTypeLegalizer::PromoteIntOp_VP_STRIDED(SDNode *N, unsigned OpNo) {
2924 assert((N->getOpcode() == ISD::EXPERIMENTAL_VP_STRIDED_LOAD && OpNo == 3) ||
2925 (N->getOpcode() == ISD::EXPERIMENTAL_VP_STRIDED_STORE && OpNo == 4));
2926
2927 SmallVector<SDValue, 8> NewOps(N->ops());
2928 NewOps[OpNo] = SExtPromotedInteger(N->getOperand(OpNo));
2929 SDNode *Res = DAG.UpdateNodeOperands(N, NewOps);
2930 if (Res == N)
2931 return SDValue(Res, 0);
2932
2933 // Update triggered CSE, do our own replacement since caller can't.
2934 ReplaceValueWith(SDValue(N, 0), SDValue(Res, 0));
2935 ReplaceValueWith(SDValue(N, 1), SDValue(Res, 1));
2936 return SDValue();
2937}
2938
2939SDValue DAGTypeLegalizer::PromoteIntOp_VP_SPLICE(SDNode *N, unsigned OpNo) {
2940 SmallVector<SDValue, 6> NewOps(N->ops());
2941
2942 if (OpNo == 2) { // Offset operand
2943 NewOps[OpNo] = SExtPromotedInteger(N->getOperand(OpNo));
2944 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2945 }
2946
2947 assert((OpNo == 4 || OpNo == 5) && "Unexpected operand for promotion");
2948
2949 NewOps[OpNo] = ZExtPromotedInteger(N->getOperand(OpNo));
2950 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2951}
2952
2953SDValue DAGTypeLegalizer::PromoteIntOp_VECTOR_HISTOGRAM(SDNode *N,
2954 unsigned OpNo) {
2955 assert(OpNo == 1 && "Unexpected operand for promotion");
2956 SmallVector<SDValue, 7> NewOps(N->ops());
2957 NewOps[1] = GetPromotedInteger(N->getOperand(1));
2958 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2959}
2960
2961SDValue DAGTypeLegalizer::PromoteIntOp_UnaryBooleanVectorOp(SDNode *N,
2962 unsigned OpNo) {
2963 assert(OpNo == 0 && "Unexpected operand for promotion");
2964 SDValue Op = N->getOperand(0);
2965
2966 SDValue NewOp;
2967 if (TLI.getBooleanContents(Op.getValueType()) ==
2969 NewOp = SExtPromotedInteger(Op);
2970 else
2971 NewOp = ZExtPromotedInteger(Op);
2972
2973 return SDValue(DAG.UpdateNodeOperands(N, NewOp), 0);
2974}
2975
2976SDValue DAGTypeLegalizer::PromoteIntOp_GET_ACTIVE_LANE_MASK(SDNode *N) {
2977 SmallVector<SDValue, 1> NewOps(N->ops());
2978 NewOps[0] = ZExtPromotedInteger(N->getOperand(0));
2979 NewOps[1] = ZExtPromotedInteger(N->getOperand(1));
2980 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2981}
2982
2983SDValue DAGTypeLegalizer::PromoteIntOp_VECTOR_MATCH(SDNode *N, unsigned OpNo) {
2984 assert(OpNo < 3 && "Unexpected operand for promotion");
2985 if (OpNo != 2)
2986 return TLI.expandVectorMatch(N, DAG);
2987
2988 SmallVector<SDValue, 3> NewOps(N->ops());
2989 NewOps[2] = PromoteTargetBoolean(N->getOperand(2), N->getValueType(0));
2990 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2991}
2992
2993SDValue DAGTypeLegalizer::PromoteIntOp_MaskedBinOp(SDNode *N, unsigned OpNo) {
2994 assert(OpNo == 2);
2995 SmallVector<SDValue, 3> NewOps(N->ops());
2996 NewOps[2] = PromoteTargetBoolean(NewOps[2], N->getValueType(0));
2997 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
2998}
2999
3000SDValue DAGTypeLegalizer::PromoteIntOp_PARTIAL_REDUCE_MLA(SDNode *N) {
3001 SmallVector<SDValue, 1> NewOps(N->ops());
3002 switch (N->getOpcode()) {
3004 NewOps[1] = SExtPromotedInteger(N->getOperand(1));
3005 NewOps[2] = SExtPromotedInteger(N->getOperand(2));
3006 break;
3008 NewOps[1] = ZExtPromotedInteger(N->getOperand(1));
3009 NewOps[2] = ZExtPromotedInteger(N->getOperand(2));
3010 break;
3012 NewOps[1] = SExtPromotedInteger(N->getOperand(1));
3013 NewOps[2] = ZExtPromotedInteger(N->getOperand(2));
3014 break;
3015 default:
3016 llvm_unreachable("unexpected opcode");
3017 }
3018 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
3019}
3020
3021SDValue DAGTypeLegalizer::PromoteIntOp_LOOP_DEPENDENCE_MASK(SDNode *N) {
3022 SDValue NewOps[4];
3023 NewOps[0] = ZExtPromotedInteger(N->getOperand(0));
3024 NewOps[1] = ZExtPromotedInteger(N->getOperand(1));
3025 NewOps[2] = ZExtPromotedInteger(N->getOperand(2));
3026 NewOps[3] = N->getOperand(3);
3027 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
3028}
3029
3030SDValue DAGTypeLegalizer::PromoteIntOp_VECTOR_REPEAT(SDNode *N) {
3031 SDLoc DL(N);
3032 SDValue Src = GetPromotedInteger(N->getOperand(0));
3033 EVT SrcVT = Src.getValueType();
3034 EVT OrigVT = N->getValueType(0);
3035 EVT NewVT = OrigVT.changeVectorElementType(*DAG.getContext(),
3036 SrcVT.getVectorElementType());
3037 SDValue Res = DAG.getNode(ISD::VECTOR_REPEAT, DL, NewVT, Src);
3038 return DAG.getNode(ISD::TRUNCATE, DL, OrigVT, Res);
3039}
3040
3041//===----------------------------------------------------------------------===//
3042// Integer Result Expansion
3043//===----------------------------------------------------------------------===//
3044
3045/// ExpandIntegerResult - This method is called when the specified result of the
3046/// specified node is found to need expansion. At this point, the node may also
3047/// have invalid operands or may have other results that need promotion, we just
3048/// know that (at least) one result needs expansion.
3049void DAGTypeLegalizer::ExpandIntegerResult(SDNode *N, unsigned ResNo) {
3050 LLVM_DEBUG(dbgs() << "Expand integer result: "; N->dump(&DAG));
3051 SDValue Lo, Hi;
3052 Lo = Hi = SDValue();
3053
3054 // See if the target wants to custom expand this node.
3055 if (CustomLowerNode(N, N->getValueType(ResNo), true))
3056 return;
3057
3058 switch (N->getOpcode()) {
3059 default:
3060#ifndef NDEBUG
3061 dbgs() << "ExpandIntegerResult #" << ResNo << ": ";
3062 N->dump(&DAG); dbgs() << "\n";
3063#endif
3064 report_fatal_error("do not know how to expand the result of this "
3065 "operator!");
3066
3067 case ISD::ARITH_FENCE: SplitRes_ARITH_FENCE(N, Lo, Hi); break;
3068 case ISD::MERGE_VALUES: SplitRes_MERGE_VALUES(N, ResNo, Lo, Hi); break;
3069 case ISD::SELECT: SplitRes_Select(N, Lo, Hi); break;
3070 case ISD::SELECT_CC: SplitRes_SELECT_CC(N, Lo, Hi); break;
3071 case ISD::POISON:
3072 case ISD::UNDEF: SplitRes_UNDEF(N, Lo, Hi); break;
3073 case ISD::FREEZE: SplitRes_FREEZE(N, Lo, Hi); break;
3074 case ISD::SETCC: ExpandIntRes_SETCC(N, Lo, Hi); break;
3075
3076 case ISD::BITCAST: ExpandRes_BITCAST(N, Lo, Hi); break;
3077 case ISD::BUILD_PAIR: ExpandRes_BUILD_PAIR(N, Lo, Hi); break;
3078 case ISD::EXTRACT_ELEMENT: ExpandRes_EXTRACT_ELEMENT(N, Lo, Hi); break;
3079 case ISD::EXTRACT_VECTOR_ELT: ExpandRes_EXTRACT_VECTOR_ELT(N, Lo, Hi); break;
3080 case ISD::VAARG: ExpandRes_VAARG(N, Lo, Hi); break;
3081
3082 case ISD::ANY_EXTEND: ExpandIntRes_ANY_EXTEND(N, Lo, Hi); break;
3083 case ISD::AssertSext: ExpandIntRes_AssertSext(N, Lo, Hi); break;
3084 case ISD::AssertZext: ExpandIntRes_AssertZext(N, Lo, Hi); break;
3085 case ISD::BITREVERSE: ExpandIntRes_BITREVERSE(N, Lo, Hi); break;
3086 case ISD::BSWAP: ExpandIntRes_BSWAP(N, Lo, Hi); break;
3087 case ISD::PARITY: ExpandIntRes_PARITY(N, Lo, Hi); break;
3088 case ISD::Constant: ExpandIntRes_Constant(N, Lo, Hi); break;
3089 case ISD::ABS:
3091 ExpandIntRes_ABS(N, Lo, Hi);
3092 break;
3093 case ISD::ABDS:
3094 case ISD::ABDU: ExpandIntRes_ABD(N, Lo, Hi); break;
3096 case ISD::CTLZ: ExpandIntRes_CTLZ(N, Lo, Hi); break;
3097 case ISD::CTLS: ExpandIntRes_CTLS(N, Lo, Hi); break;
3098 case ISD::CTPOP: ExpandIntRes_CTPOP(N, Lo, Hi); break;
3100 case ISD::CTTZ: ExpandIntRes_CTTZ(N, Lo, Hi); break;
3101 case ISD::GET_ROUNDING:ExpandIntRes_GET_ROUNDING(N, Lo, Hi); break;
3103 case ISD::FP_TO_SINT:
3105 case ISD::FP_TO_UINT: ExpandIntRes_FP_TO_XINT(N, Lo, Hi); break;
3107 case ISD::FP_TO_UINT_SAT: ExpandIntRes_FP_TO_XINT_SAT(N, Lo, Hi); break;
3108 case ISD::STRICT_LROUND:
3109 case ISD::STRICT_LRINT:
3110 case ISD::LROUND:
3111 case ISD::LRINT:
3113 case ISD::STRICT_LLRINT:
3114 case ISD::LLROUND:
3115 case ISD::LLRINT: ExpandIntRes_XROUND_XRINT(N, Lo, Hi); break;
3116 case ISD::LOAD: ExpandIntRes_LOAD(cast<LoadSDNode>(N), Lo, Hi); break;
3117 case ISD::MUL: ExpandIntRes_MUL(N, Lo, Hi); break;
3119 case ISD::READSTEADYCOUNTER: ExpandIntRes_READCOUNTER(N, Lo, Hi); break;
3120 case ISD::SDIV: ExpandIntRes_SDIV(N, Lo, Hi); break;
3121 case ISD::SIGN_EXTEND: ExpandIntRes_SIGN_EXTEND(N, Lo, Hi); break;
3122 case ISD::SIGN_EXTEND_INREG: ExpandIntRes_SIGN_EXTEND_INREG(N, Lo, Hi); break;
3123 case ISD::SREM: ExpandIntRes_SREM(N, Lo, Hi); break;
3124 case ISD::TRUNCATE: ExpandIntRes_TRUNCATE(N, Lo, Hi); break;
3125 case ISD::UDIV: ExpandIntRes_UDIV(N, Lo, Hi); break;
3126 case ISD::UREM: ExpandIntRes_UREM(N, Lo, Hi); break;
3127 case ISD::ZERO_EXTEND: ExpandIntRes_ZERO_EXTEND(N, Lo, Hi); break;
3128 case ISD::ATOMIC_LOAD: ExpandIntRes_ATOMIC_LOAD(N, Lo, Hi); break;
3129
3141 case ISD::ATOMIC_SWAP:
3142 case ISD::ATOMIC_CMP_SWAP: {
3143 std::pair<SDValue, SDValue> Tmp = ExpandAtomic(N);
3144 SplitInteger(Tmp.first, Lo, Hi);
3145 ReplaceValueWith(SDValue(N, 1), Tmp.second);
3146 break;
3147 }
3149 AtomicSDNode *AN = cast<AtomicSDNode>(N);
3150 SDVTList VTs = DAG.getVTList(N->getValueType(0), MVT::Other);
3151 SDValue Tmp = DAG.getAtomicCmpSwap(
3152 ISD::ATOMIC_CMP_SWAP, SDLoc(N), AN->getMemoryVT(), VTs,
3153 N->getOperand(0), N->getOperand(1), N->getOperand(2), N->getOperand(3),
3154 AN->getMemOperand());
3155
3156 // Expanding to the strong ATOMIC_CMP_SWAP node means we can determine
3157 // success simply by comparing the loaded value against the ingoing
3158 // comparison.
3159 SDValue Success = DAG.getSetCC(SDLoc(N), N->getValueType(1), Tmp,
3160 N->getOperand(2), ISD::SETEQ);
3161
3162 SplitInteger(Tmp, Lo, Hi);
3163 ReplaceValueWith(SDValue(N, 1), Success);
3164 ReplaceValueWith(SDValue(N, 2), Tmp.getValue(1));
3165 break;
3166 }
3167
3168 case ISD::AND:
3169 case ISD::OR:
3170 case ISD::XOR: ExpandIntRes_Logical(N, Lo, Hi); break;
3171
3172 case ISD::UMAX:
3173 case ISD::SMAX:
3174 case ISD::UMIN:
3175 case ISD::SMIN: ExpandIntRes_MINMAX(N, Lo, Hi); break;
3176
3177 case ISD::SCMP:
3178 case ISD::UCMP: ExpandIntRes_CMP(N, Lo, Hi); break;
3179
3180 case ISD::ADD:
3181 case ISD::SUB: ExpandIntRes_ADDSUB(N, Lo, Hi); break;
3182
3183 case ISD::ADDC:
3184 case ISD::SUBC: ExpandIntRes_ADDSUBC(N, Lo, Hi); break;
3185
3186 case ISD::ADDE:
3187 case ISD::SUBE: ExpandIntRes_ADDSUBE(N, Lo, Hi); break;
3188
3189 case ISD::UADDO_CARRY:
3190 case ISD::USUBO_CARRY: ExpandIntRes_UADDSUBO_CARRY(N, Lo, Hi); break;
3191
3192 case ISD::SADDO_CARRY:
3193 case ISD::SSUBO_CARRY: ExpandIntRes_SADDSUBO_CARRY(N, Lo, Hi); break;
3194
3195 case ISD::SHL:
3196 case ISD::SRA:
3197 case ISD::SRL: ExpandIntRes_Shift(N, Lo, Hi); break;
3198
3199 case ISD::SADDO:
3200 case ISD::SSUBO: ExpandIntRes_SADDSUBO(N, Lo, Hi); break;
3201 case ISD::UADDO:
3202 case ISD::USUBO: ExpandIntRes_UADDSUBO(N, Lo, Hi); break;
3203 case ISD::UMULO:
3204 case ISD::SMULO: ExpandIntRes_XMULO(N, Lo, Hi); break;
3205
3206 case ISD::SADDSAT:
3207 case ISD::UADDSAT:
3208 case ISD::SSUBSAT:
3209 case ISD::USUBSAT: ExpandIntRes_ADDSUBSAT(N, Lo, Hi); break;
3210
3211 case ISD::SSHLSAT:
3212 case ISD::USHLSAT: ExpandIntRes_SHLSAT(N, Lo, Hi); break;
3213
3214 case ISD::AVGCEILS:
3215 case ISD::AVGCEILU:
3216 case ISD::AVGFLOORS:
3217 case ISD::AVGFLOORU: ExpandIntRes_AVG(N, Lo, Hi); break;
3218
3219 case ISD::SMULFIX:
3220 case ISD::SMULFIXSAT:
3221 case ISD::UMULFIX:
3222 case ISD::UMULFIXSAT: ExpandIntRes_MULFIX(N, Lo, Hi); break;
3223
3224 case ISD::SDIVFIX:
3225 case ISD::SDIVFIXSAT:
3226 case ISD::UDIVFIX:
3227 case ISD::UDIVFIXSAT: ExpandIntRes_DIVFIX(N, Lo, Hi); break;
3228
3229 case ISD::VECREDUCE_ADD:
3230 case ISD::VECREDUCE_MUL:
3231 case ISD::VECREDUCE_AND:
3232 case ISD::VECREDUCE_OR:
3233 case ISD::VECREDUCE_XOR:
3237 case ISD::VECREDUCE_UMIN: ExpandIntRes_VECREDUCE(N, Lo, Hi); break;
3238
3239 case ISD::ROTL:
3240 case ISD::ROTR:
3241 ExpandIntRes_Rotate(N, Lo, Hi);
3242 break;
3243
3244 case ISD::FSHL:
3245 case ISD::FSHR:
3246 ExpandIntRes_FunnelShift(N, Lo, Hi);
3247 break;
3248
3249 case ISD::CLMUL:
3250 case ISD::CLMULR:
3251 case ISD::CLMULH:
3252 ExpandIntRes_CLMUL(N, Lo, Hi);
3253 break;
3254
3255 case ISD::PEXT:
3256 ExpandIntRes_PEXT(N, Lo, Hi);
3257 break;
3258
3259 case ISD::PDEP:
3260 ExpandIntRes_PDEP(N, Lo, Hi);
3261 break;
3262
3263 case ISD::MULHS:
3264 case ISD::MULHU:
3265 ExpandIntRes_MULH(N, Lo, Hi);
3266 break;
3267
3268 case ISD::VSCALE:
3269 ExpandIntRes_VSCALE(N, Lo, Hi);
3270 break;
3271
3272 case ISD::READ_REGISTER:
3273 ExpandIntRes_READ_REGISTER(N, Lo, Hi);
3274 break;
3275
3276 case ISD::CTTZ_ELTS:
3278 ExpandIntRes_CTTZ_ELTS(N, Lo, Hi);
3279 break;
3280 }
3281
3282 // If Lo/Hi is null, the sub-method took care of registering results etc.
3283 if (Lo.getNode())
3284 SetExpandedInteger(SDValue(N, ResNo), Lo, Hi);
3285}
3286
3287/// Lower an atomic node to the appropriate builtin call.
3288std::pair <SDValue, SDValue> DAGTypeLegalizer::ExpandAtomic(SDNode *Node) {
3289 unsigned Opc = Node->getOpcode();
3290 MVT VT = cast<AtomicSDNode>(Node)->getMemoryVT().getSimpleVT();
3291 AtomicOrdering order = cast<AtomicSDNode>(Node)->getMergedOrdering();
3292 // Lower to outline atomic libcall if outline atomics enabled,
3293 // or to sync libcall otherwise
3294 RTLIB::Libcall LC = RTLIB::getOUTLINE_ATOMIC(Opc, order, VT);
3295 EVT RetVT = Node->getValueType(0);
3296 TargetLowering::MakeLibCallOptions CallOptions;
3298
3299 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
3300 if (LCImpl != RTLIB::Unsupported) {
3301 Ops.append(Node->op_begin() + 2, Node->op_end());
3302 Ops.push_back(Node->getOperand(1));
3303 } else {
3304 LC = RTLIB::getSYNC(Opc, VT);
3305 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
3306 "Unexpected atomic op or value type!");
3307 Ops.append(Node->op_begin() + 1, Node->op_end());
3308 LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
3309 }
3310 return TLI.makeLibCall(DAG, LCImpl, RetVT, Ops, CallOptions, SDLoc(Node),
3311 Node->getOperand(0));
3312}
3313
3314/// N is a shift by a value that needs to be expanded,
3315/// and the shift amount is a constant 'Amt'. Expand the operation.
3316void DAGTypeLegalizer::ExpandShiftByConstant(SDNode *N, const APInt &Amt,
3317 SDValue &Lo, SDValue &Hi) {
3318 SDLoc DL(N);
3319 // Expand the incoming operand to be shifted, so that we have its parts
3320 SDValue InL, InH;
3321 GetExpandedInteger(N->getOperand(0), InL, InH);
3322
3323 // Though Amt shouldn't usually be 0, it's possible. E.g. when legalization
3324 // splitted a vector shift, like this: <op1, op2> SHL <0, 2>.
3325 if (!Amt) {
3326 Lo = InL;
3327 Hi = InH;
3328 return;
3329 }
3330
3331 EVT NVT = InL.getValueType();
3332 unsigned VTBits = N->getValueType(0).getSizeInBits();
3333 unsigned NVTBits = NVT.getSizeInBits();
3334
3335 if (N->getOpcode() == ISD::SHL) {
3336 if (Amt.uge(VTBits)) {
3337 Lo = Hi = DAG.getConstant(0, DL, NVT);
3338 } else if (Amt.ugt(NVTBits)) {
3339 Lo = DAG.getConstant(0, DL, NVT);
3340 Hi = DAG.getNode(ISD::SHL, DL, NVT, InL,
3341 DAG.getShiftAmountConstant(Amt - NVTBits, NVT, DL));
3342 } else if (Amt == NVTBits) {
3343 Lo = DAG.getConstant(0, DL, NVT);
3344 Hi = InL;
3345 } else {
3346 Lo = DAG.getNode(ISD::SHL, DL, NVT, InL,
3347 DAG.getShiftAmountConstant(Amt, NVT, DL));
3348 // Use FSHL if legal so we don't need to combine it later.
3349 if (TLI.isOperationLegal(ISD::FSHL, NVT)) {
3350 Hi = DAG.getNode(ISD::FSHL, DL, NVT, InH, InL,
3351 DAG.getShiftAmountConstant(Amt, NVT, DL));
3352 } else {
3353 Hi = DAG.getNode(
3354 ISD::OR, DL, NVT,
3355 DAG.getNode(ISD::SHL, DL, NVT, InH,
3356 DAG.getShiftAmountConstant(Amt, NVT, DL)),
3357 DAG.getNode(ISD::SRL, DL, NVT, InL,
3358 DAG.getShiftAmountConstant(-Amt + NVTBits, NVT, DL)));
3359 }
3360 }
3361 return;
3362 }
3363
3364 if (N->getOpcode() == ISD::SRL) {
3365 if (Amt.uge(VTBits)) {
3366 Lo = Hi = DAG.getConstant(0, DL, NVT);
3367 } else if (Amt.ugt(NVTBits)) {
3368 Lo = DAG.getNode(ISD::SRL, DL, NVT, InH,
3369 DAG.getShiftAmountConstant(Amt - NVTBits, NVT, DL));
3370 Hi = DAG.getConstant(0, DL, NVT);
3371 } else if (Amt == NVTBits) {
3372 Lo = InH;
3373 Hi = DAG.getConstant(0, DL, NVT);
3374 } else {
3375 // Use FSHR if legal so we don't need to combine it later.
3376 if (TLI.isOperationLegal(ISD::FSHR, NVT)) {
3377 Lo = DAG.getNode(ISD::FSHR, DL, NVT, InH, InL,
3378 DAG.getShiftAmountConstant(Amt, NVT, DL));
3379 } else {
3380 Lo = DAG.getNode(
3381 ISD::OR, DL, NVT,
3382 DAG.getNode(ISD::SRL, DL, NVT, InL,
3383 DAG.getShiftAmountConstant(Amt, NVT, DL)),
3384 DAG.getNode(ISD::SHL, DL, NVT, InH,
3385 DAG.getShiftAmountConstant(-Amt + NVTBits, NVT, DL)));
3386 }
3387 Hi = DAG.getNode(ISD::SRL, DL, NVT, InH,
3388 DAG.getShiftAmountConstant(Amt, NVT, DL));
3389 }
3390 return;
3391 }
3392
3393 assert(N->getOpcode() == ISD::SRA && "Unknown shift!");
3394 if (Amt.uge(VTBits)) {
3395 Hi = Lo = DAG.getNode(ISD::SRA, DL, NVT, InH,
3396 DAG.getShiftAmountConstant(NVTBits - 1, NVT, DL));
3397 } else if (Amt.ugt(NVTBits)) {
3398 Lo = DAG.getNode(ISD::SRA, DL, NVT, InH,
3399 DAG.getShiftAmountConstant(Amt - NVTBits, NVT, DL));
3400 Hi = DAG.getNode(ISD::SRA, DL, NVT, InH,
3401 DAG.getShiftAmountConstant(NVTBits - 1, NVT, DL));
3402 } else if (Amt == NVTBits) {
3403 Lo = InH;
3404 Hi = DAG.getNode(ISD::SRA, DL, NVT, InH,
3405 DAG.getShiftAmountConstant(NVTBits - 1, NVT, DL));
3406 } else {
3407 // Use FSHR if legal so we don't need to combine it later.
3408 if (TLI.isOperationLegal(ISD::FSHR, NVT)) {
3409 Lo = DAG.getNode(ISD::FSHR, DL, NVT, InH, InL,
3410 DAG.getShiftAmountConstant(Amt, NVT, DL));
3411 } else {
3412 Lo = DAG.getNode(
3413 ISD::OR, DL, NVT,
3414 DAG.getNode(ISD::SRL, DL, NVT, InL,
3415 DAG.getShiftAmountConstant(Amt, NVT, DL)),
3416 DAG.getNode(ISD::SHL, DL, NVT, InH,
3417 DAG.getShiftAmountConstant(-Amt + NVTBits, NVT, DL)));
3418 }
3419 Hi = DAG.getNode(ISD::SRA, DL, NVT, InH,
3420 DAG.getShiftAmountConstant(Amt, NVT, DL));
3421 }
3422}
3423
3424/// ExpandShiftWithKnownAmountBit - Try to determine whether we can simplify
3425/// this shift based on knowledge of the high bit of the shift amount. If we
3426/// can tell this, we know that it is >= 32 or < 32, without knowing the actual
3427/// shift amount.
3428bool DAGTypeLegalizer::
3429ExpandShiftWithKnownAmountBit(SDNode *N, SDValue &Lo, SDValue &Hi) {
3430 unsigned Opc = N->getOpcode();
3431 SDValue In = N->getOperand(0);
3432 SDValue Amt = N->getOperand(1);
3433 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
3434 EVT ShTy = Amt.getValueType();
3435 unsigned ShBits = ShTy.getScalarSizeInBits();
3436 unsigned NVTBits = NVT.getScalarSizeInBits();
3437 assert(isPowerOf2_32(NVTBits) &&
3438 "Expanded integer type size not a power of two!");
3439 SDLoc dl(N);
3440
3441 APInt HighBitMask = APInt::getHighBitsSet(ShBits, ShBits - Log2_32(NVTBits));
3442 KnownBits Known = DAG.computeKnownBits(Amt);
3443
3444 // If we don't know anything about the high bits, exit.
3445 if (((Known.Zero | Known.One) & HighBitMask) == 0)
3446 return false;
3447
3448 // Get the incoming operand to be shifted.
3449 SDValue InL, InH;
3450 GetExpandedInteger(In, InL, InH);
3451
3452 // If we know that any of the high bits of the shift amount are one, then we
3453 // can do this as a couple of simple shifts.
3454 if (Known.One.intersects(HighBitMask)) {
3455 // Mask out the high bit, which we know is set.
3456 Amt = DAG.getNode(ISD::AND, dl, ShTy, Amt,
3457 DAG.getConstant(~HighBitMask, dl, ShTy));
3458
3459 switch (Opc) {
3460 default: llvm_unreachable("Unknown shift");
3461 case ISD::SHL:
3462 Lo = DAG.getConstant(0, dl, NVT); // Low part is zero.
3463 Hi = DAG.getNode(ISD::SHL, dl, NVT, InL, Amt); // High part from Lo part.
3464 return true;
3465 case ISD::SRL:
3466 Hi = DAG.getConstant(0, dl, NVT); // Hi part is zero.
3467 Lo = DAG.getNode(ISD::SRL, dl, NVT, InH, Amt); // Lo part from Hi part.
3468 return true;
3469 case ISD::SRA:
3470 Hi = DAG.getNode(ISD::SRA, dl, NVT, InH, // Sign extend high part.
3471 DAG.getConstant(NVTBits - 1, dl, ShTy));
3472 Lo = DAG.getNode(ISD::SRA, dl, NVT, InH, Amt); // Lo part from Hi part.
3473 return true;
3474 }
3475 }
3476
3477 // If we know that all of the high bits of the shift amount are zero, then we
3478 // can do this as a couple of simple shifts.
3479 if (HighBitMask.isSubsetOf(Known.Zero)) {
3480 // Calculate 31-x. 31 is used instead of 32 to avoid creating an undefined
3481 // shift if x is zero. We can use XOR here because x is known to be smaller
3482 // than 32.
3483 SDValue Amt2 = DAG.getNode(ISD::XOR, dl, ShTy, Amt,
3484 DAG.getConstant(NVTBits - 1, dl, ShTy));
3485
3486 unsigned Op1, Op2;
3487 switch (Opc) {
3488 default: llvm_unreachable("Unknown shift");
3489 case ISD::SHL: Op1 = ISD::SHL; Op2 = ISD::SRL; break;
3490 case ISD::SRL:
3491 case ISD::SRA: Op1 = ISD::SRL; Op2 = ISD::SHL; break;
3492 }
3493
3494 // When shifting right the arithmetic for Lo and Hi is swapped.
3495 if (Opc != ISD::SHL)
3496 std::swap(InL, InH);
3497
3498 // Use a little trick to get the bits that move from Lo to Hi. First
3499 // shift by one bit.
3500 SDValue Sh1 = DAG.getNode(Op2, dl, NVT, InL, DAG.getConstant(1, dl, ShTy));
3501 // Then compute the remaining shift with amount-1.
3502 SDValue Sh2 = DAG.getNode(Op2, dl, NVT, Sh1, Amt2);
3503
3504 Lo = DAG.getNode(Opc, dl, NVT, InL, Amt);
3505 Hi = DAG.getNode(ISD::OR, dl, NVT, DAG.getNode(Op1, dl, NVT, InH, Amt),Sh2);
3506
3507 if (Opc != ISD::SHL)
3508 std::swap(Hi, Lo);
3509 return true;
3510 }
3511
3512 return false;
3513}
3514
3515/// ExpandShiftWithUnknownAmountBit - Fully general expansion of integer shift
3516/// of any size.
3517bool DAGTypeLegalizer::
3518ExpandShiftWithUnknownAmountBit(SDNode *N, SDValue &Lo, SDValue &Hi) {
3519 SDValue Amt = N->getOperand(1);
3520 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
3521 EVT ShTy = Amt.getValueType();
3522 unsigned NVTBits = NVT.getSizeInBits();
3523 assert(isPowerOf2_32(NVTBits) &&
3524 "Expanded integer type size not a power of two!");
3525 SDLoc dl(N);
3526
3527 // Get the incoming operand to be shifted.
3528 SDValue InL, InH;
3529 GetExpandedInteger(N->getOperand(0), InL, InH);
3530
3531 SDValue NVBitsNode = DAG.getConstant(NVTBits, dl, ShTy);
3532 SDValue AmtExcess = DAG.getNode(ISD::SUB, dl, ShTy, Amt, NVBitsNode);
3533 SDValue AmtLack = DAG.getNode(ISD::SUB, dl, ShTy, NVBitsNode, Amt);
3534 SDValue isShort = DAG.getSetCC(dl, getSetCCResultType(ShTy),
3535 Amt, NVBitsNode, ISD::SETULT);
3536 SDValue isZero = DAG.getSetCC(dl, getSetCCResultType(ShTy),
3537 Amt, DAG.getConstant(0, dl, ShTy),
3538 ISD::SETEQ);
3539
3540 SDValue LoS, HiS, LoL, HiL;
3541 switch (N->getOpcode()) {
3542 default: llvm_unreachable("Unknown shift");
3543 case ISD::SHL:
3544 // Short: ShAmt < NVTBits
3545 LoS = DAG.getNode(ISD::SHL, dl, NVT, InL, Amt);
3546 HiS = DAG.getNode(ISD::OR, dl, NVT,
3547 DAG.getNode(ISD::SHL, dl, NVT, InH, Amt),
3548 DAG.getNode(ISD::SRL, dl, NVT, InL, AmtLack));
3549
3550 // Long: ShAmt >= NVTBits
3551 LoL = DAG.getConstant(0, dl, NVT); // Lo part is zero.
3552 HiL = DAG.getNode(ISD::SHL, dl, NVT, InL, AmtExcess); // Hi from Lo part.
3553
3554 Lo = DAG.getSelect(dl, NVT, isShort, LoS, LoL);
3555 Hi = DAG.getSelect(dl, NVT, isZero, InH,
3556 DAG.getSelect(dl, NVT, isShort, HiS, HiL));
3557 return true;
3558 case ISD::SRL:
3559 // Short: ShAmt < NVTBits
3560 HiS = DAG.getNode(ISD::SRL, dl, NVT, InH, Amt);
3561 LoS = DAG.getNode(ISD::OR, dl, NVT,
3562 DAG.getNode(ISD::SRL, dl, NVT, InL, Amt),
3563 // FIXME: If Amt is zero, the following shift generates an undefined result
3564 // on some architectures.
3565 DAG.getNode(ISD::SHL, dl, NVT, InH, AmtLack));
3566
3567 // Long: ShAmt >= NVTBits
3568 HiL = DAG.getConstant(0, dl, NVT); // Hi part is zero.
3569 LoL = DAG.getNode(ISD::SRL, dl, NVT, InH, AmtExcess); // Lo from Hi part.
3570
3571 Lo = DAG.getSelect(dl, NVT, isZero, InL,
3572 DAG.getSelect(dl, NVT, isShort, LoS, LoL));
3573 Hi = DAG.getSelect(dl, NVT, isShort, HiS, HiL);
3574 return true;
3575 case ISD::SRA:
3576 // Short: ShAmt < NVTBits
3577 HiS = DAG.getNode(ISD::SRA, dl, NVT, InH, Amt);
3578 LoS = DAG.getNode(ISD::OR, dl, NVT,
3579 DAG.getNode(ISD::SRL, dl, NVT, InL, Amt),
3580 DAG.getNode(ISD::SHL, dl, NVT, InH, AmtLack));
3581
3582 // Long: ShAmt >= NVTBits
3583 HiL = DAG.getNode(ISD::SRA, dl, NVT, InH, // Sign of Hi part.
3584 DAG.getConstant(NVTBits - 1, dl, ShTy));
3585 LoL = DAG.getNode(ISD::SRA, dl, NVT, InH, AmtExcess); // Lo from Hi part.
3586
3587 Lo = DAG.getSelect(dl, NVT, isZero, InL,
3588 DAG.getSelect(dl, NVT, isShort, LoS, LoL));
3589 Hi = DAG.getSelect(dl, NVT, isShort, HiS, HiL);
3590 return true;
3591 }
3592}
3593
3594static std::pair<ISD::CondCode, ISD::NodeType> getExpandedMinMaxOps(int Op) {
3595
3596 switch (Op) {
3597 default: llvm_unreachable("invalid min/max opcode");
3598 case ISD::SMAX:
3599 return std::make_pair(ISD::SETGT, ISD::UMAX);
3600 case ISD::UMAX:
3601 return std::make_pair(ISD::SETUGT, ISD::UMAX);
3602 case ISD::SMIN:
3603 return std::make_pair(ISD::SETLT, ISD::UMIN);
3604 case ISD::UMIN:
3605 return std::make_pair(ISD::SETULT, ISD::UMIN);
3606 }
3607}
3608
3609void DAGTypeLegalizer::ExpandIntRes_SETCC(SDNode *N, SDValue &Lo, SDValue &Hi) {
3610 SDLoc DL(N);
3611
3612 SDValue LHS = N->getOperand(0);
3613 SDValue RHS = N->getOperand(1);
3614 EVT NewVT = getSetCCResultType(LHS.getValueType());
3615
3616 // Taking the same approach as ScalarizeVecRes_SETCC
3617 SDValue Res = DAG.getNode(ISD::SETCC, DL, NewVT, LHS, RHS, N->getOperand(2));
3618
3619 Res = DAG.getBoolExtOrTrunc(Res, DL, N->getValueType(0), NewVT);
3620 SplitInteger(Res, Lo, Hi);
3621}
3622
3623void DAGTypeLegalizer::ExpandIntRes_MINMAX(SDNode *N,
3624 SDValue &Lo, SDValue &Hi) {
3625 SDLoc DL(N);
3626
3627 SDValue LHS = N->getOperand(0);
3628 SDValue RHS = N->getOperand(1);
3629
3630 // If the upper halves are all sign bits, then we can perform the MINMAX on
3631 // the lower half and sign-extend the result to the upper half.
3632 unsigned NumBits = N->getValueType(0).getScalarSizeInBits();
3633 unsigned NumHalfBits = NumBits / 2;
3634 if (DAG.ComputeNumSignBits(LHS) > NumHalfBits &&
3635 DAG.ComputeNumSignBits(RHS) > NumHalfBits) {
3636 SDValue LHSL, LHSH, RHSL, RHSH;
3637 GetExpandedInteger(LHS, LHSL, LHSH);
3638 GetExpandedInteger(RHS, RHSL, RHSH);
3639 EVT NVT = LHSL.getValueType();
3640
3641 Lo = DAG.getNode(N->getOpcode(), DL, NVT, LHSL, RHSL);
3642 Hi = DAG.getNode(ISD::SRA, DL, NVT, Lo,
3643 DAG.getShiftAmountConstant(NumHalfBits - 1, NVT, DL));
3644 return;
3645 }
3646
3647 // The Lo of smin(X, -1) is LHSL if X is negative. Otherwise it's -1.
3648 // The Lo of smax(X, 0) is 0 if X is negative. Otherwise it's LHSL.
3649 if ((N->getOpcode() == ISD::SMAX && isNullConstant(RHS)) ||
3650 (N->getOpcode() == ISD::SMIN && isAllOnesConstant(RHS))) {
3651 SDValue LHSL, LHSH, RHSL, RHSH;
3652 GetExpandedInteger(LHS, LHSL, LHSH);
3653 GetExpandedInteger(RHS, RHSL, RHSH);
3654 EVT NVT = LHSL.getValueType();
3655 EVT CCT = getSetCCResultType(NVT);
3656
3657 SDValue HiNeg =
3658 DAG.getSetCC(DL, CCT, LHSH, DAG.getConstant(0, DL, NVT), ISD::SETLT);
3659 if (N->getOpcode() == ISD::SMIN) {
3660 Lo = DAG.getSelect(DL, NVT, HiNeg, LHSL, DAG.getAllOnesConstant(DL, NVT));
3661 } else {
3662 Lo = DAG.getSelect(DL, NVT, HiNeg, DAG.getConstant(0, DL, NVT), LHSL);
3663 }
3664 Hi = DAG.getNode(N->getOpcode(), DL, NVT, {LHSH, RHSH});
3665 return;
3666 }
3667
3668 const APInt *RHSVal = nullptr;
3669 if (auto *RHSConst = dyn_cast<ConstantSDNode>(RHS))
3670 RHSVal = &RHSConst->getAPIntValue();
3671
3672 // The high half of MIN/MAX is always just the the MIN/MAX of the
3673 // high halves of the operands. Expand this way if it appears profitable.
3674 if (RHSVal && (N->getOpcode() == ISD::UMIN || N->getOpcode() == ISD::UMAX) &&
3675 (RHSVal->countLeadingOnes() >= NumHalfBits ||
3676 RHSVal->countLeadingZeros() >= NumHalfBits)) {
3677 SDValue LHSL, LHSH, RHSL, RHSH;
3678 GetExpandedInteger(LHS, LHSL, LHSH);
3679 GetExpandedInteger(RHS, RHSL, RHSH);
3680 EVT NVT = LHSL.getValueType();
3681 EVT CCT = getSetCCResultType(NVT);
3682
3683 ISD::NodeType LoOpc;
3684 ISD::CondCode CondC;
3685 std::tie(CondC, LoOpc) = getExpandedMinMaxOps(N->getOpcode());
3686
3687 Hi = DAG.getNode(N->getOpcode(), DL, NVT, {LHSH, RHSH});
3688 // We need to know whether to select Lo part that corresponds to 'winning'
3689 // Hi part or if Hi parts are equal.
3690 SDValue IsHiLeft = DAG.getSetCC(DL, CCT, LHSH, RHSH, CondC);
3691 SDValue IsHiEq = DAG.getSetCC(DL, CCT, LHSH, RHSH, ISD::SETEQ);
3692
3693 // Lo part corresponding to the 'winning' Hi part
3694 SDValue LoCmp = DAG.getSelect(DL, NVT, IsHiLeft, LHSL, RHSL);
3695
3696 // Recursed Lo part if Hi parts are equal, this uses unsigned version
3697 SDValue LoMinMax = DAG.getNode(LoOpc, DL, NVT, {LHSL, RHSL});
3698
3699 Lo = DAG.getSelect(DL, NVT, IsHiEq, LoMinMax, LoCmp);
3700 return;
3701 }
3702
3703 // Expand to "a < b ? a : b" etc. Prefer ge/le if that simplifies
3704 // the compare.
3705 ISD::CondCode Pred;
3706 switch (N->getOpcode()) {
3707 default: llvm_unreachable("How did we get here?");
3708 case ISD::SMAX:
3709 if (RHSVal && RHSVal->countTrailingZeros() >= NumHalfBits)
3710 Pred = ISD::SETGE;
3711 else
3712 Pred = ISD::SETGT;
3713 break;
3714 case ISD::SMIN:
3715 if (RHSVal && RHSVal->countTrailingOnes() >= NumHalfBits)
3716 Pred = ISD::SETLE;
3717 else
3718 Pred = ISD::SETLT;
3719 break;
3720 case ISD::UMAX:
3721 if (RHSVal && RHSVal->countTrailingZeros() >= NumHalfBits)
3722 Pred = ISD::SETUGE;
3723 else
3724 Pred = ISD::SETUGT;
3725 break;
3726 case ISD::UMIN:
3727 if (RHSVal && RHSVal->countTrailingOnes() >= NumHalfBits)
3728 Pred = ISD::SETULE;
3729 else
3730 Pred = ISD::SETULT;
3731 break;
3732 }
3733 EVT VT = N->getValueType(0);
3734 EVT CCT = getSetCCResultType(VT);
3735 SDValue Cond = DAG.getSetCC(DL, CCT, LHS, RHS, Pred);
3736 SDValue Result = DAG.getSelect(DL, VT, Cond, LHS, RHS);
3737 SplitInteger(Result, Lo, Hi);
3738}
3739
3740void DAGTypeLegalizer::ExpandIntRes_CMP(SDNode *N, SDValue &Lo, SDValue &Hi) {
3741 SDValue ExpandedCMP = TLI.expandCMP(N, DAG);
3742 SplitInteger(ExpandedCMP, Lo, Hi);
3743}
3744
3745void DAGTypeLegalizer::ExpandIntRes_ADDSUB(SDNode *N,
3746 SDValue &Lo, SDValue &Hi) {
3747 SDLoc dl(N);
3748 // Expand the subcomponents.
3749 SDValue LHSL, LHSH, RHSL, RHSH;
3750 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
3751 GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
3752
3753 EVT NVT = LHSL.getValueType();
3754 SDValue LoOps[2] = { LHSL, RHSL };
3755 SDValue HiOps[3] = { LHSH, RHSH };
3756
3757 bool HasOpCarry = TLI.isOperationLegalOrCustom(
3758 N->getOpcode() == ISD::ADD ? ISD::UADDO_CARRY : ISD::USUBO_CARRY,
3759 TLI.getTypeToExpandTo(*DAG.getContext(), NVT));
3760 if (HasOpCarry) {
3761 SDVTList VTList = DAG.getVTList(NVT, getSetCCResultType(NVT));
3762 if (N->getOpcode() == ISD::ADD) {
3763 Lo = DAG.getNode(ISD::UADDO, dl, VTList, LoOps);
3764 HiOps[2] = Lo.getValue(1);
3765 Hi = DAG.computeKnownBits(HiOps[2]).isZero()
3766 ? DAG.getNode(ISD::ADD, dl, NVT, ArrayRef(HiOps, 2))
3767 : DAG.getNode(ISD::UADDO_CARRY, dl, VTList, HiOps);
3768 } else {
3769 Lo = DAG.getNode(ISD::USUBO, dl, VTList, LoOps);
3770 HiOps[2] = Lo.getValue(1);
3771 Hi = DAG.computeKnownBits(HiOps[2]).isZero()
3772 ? DAG.getNode(ISD::SUB, dl, NVT, ArrayRef(HiOps, 2))
3773 : DAG.getNode(ISD::USUBO_CARRY, dl, VTList, HiOps);
3774 }
3775 return;
3776 }
3777
3778 // Do not generate ADDC/ADDE or SUBC/SUBE if the target does not support
3779 // them. TODO: Teach operation legalization how to expand unsupported
3780 // ADDC/ADDE/SUBC/SUBE. The problem is that these operations generate
3781 // a carry of type MVT::Glue, but there doesn't seem to be any way to
3782 // generate a value of this type in the expanded code sequence.
3783 bool hasCarry =
3784 TLI.isOperationLegalOrCustom(N->getOpcode() == ISD::ADD ?
3786 TLI.getTypeToExpandTo(*DAG.getContext(), NVT));
3787
3788 if (hasCarry) {
3789 SDVTList VTList = DAG.getVTList(NVT, MVT::Glue);
3790 if (N->getOpcode() == ISD::ADD) {
3791 Lo = DAG.getNode(ISD::ADDC, dl, VTList, LoOps);
3792 HiOps[2] = Lo.getValue(1);
3793 Hi = DAG.getNode(ISD::ADDE, dl, VTList, HiOps);
3794 } else {
3795 Lo = DAG.getNode(ISD::SUBC, dl, VTList, LoOps);
3796 HiOps[2] = Lo.getValue(1);
3797 Hi = DAG.getNode(ISD::SUBE, dl, VTList, HiOps);
3798 }
3799 return;
3800 }
3801
3802 bool hasOVF =
3803 TLI.isOperationLegalOrCustom(N->getOpcode() == ISD::ADD ?
3805 TLI.getTypeToExpandTo(*DAG.getContext(), NVT));
3806 TargetLoweringBase::BooleanContent BoolType = TLI.getBooleanContents(NVT);
3807
3808 if (hasOVF) {
3809 EVT OvfVT = getSetCCResultType(NVT);
3810 SDVTList VTList = DAG.getVTList(NVT, OvfVT);
3811 int RevOpc;
3812 if (N->getOpcode() == ISD::ADD) {
3813 RevOpc = ISD::SUB;
3814 Lo = DAG.getNode(ISD::UADDO, dl, VTList, LoOps);
3815 Hi = DAG.getNode(ISD::ADD, dl, NVT, ArrayRef(HiOps, 2));
3816 } else {
3817 RevOpc = ISD::ADD;
3818 Lo = DAG.getNode(ISD::USUBO, dl, VTList, LoOps);
3819 Hi = DAG.getNode(ISD::SUB, dl, NVT, ArrayRef(HiOps, 2));
3820 }
3821 SDValue OVF = Lo.getValue(1);
3822
3823 switch (BoolType) {
3825 OVF = DAG.getNode(ISD::AND, dl, OvfVT, DAG.getConstant(1, dl, OvfVT), OVF);
3826 [[fallthrough]];
3828 OVF = DAG.getZExtOrTrunc(OVF, dl, NVT);
3829 Hi = DAG.getNode(N->getOpcode(), dl, NVT, Hi, OVF);
3830 break;
3832 OVF = DAG.getSExtOrTrunc(OVF, dl, NVT);
3833 Hi = DAG.getNode(RevOpc, dl, NVT, Hi, OVF);
3834 }
3835 return;
3836 }
3837
3838 if (N->getOpcode() == ISD::ADD) {
3839 Lo = DAG.getNode(ISD::ADD, dl, NVT, LoOps);
3840 SDValue Cmp;
3841 // Special case: X+1 has a carry out if X+1==0. This may reduce the live
3842 // range of X. We assume comparing with 0 is cheap.
3843 if (isOneConstant(LoOps[1]))
3844 Cmp = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo,
3845 DAG.getConstant(0, dl, NVT), ISD::SETEQ);
3846 else if (isAllOnesConstant(LoOps[1])) {
3847 if (isAllOnesConstant(HiOps[1]))
3848 Cmp = DAG.getSetCC(dl, getSetCCResultType(NVT), LoOps[0],
3849 DAG.getConstant(0, dl, NVT), ISD::SETEQ);
3850 else
3851 Cmp = DAG.getSetCC(dl, getSetCCResultType(NVT), LoOps[0],
3852 DAG.getConstant(0, dl, NVT), ISD::SETNE);
3853 } else
3854 Cmp = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo, LoOps[0],
3855 ISD::SETULT);
3856
3857 SDValue Carry;
3859 Carry = DAG.getZExtOrTrunc(Cmp, dl, NVT);
3860 else
3861 Carry = DAG.getSelect(dl, NVT, Cmp, DAG.getConstant(1, dl, NVT),
3862 DAG.getConstant(0, dl, NVT));
3863
3864 if (isAllOnesConstant(LoOps[1]) && isAllOnesConstant(HiOps[1])) {
3865 Hi = DAG.getNode(ISD::SUB, dl, NVT, HiOps[0], Carry);
3866 } else {
3867 Hi = DAG.getNode(ISD::ADD, dl, NVT, ArrayRef(HiOps, 2));
3868 Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, Carry);
3869 }
3870 } else {
3871 Lo = DAG.getNode(ISD::SUB, dl, NVT, LoOps);
3872 Hi = DAG.getNode(ISD::SUB, dl, NVT, ArrayRef(HiOps, 2));
3873 SDValue Cmp =
3874 DAG.getSetCC(dl, getSetCCResultType(LoOps[0].getValueType()),
3875 LoOps[0], LoOps[1], ISD::SETULT);
3876
3877 SDValue Borrow;
3879 Borrow = DAG.getZExtOrTrunc(Cmp, dl, NVT);
3880 else
3881 Borrow = DAG.getSelect(dl, NVT, Cmp, DAG.getConstant(1, dl, NVT),
3882 DAG.getConstant(0, dl, NVT));
3883
3884 Hi = DAG.getNode(ISD::SUB, dl, NVT, Hi, Borrow);
3885 }
3886}
3887
3888void DAGTypeLegalizer::ExpandIntRes_ADDSUBC(SDNode *N,
3889 SDValue &Lo, SDValue &Hi) {
3890 // Expand the subcomponents.
3891 SDValue LHSL, LHSH, RHSL, RHSH;
3892 SDLoc dl(N);
3893 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
3894 GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
3895 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), MVT::Glue);
3896 SDValue LoOps[2] = { LHSL, RHSL };
3897 SDValue HiOps[3] = { LHSH, RHSH };
3898
3899 if (N->getOpcode() == ISD::ADDC) {
3900 Lo = DAG.getNode(ISD::ADDC, dl, VTList, LoOps);
3901 HiOps[2] = Lo.getValue(1);
3902 Hi = DAG.getNode(ISD::ADDE, dl, VTList, HiOps);
3903 } else {
3904 Lo = DAG.getNode(ISD::SUBC, dl, VTList, LoOps);
3905 HiOps[2] = Lo.getValue(1);
3906 Hi = DAG.getNode(ISD::SUBE, dl, VTList, HiOps);
3907 }
3908
3909 // Legalized the flag result - switch anything that used the old flag to
3910 // use the new one.
3911 ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
3912}
3913
3914void DAGTypeLegalizer::ExpandIntRes_ADDSUBE(SDNode *N,
3915 SDValue &Lo, SDValue &Hi) {
3916 // Expand the subcomponents.
3917 SDValue LHSL, LHSH, RHSL, RHSH;
3918 SDLoc dl(N);
3919 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
3920 GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
3921 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), MVT::Glue);
3922 SDValue LoOps[3] = { LHSL, RHSL, N->getOperand(2) };
3923 SDValue HiOps[3] = { LHSH, RHSH };
3924
3925 Lo = DAG.getNode(N->getOpcode(), dl, VTList, LoOps);
3926 HiOps[2] = Lo.getValue(1);
3927 Hi = DAG.getNode(N->getOpcode(), dl, VTList, HiOps);
3928
3929 // Legalized the flag result - switch anything that used the old flag to
3930 // use the new one.
3931 ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
3932}
3933
3934void DAGTypeLegalizer::ExpandIntRes_UADDSUBO(SDNode *N,
3935 SDValue &Lo, SDValue &Hi) {
3936 SDValue LHS = N->getOperand(0);
3937 SDValue RHS = N->getOperand(1);
3938 SDLoc dl(N);
3939
3940 SDValue Ovf;
3941
3942 unsigned CarryOp, NoCarryOp;
3944 switch(N->getOpcode()) {
3945 case ISD::UADDO:
3946 CarryOp = ISD::UADDO_CARRY;
3947 NoCarryOp = ISD::ADD;
3948 Cond = ISD::SETULT;
3949 break;
3950 case ISD::USUBO:
3951 CarryOp = ISD::USUBO_CARRY;
3952 NoCarryOp = ISD::SUB;
3953 Cond = ISD::SETUGT;
3954 break;
3955 default:
3956 llvm_unreachable("Node has unexpected Opcode");
3957 }
3958
3959 bool HasCarryOp = TLI.isOperationLegalOrCustom(
3960 CarryOp, TLI.getTypeToExpandTo(*DAG.getContext(), LHS.getValueType()));
3961
3962 if (HasCarryOp) {
3963 // Expand the subcomponents.
3964 SDValue LHSL, LHSH, RHSL, RHSH;
3965 GetExpandedInteger(LHS, LHSL, LHSH);
3966 GetExpandedInteger(RHS, RHSL, RHSH);
3967 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), N->getValueType(1));
3968 SDValue LoOps[2] = { LHSL, RHSL };
3969 SDValue HiOps[3] = { LHSH, RHSH };
3970
3971 Lo = DAG.getNode(N->getOpcode(), dl, VTList, LoOps);
3972 HiOps[2] = Lo.getValue(1);
3973 Hi = DAG.getNode(CarryOp, dl, VTList, HiOps);
3974
3975 Ovf = Hi.getValue(1);
3976 } else {
3977 // Expand the result by simply replacing it with the equivalent
3978 // non-overflow-checking operation.
3979 SDValue Sum = DAG.getNode(NoCarryOp, dl, LHS.getValueType(), LHS, RHS);
3980 SplitInteger(Sum, Lo, Hi);
3981
3982 if (N->getOpcode() == ISD::UADDO && isOneConstant(RHS)) {
3983 // Special case: uaddo X, 1 overflowed if X+1 == 0. We can detect this
3984 // with (Lo | Hi) == 0.
3985 SDValue Or = DAG.getNode(ISD::OR, dl, Lo.getValueType(), Lo, Hi);
3986 Ovf = DAG.getSetCC(dl, N->getValueType(1), Or,
3987 DAG.getConstant(0, dl, Lo.getValueType()), ISD::SETEQ);
3988 } else if (N->getOpcode() == ISD::UADDO && isAllOnesConstant(RHS)) {
3989 // Special case: uaddo X, -1 overflows if X == 0.
3990 Ovf =
3991 DAG.getSetCC(dl, N->getValueType(1), LHS,
3992 DAG.getConstant(0, dl, LHS.getValueType()), ISD::SETNE);
3993 } else {
3994 // Calculate the overflow: addition overflows iff a + b < a, and
3995 // subtraction overflows iff a - b > a.
3996 Ovf = DAG.getSetCC(dl, N->getValueType(1), Sum, LHS, Cond);
3997 }
3998 }
3999
4000 // Legalized the flag result - switch anything that used the old flag to
4001 // use the new one.
4002 ReplaceValueWith(SDValue(N, 1), Ovf);
4003}
4004
4005void DAGTypeLegalizer::ExpandIntRes_UADDSUBO_CARRY(SDNode *N, SDValue &Lo,
4006 SDValue &Hi) {
4007 // Expand the subcomponents.
4008 SDValue LHSL, LHSH, RHSL, RHSH;
4009 SDLoc dl(N);
4010 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
4011 GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
4012 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), N->getValueType(1));
4013 SDValue LoOps[3] = { LHSL, RHSL, N->getOperand(2) };
4014 SDValue HiOps[3] = { LHSH, RHSH, SDValue() };
4015
4016 Lo = DAG.getNode(N->getOpcode(), dl, VTList, LoOps);
4017 HiOps[2] = Lo.getValue(1);
4018 Hi = DAG.getNode(N->getOpcode(), dl, VTList, HiOps);
4019
4020 // Legalized the flag result - switch anything that used the old flag to
4021 // use the new one.
4022 ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
4023}
4024
4025void DAGTypeLegalizer::ExpandIntRes_SADDSUBO_CARRY(SDNode *N,
4026 SDValue &Lo, SDValue &Hi) {
4027 // Expand the subcomponents.
4028 SDValue LHSL, LHSH, RHSL, RHSH;
4029 SDLoc dl(N);
4030 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
4031 GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
4032 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), N->getValueType(1));
4033
4034 // We need to use an unsigned carry op for the lo part.
4035 unsigned CarryOp =
4037 Lo = DAG.getNode(CarryOp, dl, VTList, { LHSL, RHSL, N->getOperand(2) });
4038 Hi = DAG.getNode(N->getOpcode(), dl, VTList, { LHSH, RHSH, Lo.getValue(1) });
4039
4040 // Legalized the flag result - switch anything that used the old flag to
4041 // use the new one.
4042 ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
4043}
4044
4045void DAGTypeLegalizer::ExpandIntRes_ANY_EXTEND(SDNode *N,
4046 SDValue &Lo, SDValue &Hi) {
4047 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
4048 SDLoc dl(N);
4049 SDValue Op = N->getOperand(0);
4050 if (Op.getValueType().bitsLE(NVT)) {
4051 // The low part is any extension of the input (which degenerates to a copy).
4052 Lo = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Op);
4053 Hi = DAG.getUNDEF(NVT); // The high part is undefined.
4054 } else {
4055 // For example, extension of an i48 to an i64. The operand type necessarily
4056 // promotes to the result type, so will end up being expanded too.
4057 assert(getTypeAction(Op.getValueType()) ==
4059 "Only know how to promote this result!");
4060 SDValue Res = GetPromotedInteger(Op);
4061 assert(Res.getValueType() == N->getValueType(0) &&
4062 "Operand over promoted?");
4063 // Split the promoted operand. This will simplify when it is expanded.
4064 SplitInteger(Res, Lo, Hi);
4065 }
4066}
4067
4068void DAGTypeLegalizer::ExpandIntRes_AssertSext(SDNode *N,
4069 SDValue &Lo, SDValue &Hi) {
4070 SDLoc dl(N);
4071 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4072 EVT NVT = Lo.getValueType();
4073 EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
4074 unsigned NVTBits = NVT.getSizeInBits();
4075 unsigned EVTBits = EVT.getSizeInBits();
4076
4077 if (NVTBits < EVTBits) {
4078 Hi = DAG.getNode(ISD::AssertSext, dl, NVT, Hi,
4079 DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
4080 EVTBits - NVTBits)));
4081 } else {
4082 Lo = DAG.getNode(ISD::AssertSext, dl, NVT, Lo, DAG.getValueType(EVT));
4083 // The high part replicates the sign bit of Lo, make it explicit.
4084 Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
4085 DAG.getShiftAmountConstant(NVTBits - 1, NVT, dl));
4086 }
4087}
4088
4089void DAGTypeLegalizer::ExpandIntRes_AssertZext(SDNode *N,
4090 SDValue &Lo, SDValue &Hi) {
4091 SDLoc dl(N);
4092 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4093 EVT NVT = Lo.getValueType();
4094 EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
4095 unsigned NVTBits = NVT.getSizeInBits();
4096 unsigned EVTBits = EVT.getSizeInBits();
4097
4098 if (NVTBits < EVTBits) {
4099 Hi = DAG.getNode(ISD::AssertZext, dl, NVT, Hi,
4100 DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
4101 EVTBits - NVTBits)));
4102 } else {
4103 Lo = DAG.getNode(ISD::AssertZext, dl, NVT, Lo, DAG.getValueType(EVT));
4104 // The high part must be zero, make it explicit.
4105 Hi = DAG.getConstant(0, dl, NVT);
4106 }
4107}
4108
4109void DAGTypeLegalizer::ExpandIntRes_BITREVERSE(SDNode *N,
4110 SDValue &Lo, SDValue &Hi) {
4111 SDLoc dl(N);
4112 GetExpandedInteger(N->getOperand(0), Hi, Lo); // Note swapped operands.
4113 Lo = DAG.getNode(ISD::BITREVERSE, dl, Lo.getValueType(), Lo);
4114 Hi = DAG.getNode(ISD::BITREVERSE, dl, Hi.getValueType(), Hi);
4115}
4116
4117void DAGTypeLegalizer::ExpandIntRes_BSWAP(SDNode *N,
4118 SDValue &Lo, SDValue &Hi) {
4119 SDLoc dl(N);
4120 GetExpandedInteger(N->getOperand(0), Hi, Lo); // Note swapped operands.
4121 Lo = DAG.getNode(ISD::BSWAP, dl, Lo.getValueType(), Lo);
4122 Hi = DAG.getNode(ISD::BSWAP, dl, Hi.getValueType(), Hi);
4123}
4124
4125void DAGTypeLegalizer::ExpandIntRes_PARITY(SDNode *N, SDValue &Lo,
4126 SDValue &Hi) {
4127 SDLoc dl(N);
4128 // parity(HiLo) -> parity(Lo^Hi)
4129 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4130 EVT NVT = Lo.getValueType();
4131 Lo =
4132 DAG.getNode(ISD::PARITY, dl, NVT, DAG.getNode(ISD::XOR, dl, NVT, Lo, Hi));
4133 Hi = DAG.getConstant(0, dl, NVT);
4134}
4135
4136void DAGTypeLegalizer::ExpandIntRes_Constant(SDNode *N,
4137 SDValue &Lo, SDValue &Hi) {
4138 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
4139 unsigned NBitWidth = NVT.getSizeInBits();
4141 const APInt &Cst = Constant->getAPIntValue();
4142 bool IsTarget = Constant->isTargetOpcode();
4143 bool IsOpaque = Constant->isOpaque();
4144 SDLoc dl(N);
4145 Lo = DAG.getConstant(Cst.trunc(NBitWidth), dl, NVT, IsTarget, IsOpaque);
4146 Hi = DAG.getConstant(Cst.lshr(NBitWidth).trunc(NBitWidth), dl, NVT, IsTarget,
4147 IsOpaque);
4148}
4149
4150void DAGTypeLegalizer::ExpandIntRes_ABS(SDNode *N, SDValue &Lo, SDValue &Hi) {
4151 SDLoc dl(N);
4152
4153 SDValue N0 = N->getOperand(0);
4154 GetExpandedInteger(N0, Lo, Hi);
4155 EVT NVT = Lo.getValueType();
4156
4157 // If the upper half is all sign bits, then we can perform the ABS on the
4158 // lower half and zero-extend. We could use ISD::ABS_MIN_POISON here if
4159 // DAG.ComputeNumSignBits(N0) is larger than NVT.getScalarSizeInBits() + 1.
4160 unsigned NumSignBits = DAG.ComputeNumSignBits(N0);
4161 if (NumSignBits > NVT.getScalarSizeInBits()) {
4162 unsigned AbsOpc = NumSignBits > NVT.getScalarSizeInBits() + 1
4164 : ISD::ABS;
4165 Lo = DAG.getNode(AbsOpc, dl, NVT, Lo);
4166 Hi = DAG.getConstant(0, dl, NVT);
4167 return;
4168 }
4169
4170 // If we have USUBO_CARRY, use the expanded form of the sra+xor+sub sequence
4171 // we use in LegalizeDAG. The SUB part of the expansion is based on
4172 // ExpandIntRes_ADDSUB which also uses USUBO_CARRY/USUBO after checking that
4173 // USUBO_CARRY is LegalOrCustom. Each of the pieces here can be further
4174 // expanded if needed. Shift expansion has a special case for filling with
4175 // sign bits so that we will only end up with one SRA.
4176 bool HasSubCarry = TLI.isOperationLegalOrCustom(
4177 ISD::USUBO_CARRY, TLI.getTypeToExpandTo(*DAG.getContext(), NVT));
4178 if (HasSubCarry) {
4179 SDValue Sign = DAG.getNode(
4180 ISD::SRA, dl, NVT, Hi,
4181 DAG.getShiftAmountConstant(NVT.getSizeInBits() - 1, NVT, dl));
4182 SDVTList VTList = DAG.getVTList(NVT, getSetCCResultType(NVT));
4183 Lo = DAG.getNode(ISD::XOR, dl, NVT, Lo, Sign);
4184 Hi = DAG.getNode(ISD::XOR, dl, NVT, Hi, Sign);
4185 Lo = DAG.getNode(ISD::USUBO, dl, VTList, Lo, Sign);
4186 Hi = DAG.getNode(ISD::USUBO_CARRY, dl, VTList, Hi, Sign, Lo.getValue(1));
4187 return;
4188 }
4189
4190 // abs(HiLo) -> (Hi < 0 ? -HiLo : HiLo)
4191 EVT VT = N->getValueType(0);
4192 SDValue Neg = DAG.getNode(ISD::SUB, dl, VT,
4193 DAG.getConstant(0, dl, VT), N0);
4194 SDValue NegLo, NegHi;
4195 SplitInteger(Neg, NegLo, NegHi);
4196
4197 SDValue HiIsNeg = DAG.getSetCC(dl, getSetCCResultType(NVT), Hi,
4198 DAG.getConstant(0, dl, NVT), ISD::SETLT);
4199 Lo = DAG.getSelect(dl, NVT, HiIsNeg, NegLo, Lo);
4200 Hi = DAG.getSelect(dl, NVT, HiIsNeg, NegHi, Hi);
4201}
4202
4203void DAGTypeLegalizer::ExpandIntRes_CTLZ(SDNode *N,
4204 SDValue &Lo, SDValue &Hi) {
4205 SDLoc dl(N);
4206 // ctlz (HiLo) -> Hi != 0 ? ctlz(Hi) : (ctlz(Lo)+32)
4207 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4208 EVT NVT = Lo.getValueType();
4209
4210 SDValue HiNotZero = DAG.getSetCC(dl, getSetCCResultType(NVT), Hi,
4211 DAG.getConstant(0, dl, NVT), ISD::SETNE);
4212
4213 SDValue LoLZ = DAG.getNode(N->getOpcode(), dl, NVT, Lo);
4214 SDValue HiLZ = DAG.getNode(ISD::CTLZ_ZERO_POISON, dl, NVT, Hi);
4215
4216 Lo = DAG.getSelect(dl, NVT, HiNotZero, HiLZ,
4217 DAG.getNode(ISD::ADD, dl, NVT, LoLZ,
4218 DAG.getConstant(NVT.getSizeInBits(), dl,
4219 NVT)));
4220 Hi = DAG.getConstant(0, dl, NVT);
4221}
4222
4223void DAGTypeLegalizer::ExpandIntRes_CTLS(SDNode *N, SDValue &Lo, SDValue &Hi) {
4224 SDLoc dl(N);
4225 // ctls(HiLo) -> if (IsAllSignBits = (ctls(Hi) == BW-1)) then
4226 // BW-1 + clz(IsNegative = (Hi < 0) ? ~Lo : Lo)
4227 // else ctls(Hi)
4228 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4229 EVT NVT = Lo.getValueType();
4230 unsigned NVTBits = NVT.getScalarSizeInBits();
4231
4232 SDValue Constant0 = DAG.getConstant(0, dl, NVT);
4233 SDValue ConstantBWM1 = DAG.getConstant(NVTBits - 1, dl, NVT);
4234
4235 SDValue HiCTLS = DAG.getNode(ISD::CTLS, dl, NVT, Hi);
4236 SDValue IsAllSignBits = DAG.getSetCC(dl, getSetCCResultType(NVT), HiCTLS,
4237 ConstantBWM1, ISD::SETEQ);
4238 SDValue IsNegative =
4239 DAG.getSetCC(dl, getSetCCResultType(NVT), Hi, Constant0, ISD::SETLT);
4240 SDValue AdjustedLo =
4241 DAG.getSelect(dl, NVT, IsNegative, DAG.getNOT(dl, Lo, NVT), Lo);
4242 SDValue LoCLZ = DAG.getNode(ISD::CTLZ, dl, NVT, AdjustedLo);
4243 Lo = DAG.getSelect(dl, NVT, IsAllSignBits,
4244 DAG.getNode(ISD::ADD, dl, NVT, LoCLZ, ConstantBWM1),
4245 HiCTLS);
4246 Hi = DAG.getConstant(0, dl, NVT);
4247}
4248
4249void DAGTypeLegalizer::ExpandIntRes_ABD(SDNode *N, SDValue &Lo, SDValue &Hi) {
4250 SDValue Result = TLI.expandABD(N, DAG);
4251 SplitInteger(Result, Lo, Hi);
4252}
4253
4254void DAGTypeLegalizer::ExpandIntRes_CTPOP(SDNode *N, SDValue &Lo, SDValue &Hi) {
4255 SDValue Op = N->getOperand(0);
4256 EVT VT = N->getValueType(0);
4257 SDLoc DL(N);
4258
4259 if (TLI.getOperationAction(ISD::CTPOP, VT) == TargetLoweringBase::LibCall) {
4260 RTLIB::Libcall LC = RTLIB::getCTPOP(VT);
4261 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
4262 "LibCall explicitly requested, but not available");
4263
4264 if (RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC)) {
4265 TargetLowering::MakeLibCallOptions CallOptions;
4266 EVT IntVT =
4267 EVT::getIntegerVT(*DAG.getContext(), DAG.getLibInfo().getIntSize());
4268 SDValue Res =
4269 TLI.makeLibCall(DAG, LCImpl, IntVT, Op, CallOptions, DL).first;
4270 SplitInteger(DAG.getSExtOrTrunc(Res, DL, VT), Lo, Hi);
4271 return;
4272 }
4273
4274 // If the function is not available, fall back on the expansion.
4275 }
4276
4277 // ctpop(HiLo) -> ctpop(Hi)+ctpop(Lo)
4278 GetExpandedInteger(Op, Lo, Hi);
4279 EVT NVT = Lo.getValueType();
4280 Lo = DAG.getNode(ISD::ADD, DL, NVT, DAG.getNode(ISD::CTPOP, DL, NVT, Lo),
4281 DAG.getNode(ISD::CTPOP, DL, NVT, Hi));
4282 Hi = DAG.getConstant(0, DL, NVT);
4283}
4284
4285void DAGTypeLegalizer::ExpandIntRes_CTTZ(SDNode *N,
4286 SDValue &Lo, SDValue &Hi) {
4287 SDLoc dl(N);
4288 // cttz (HiLo) -> Lo != 0 ? cttz(Lo) : (cttz(Hi)+32)
4289 GetExpandedInteger(N->getOperand(0), Lo, Hi);
4290 EVT NVT = Lo.getValueType();
4291
4292 SDValue LoNotZero = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo,
4293 DAG.getConstant(0, dl, NVT), ISD::SETNE);
4294
4295 SDValue LoLZ = DAG.getNode(ISD::CTTZ_ZERO_POISON, dl, NVT, Lo);
4296 SDValue HiLZ = DAG.getNode(N->getOpcode(), dl, NVT, Hi);
4297
4298 Lo = DAG.getSelect(dl, NVT, LoNotZero, LoLZ,
4299 DAG.getNode(ISD::ADD, dl, NVT, HiLZ,
4300 DAG.getConstant(NVT.getSizeInBits(), dl,
4301 NVT)));
4302 Hi = DAG.getConstant(0, dl, NVT);
4303}
4304
4305void DAGTypeLegalizer::ExpandIntRes_GET_ROUNDING(SDNode *N, SDValue &Lo,
4306 SDValue &Hi) {
4307 SDLoc dl(N);
4308 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
4309 unsigned NBitWidth = NVT.getSizeInBits();
4310
4311 Lo = DAG.getNode(ISD::GET_ROUNDING, dl, {NVT, MVT::Other}, N->getOperand(0));
4312 SDValue Chain = Lo.getValue(1);
4313 // The high part is the sign of Lo, as -1 is a valid value for GET_ROUNDING
4314 Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
4315 DAG.getShiftAmountConstant(NBitWidth - 1, NVT, dl));
4316
4317 // Legalize the chain result - switch anything that used the old chain to
4318 // use the new one.
4319 ReplaceValueWith(SDValue(N, 1), Chain);
4320}
4321
4322// Helper for producing an FP_EXTEND/STRICT_FP_EXTEND of Op.
4323static SDValue fpExtendHelper(SDValue Op, SDValue &Chain, bool IsStrict, EVT VT,
4324 SDLoc DL, SelectionDAG &DAG) {
4325 if (IsStrict) {
4326 Op = DAG.getNode(ISD::STRICT_FP_EXTEND, DL, {VT, MVT::Other}, {Chain, Op});
4327 Chain = Op.getValue(1);
4328 return Op;
4329 }
4330 return DAG.getNode(ISD::FP_EXTEND, DL, VT, Op);
4331}
4332
4333void DAGTypeLegalizer::ExpandIntRes_FP_TO_XINT(SDNode *N, SDValue &Lo,
4334 SDValue &Hi) {
4335 SDLoc dl(N);
4336 EVT VT = N->getValueType(0);
4337
4338 bool IsSigned = N->getOpcode() == ISD::FP_TO_SINT ||
4339 N->getOpcode() == ISD::STRICT_FP_TO_SINT;
4340 bool IsStrict = N->isStrictFPOpcode();
4341 SDValue Chain = IsStrict ? N->getOperand(0) : SDValue();
4342 SDValue Op = N->getOperand(IsStrict ? 1 : 0);
4343
4344 // If the input is bf16 or needs to be soft promoted, extend to f32.
4345 if (getTypeAction(Op.getValueType()) == TargetLowering::TypeSoftPromoteHalf ||
4346 Op.getValueType() == MVT::bf16) {
4347 Op = fpExtendHelper(Op, Chain, IsStrict, MVT::f32, dl, DAG);
4348 }
4349
4350 // NOTE: We need a variable that lives across makeLibCall so
4351 // CallOptions.setTypeListBeforeSoften can save a reference to it.
4352 EVT OpVT = Op.getValueType();
4353
4354 RTLIB::Libcall LC =
4355 IsSigned ? RTLIB::getFPTOSINT(OpVT, VT) : RTLIB::getFPTOUINT(OpVT, VT);
4356 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected fp-to-xint conversion!");
4357 TargetLowering::MakeLibCallOptions CallOptions;
4358 if (getTypeAction(Op.getValueType()) == TargetLowering::TypeSoftenFloat)
4359 CallOptions.setTypeListBeforeSoften(OpVT, VT);
4360 else
4361 CallOptions.setIsSigned(true); // FIXME: Is this needed?
4362 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(DAG, LC, VT, Op,
4363 CallOptions, dl, Chain);
4364 SplitInteger(Tmp.first, Lo, Hi);
4365
4366 if (IsStrict)
4367 ReplaceValueWith(SDValue(N, 1), Tmp.second);
4368}
4369
4370void DAGTypeLegalizer::ExpandIntRes_FP_TO_XINT_SAT(SDNode *N, SDValue &Lo,
4371 SDValue &Hi) {
4372 SDValue Res = TLI.expandFP_TO_INT_SAT(N, DAG);
4373 SplitInteger(Res, Lo, Hi);
4374}
4375
4376void DAGTypeLegalizer::ExpandIntRes_XROUND_XRINT(SDNode *N, SDValue &Lo,
4377 SDValue &Hi) {
4378 SDLoc dl(N);
4379 bool IsStrict = N->isStrictFPOpcode();
4380 SDValue Op = N->getOperand(IsStrict ? 1 : 0);
4381 SDValue Chain = IsStrict ? N->getOperand(0) : SDValue();
4382
4383 EVT VT = Op.getValueType();
4384
4385 if (VT == MVT::f16) {
4386 // Extend to f32.
4387 VT = MVT::f32;
4388 Op = fpExtendHelper(Op, Chain, IsStrict, VT, dl, DAG);
4389 }
4390
4391 RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
4392 if (N->getOpcode() == ISD::LROUND ||
4393 N->getOpcode() == ISD::STRICT_LROUND) {
4394 LC = RTLIB::getLROUND(VT);
4395 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected lround input type!");
4396 } else if (N->getOpcode() == ISD::LRINT ||
4397 N->getOpcode() == ISD::STRICT_LRINT) {
4398 LC = RTLIB::getLRINT(VT);
4399 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected lrint input type!");
4400 } else if (N->getOpcode() == ISD::LLROUND ||
4401 N->getOpcode() == ISD::STRICT_LLROUND) {
4402 LC = RTLIB::getLLROUND(VT);
4403 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected llround input type!");
4404 } else if (N->getOpcode() == ISD::LLRINT ||
4405 N->getOpcode() == ISD::STRICT_LLRINT) {
4406 LC = RTLIB::getLLRINT(VT);
4407 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected llrint input type!");
4408 } else
4409 llvm_unreachable("Unexpected opcode!");
4410
4411 EVT RetVT = N->getValueType(0);
4412
4413 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
4414 if (LCImpl == RTLIB::Unsupported) {
4415 DAG.getContext()->emitError(Twine("no libcall available for ") +
4416 N->getOperationName(&DAG));
4417 SDValue Poison = DAG.getPOISON(N->getValueType(0));
4418 SplitInteger(Poison, Lo, Hi);
4419 if (N->isStrictFPOpcode())
4420 ReplaceValueWith(SDValue(N, 1), N->getOperand(0));
4421 return;
4422 }
4423
4424 TargetLowering::MakeLibCallOptions CallOptions;
4425 CallOptions.setIsSigned(true);
4426 std::pair<SDValue, SDValue> Tmp =
4427 TLI.makeLibCall(DAG, LCImpl, RetVT, Op, CallOptions, dl, Chain);
4428 SplitInteger(Tmp.first, Lo, Hi);
4429
4430 if (N->isStrictFPOpcode())
4431 ReplaceValueWith(SDValue(N, 1), Tmp.second);
4432}
4433
4434void DAGTypeLegalizer::ExpandIntRes_LOAD(LoadSDNode *N,
4435 SDValue &Lo, SDValue &Hi) {
4436 assert(!N->isAtomic() && "Should have been a ATOMIC_LOAD?");
4437
4438 if (ISD::isNormalLoad(N)) {
4439 ExpandRes_NormalLoad(N, Lo, Hi);
4440 return;
4441 }
4442
4443 assert(ISD::isUNINDEXEDLoad(N) && "Indexed load during type legalization!");
4444
4445 EVT VT = N->getValueType(0);
4446 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
4447 SDValue Ch = N->getChain();
4448 SDValue Ptr = N->getBasePtr();
4449 ISD::LoadExtType ExtType = N->getExtensionType();
4450 MachineMemOperand::Flags MMOFlags = N->getMemOperand()->getFlags();
4451 MMOMetadata Metadata = N->getMMOMetadataForSubAccess();
4452 SDLoc dl(N);
4453
4454 assert(NVT.isByteSized() && "Expanded type not byte sized!");
4455
4456 if (N->getMemoryVT().bitsLE(NVT)) {
4457 EVT MemVT = N->getMemoryVT();
4458
4459 Lo = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr, N->getPointerInfo(), MemVT,
4460 N->getBaseAlign(), MMOFlags, Metadata);
4461
4462 // Remember the chain.
4463 Ch = Lo.getValue(1);
4464
4465 if (ExtType == ISD::SEXTLOAD) {
4466 // The high part is obtained by SRA'ing all but one of the bits of the
4467 // lo part.
4468 unsigned LoSize = Lo.getValueSizeInBits();
4469 Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
4470 DAG.getShiftAmountConstant(LoSize - 1, NVT, dl));
4471 } else if (ExtType == ISD::ZEXTLOAD) {
4472 // The high part is just a zero.
4473 Hi = DAG.getConstant(0, dl, NVT);
4474 } else {
4475 assert(ExtType == ISD::EXTLOAD && "Unknown extload!");
4476 // The high part is undefined.
4477 Hi = DAG.getUNDEF(NVT);
4478 }
4479 } else if (DAG.getDataLayout().isLittleEndian()) {
4480 // Little-endian - low bits are at low addresses.
4481 Lo = DAG.getLoad(NVT, dl, Ch, Ptr, N->getPointerInfo(), N->getBaseAlign(),
4482 MMOFlags, Metadata);
4483
4484 unsigned ExcessBits =
4485 N->getMemoryVT().getSizeInBits() - NVT.getSizeInBits();
4486 EVT NEVT = EVT::getIntegerVT(*DAG.getContext(), ExcessBits);
4487
4488 // Increment the pointer to the other half.
4489 unsigned IncrementSize = NVT.getSizeInBits()/8;
4490 Ptr = DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(IncrementSize), dl);
4491 Hi = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr,
4492 N->getPointerInfo().getWithOffset(IncrementSize), NEVT,
4493 N->getBaseAlign(), MMOFlags, Metadata);
4494
4495 // Build a factor node to remember that this load is independent of the
4496 // other one.
4497 Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
4498 Hi.getValue(1));
4499 } else {
4500 // Big-endian - high bits are at low addresses. Favor aligned loads at
4501 // the cost of some bit-fiddling.
4502 EVT MemVT = N->getMemoryVT();
4503 unsigned EBytes = MemVT.getStoreSize();
4504 unsigned IncrementSize = NVT.getSizeInBits()/8;
4505 unsigned ExcessBits = (EBytes - IncrementSize)*8;
4506
4507 // Load both the high bits and maybe some of the low bits.
4508 Hi = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr, N->getPointerInfo(),
4509 EVT::getIntegerVT(*DAG.getContext(),
4510 MemVT.getSizeInBits() - ExcessBits),
4511 N->getBaseAlign(), MMOFlags, Metadata);
4512
4513 // Increment the pointer to the other half.
4514 Ptr = DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(IncrementSize), dl);
4515 // Load the rest of the low bits.
4516 Lo = DAG.getExtLoad(ISD::ZEXTLOAD, dl, NVT, Ch, Ptr,
4517 N->getPointerInfo().getWithOffset(IncrementSize),
4518 EVT::getIntegerVT(*DAG.getContext(), ExcessBits),
4519 N->getBaseAlign(), MMOFlags, Metadata);
4520
4521 // Build a factor node to remember that this load is independent of the
4522 // other one.
4523 Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
4524 Hi.getValue(1));
4525
4526 if (ExcessBits < NVT.getSizeInBits()) {
4527 // Transfer low bits from the bottom of Hi to the top of Lo.
4528 Lo = DAG.getNode(
4529 ISD::OR, dl, NVT, Lo,
4530 DAG.getNode(ISD::SHL, dl, NVT, Hi,
4531 DAG.getShiftAmountConstant(ExcessBits, NVT, dl)));
4532 // Move high bits to the right position in Hi.
4533 Hi = DAG.getNode(ExtType == ISD::SEXTLOAD ? ISD::SRA : ISD::SRL, dl, NVT,
4534 Hi,
4535 DAG.getShiftAmountConstant(
4536 NVT.getSizeInBits() - ExcessBits, NVT, dl));
4537 }
4538 }
4539
4540 // Legalize the chain result - switch anything that used the old chain to
4541 // use the new one.
4542 ReplaceValueWith(SDValue(N, 1), Ch);
4543}
4544
4545void DAGTypeLegalizer::ExpandIntRes_Logical(SDNode *N,
4546 SDValue &Lo, SDValue &Hi) {
4547 SDLoc dl(N);
4548 SDValue LL, LH, RL, RH;
4549 GetExpandedInteger(N->getOperand(0), LL, LH);
4550 GetExpandedInteger(N->getOperand(1), RL, RH);
4551
4552 SDNodeFlags Flags;
4553 if (N->getOpcode() == ISD::OR)
4554 Flags.setDisjoint(N->getFlags().hasDisjoint());
4555
4556 Lo = DAG.getNode(N->getOpcode(), dl, LL.getValueType(), LL, RL, Flags);
4557 Hi = DAG.getNode(N->getOpcode(), dl, LL.getValueType(), LH, RH, Flags);
4558}
4559
4560void DAGTypeLegalizer::ExpandIntRes_MUL(SDNode *N,
4561 SDValue &Lo, SDValue &Hi) {
4562 EVT VT = N->getValueType(0);
4563 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
4564 SDLoc dl(N);
4565
4566 SDValue LL, LH, RL, RH;
4567 GetExpandedInteger(N->getOperand(0), LL, LH);
4568 GetExpandedInteger(N->getOperand(1), RL, RH);
4569
4570 if (TLI.expandMUL(N, Lo, Hi, NVT, DAG,
4572 LL, LH, RL, RH))
4573 return;
4574
4575 // If nothing else, we can make a libcall.
4576 RTLIB::Libcall LC = RTLIB::getMUL(VT);
4577 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
4578 if (LCImpl == RTLIB::Unsupported) {
4579 // Perform a wide multiplication where the wide type is the original VT and
4580 // the 4 parts are the split arguments.
4581 TLI.forceExpandMultiply(DAG, dl, /*Signed=*/false, Lo, Hi, LL, RL, LH, RH);
4582 return;
4583 }
4584
4585 // Note that we don't need to do a wide MUL here since we don't care about the
4586 // upper half of the result if it exceeds VT.
4587 SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
4588 TargetLowering::MakeLibCallOptions CallOptions;
4589 CallOptions.setIsSigned(true);
4590 SplitInteger(TLI.makeLibCall(DAG, LCImpl, VT, Ops, CallOptions, dl).first, Lo,
4591 Hi);
4592}
4593
4594void DAGTypeLegalizer::ExpandIntRes_READCOUNTER(SDNode *N, SDValue &Lo,
4595 SDValue &Hi) {
4596 SDLoc DL(N);
4597 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
4598 SDVTList VTs = DAG.getVTList(NVT, NVT, MVT::Other);
4599 SDValue R = DAG.getNode(N->getOpcode(), DL, VTs, N->getOperand(0));
4600 Lo = R.getValue(0);
4601 Hi = R.getValue(1);
4602 ReplaceValueWith(SDValue(N, 1), R.getValue(2));
4603}
4604
4605void DAGTypeLegalizer::ExpandIntRes_AVG(SDNode *N, SDValue &Lo, SDValue &Hi) {
4606 SDValue Result = TLI.expandAVG(N, DAG);
4607 SplitInteger(Result, Lo, Hi);
4608}
4609
4610void DAGTypeLegalizer::ExpandIntRes_ADDSUBSAT(SDNode *N, SDValue &Lo,
4611 SDValue &Hi) {
4612 SDValue Result = TLI.expandAddSubSat(N, DAG);
4613 SplitInteger(Result, Lo, Hi);
4614}
4615
4616void DAGTypeLegalizer::ExpandIntRes_SHLSAT(SDNode *N, SDValue &Lo,
4617 SDValue &Hi) {
4618 SDValue Result = TLI.expandShlSat(N, DAG);
4619 SplitInteger(Result, Lo, Hi);
4620}
4621
4622/// This performs an expansion of the integer result for a fixed point
4623/// multiplication. The default expansion performs rounding down towards
4624/// negative infinity, though targets that do care about rounding should specify
4625/// a target hook for rounding and provide their own expansion or lowering of
4626/// fixed point multiplication to be consistent with rounding.
4627void DAGTypeLegalizer::ExpandIntRes_MULFIX(SDNode *N, SDValue &Lo,
4628 SDValue &Hi) {
4629 SDLoc dl(N);
4630 EVT VT = N->getValueType(0);
4631 unsigned VTSize = VT.getScalarSizeInBits();
4632 SDValue LHS = N->getOperand(0);
4633 SDValue RHS = N->getOperand(1);
4634 uint64_t Scale = N->getConstantOperandVal(2);
4635 bool Saturating = (N->getOpcode() == ISD::SMULFIXSAT ||
4636 N->getOpcode() == ISD::UMULFIXSAT);
4637 bool Signed = (N->getOpcode() == ISD::SMULFIX ||
4638 N->getOpcode() == ISD::SMULFIXSAT);
4639
4640 // Handle special case when scale is equal to zero.
4641 if (!Scale) {
4642 SDValue Result;
4643 if (!Saturating) {
4644 Result = DAG.getNode(ISD::MUL, dl, VT, LHS, RHS);
4645 } else {
4646 EVT BoolVT = getSetCCResultType(VT);
4647 unsigned MulOp = Signed ? ISD::SMULO : ISD::UMULO;
4648 Result = DAG.getNode(MulOp, dl, DAG.getVTList(VT, BoolVT), LHS, RHS);
4649 SDValue Product = Result.getValue(0);
4650 SDValue Overflow = Result.getValue(1);
4651 if (Signed) {
4652 APInt MinVal = APInt::getSignedMinValue(VTSize);
4653 APInt MaxVal = APInt::getSignedMaxValue(VTSize);
4654 SDValue SatMin = DAG.getConstant(MinVal, dl, VT);
4655 SDValue SatMax = DAG.getConstant(MaxVal, dl, VT);
4656 SDValue Zero = DAG.getConstant(0, dl, VT);
4657 // Xor the inputs, if resulting sign bit is 0 the product will be
4658 // positive, else negative.
4659 SDValue Xor = DAG.getNode(ISD::XOR, dl, VT, LHS, RHS);
4660 SDValue ProdNeg = DAG.getSetCC(dl, BoolVT, Xor, Zero, ISD::SETLT);
4661 Result = DAG.getSelect(dl, VT, ProdNeg, SatMin, SatMax);
4662 Result = DAG.getSelect(dl, VT, Overflow, Result, Product);
4663 } else {
4664 // For unsigned multiplication, we only need to check the max since we
4665 // can't really overflow towards zero.
4666 APInt MaxVal = APInt::getMaxValue(VTSize);
4667 SDValue SatMax = DAG.getConstant(MaxVal, dl, VT);
4668 Result = DAG.getSelect(dl, VT, Overflow, SatMax, Product);
4669 }
4670 }
4671 SplitInteger(Result, Lo, Hi);
4672 return;
4673 }
4674
4675 // For SMULFIX[SAT] we only expect to find Scale<VTSize, but this assert will
4676 // cover for unhandled cases below, while still being valid for UMULFIX[SAT].
4677 assert(Scale <= VTSize && "Scale can't be larger than the value type size.");
4678
4679 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
4680 SDValue LL, LH, RL, RH;
4681 GetExpandedInteger(LHS, LL, LH);
4682 GetExpandedInteger(RHS, RL, RH);
4684
4685 unsigned LoHiOp = Signed ? ISD::SMUL_LOHI : ISD::UMUL_LOHI;
4686 if (!TLI.expandMUL_LOHI(LoHiOp, VT, dl, LHS, RHS, Result, NVT, DAG,
4688 LL, LH, RL, RH)) {
4689 Result.clear();
4690 Result.resize(4);
4691
4692 SDValue LoTmp, HiTmp;
4693 TLI.forceExpandWideMUL(DAG, dl, Signed, LHS, RHS, LoTmp, HiTmp);
4694 SplitInteger(LoTmp, Result[0], Result[1]);
4695 SplitInteger(HiTmp, Result[2], Result[3]);
4696 }
4697 assert(Result.size() == 4 && "Unexpected number of partlets in the result");
4698
4699 unsigned NVTSize = NVT.getScalarSizeInBits();
4700 assert((VTSize == NVTSize * 2) && "Expected the new value type to be half "
4701 "the size of the current value type");
4702
4703 // After getting the multiplication result in 4 parts, we need to perform a
4704 // shift right by the amount of the scale to get the result in that scale.
4705 //
4706 // Let's say we multiply 2 64 bit numbers. The resulting value can be held in
4707 // 128 bits that are cut into 4 32-bit parts:
4708 //
4709 // HH HL LH LL
4710 // |---32---|---32---|---32---|---32---|
4711 // 128 96 64 32 0
4712 //
4713 // |------VTSize-----|
4714 //
4715 // |NVTSize-|
4716 //
4717 // The resulting Lo and Hi would normally be in LL and LH after the shift. But
4718 // to avoid unneccessary shifting of all 4 parts, we can adjust the shift
4719 // amount and get Lo and Hi using two funnel shifts. Or for the special case
4720 // when Scale is a multiple of NVTSize we can just pick the result without
4721 // shifting.
4722 uint64_t Part0 = Scale / NVTSize; // Part holding lowest bit needed.
4723 if (Scale % NVTSize) {
4724 SDValue ShiftAmount = DAG.getShiftAmountConstant(Scale % NVTSize, NVT, dl);
4725 Lo = DAG.getNode(ISD::FSHR, dl, NVT, Result[Part0 + 1], Result[Part0],
4726 ShiftAmount);
4727 Hi = DAG.getNode(ISD::FSHR, dl, NVT, Result[Part0 + 2], Result[Part0 + 1],
4728 ShiftAmount);
4729 } else {
4730 Lo = Result[Part0];
4731 Hi = Result[Part0 + 1];
4732 }
4733
4734 // Unless saturation is requested we are done. The result is in <Hi,Lo>.
4735 if (!Saturating)
4736 return;
4737
4738 // Can not overflow when there is no integer part.
4739 if (Scale == VTSize)
4740 return;
4741
4742 // To handle saturation we must check for overflow in the multiplication.
4743 //
4744 // Unsigned overflow happened if the upper (VTSize - Scale) bits (of Result)
4745 // aren't all zeroes.
4746 //
4747 // Signed overflow happened if the upper (VTSize - Scale + 1) bits (of Result)
4748 // aren't all ones or all zeroes.
4749 //
4750 // We cannot overflow past HH when multiplying 2 ints of size VTSize, so the
4751 // highest bit of HH determines saturation direction in the event of signed
4752 // saturation.
4753
4754 SDValue ResultHL = Result[2];
4755 SDValue ResultHH = Result[3];
4756
4757 SDValue SatMax, SatMin;
4758 SDValue NVTZero = DAG.getConstant(0, dl, NVT);
4759 SDValue NVTNeg1 = DAG.getAllOnesConstant(dl, NVT);
4760 EVT BoolNVT = getSetCCResultType(NVT);
4761
4762 if (!Signed) {
4763 if (Scale < NVTSize) {
4764 // Overflow happened if ((HH | (HL >> Scale)) != 0).
4765 SDValue HLAdjusted =
4766 DAG.getNode(ISD::SRL, dl, NVT, ResultHL,
4767 DAG.getShiftAmountConstant(Scale, NVT, dl));
4768 SDValue Tmp = DAG.getNode(ISD::OR, dl, NVT, HLAdjusted, ResultHH);
4769 SatMax = DAG.getSetCC(dl, BoolNVT, Tmp, NVTZero, ISD::SETNE);
4770 } else if (Scale == NVTSize) {
4771 // Overflow happened if (HH != 0).
4772 SatMax = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTZero, ISD::SETNE);
4773 } else if (Scale < VTSize) {
4774 // Overflow happened if ((HH >> (Scale - NVTSize)) != 0).
4775 SDValue HLAdjusted =
4776 DAG.getNode(ISD::SRL, dl, NVT, ResultHL,
4777 DAG.getShiftAmountConstant(Scale - NVTSize, NVT, dl));
4778 SatMax = DAG.getSetCC(dl, BoolNVT, HLAdjusted, NVTZero, ISD::SETNE);
4779 } else
4780 llvm_unreachable("Scale must be less or equal to VTSize for UMULFIXSAT"
4781 "(and saturation can't happen with Scale==VTSize).");
4782
4783 Hi = DAG.getSelect(dl, NVT, SatMax, NVTNeg1, Hi);
4784 Lo = DAG.getSelect(dl, NVT, SatMax, NVTNeg1, Lo);
4785 return;
4786 }
4787
4788 if (Scale < NVTSize) {
4789 // The number of overflow bits we can check are VTSize - Scale + 1 (we
4790 // include the sign bit). If these top bits are > 0, then we overflowed past
4791 // the max value. If these top bits are < -1, then we overflowed past the
4792 // min value. Otherwise, we did not overflow.
4793 unsigned OverflowBits = VTSize - Scale + 1;
4794 assert(OverflowBits <= VTSize && OverflowBits > NVTSize &&
4795 "Extent of overflow bits must start within HL");
4796 SDValue HLHiMask = DAG.getConstant(
4797 APInt::getHighBitsSet(NVTSize, OverflowBits - NVTSize), dl, NVT);
4798 SDValue HLLoMask = DAG.getConstant(
4799 APInt::getLowBitsSet(NVTSize, VTSize - OverflowBits), dl, NVT);
4800 // We overflow max if HH > 0 or (HH == 0 && HL > HLLoMask).
4801 SDValue HHGT0 = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTZero, ISD::SETGT);
4802 SDValue HHEQ0 = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTZero, ISD::SETEQ);
4803 SDValue HLUGT = DAG.getSetCC(dl, BoolNVT, ResultHL, HLLoMask, ISD::SETUGT);
4804 SatMax = DAG.getNode(ISD::OR, dl, BoolNVT, HHGT0,
4805 DAG.getNode(ISD::AND, dl, BoolNVT, HHEQ0, HLUGT));
4806 // We overflow min if HH < -1 or (HH == -1 && HL < HLHiMask).
4807 SDValue HHLT = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTNeg1, ISD::SETLT);
4808 SDValue HHEQ = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTNeg1, ISD::SETEQ);
4809 SDValue HLULT = DAG.getSetCC(dl, BoolNVT, ResultHL, HLHiMask, ISD::SETULT);
4810 SatMin = DAG.getNode(ISD::OR, dl, BoolNVT, HHLT,
4811 DAG.getNode(ISD::AND, dl, BoolNVT, HHEQ, HLULT));
4812 } else if (Scale == NVTSize) {
4813 // We overflow max if HH > 0 or (HH == 0 && HL sign bit is 1).
4814 SDValue HHGT0 = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTZero, ISD::SETGT);
4815 SDValue HHEQ0 = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTZero, ISD::SETEQ);
4816 SDValue HLNeg = DAG.getSetCC(dl, BoolNVT, ResultHL, NVTZero, ISD::SETLT);
4817 SatMax = DAG.getNode(ISD::OR, dl, BoolNVT, HHGT0,
4818 DAG.getNode(ISD::AND, dl, BoolNVT, HHEQ0, HLNeg));
4819 // We overflow min if HH < -1 or (HH == -1 && HL sign bit is 0).
4820 SDValue HHLT = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTNeg1, ISD::SETLT);
4821 SDValue HHEQ = DAG.getSetCC(dl, BoolNVT, ResultHH, NVTNeg1, ISD::SETEQ);
4822 SDValue HLPos = DAG.getSetCC(dl, BoolNVT, ResultHL, NVTZero, ISD::SETGE);
4823 SatMin = DAG.getNode(ISD::OR, dl, BoolNVT, HHLT,
4824 DAG.getNode(ISD::AND, dl, BoolNVT, HHEQ, HLPos));
4825 } else if (Scale < VTSize) {
4826 // This is similar to the case when we saturate if Scale < NVTSize, but we
4827 // only need to check HH.
4828 unsigned OverflowBits = VTSize - Scale + 1;
4829 SDValue HHHiMask = DAG.getConstant(
4830 APInt::getHighBitsSet(NVTSize, OverflowBits), dl, NVT);
4831 SDValue HHLoMask = DAG.getConstant(
4832 APInt::getLowBitsSet(NVTSize, NVTSize - OverflowBits), dl, NVT);
4833 SatMax = DAG.getSetCC(dl, BoolNVT, ResultHH, HHLoMask, ISD::SETGT);
4834 SatMin = DAG.getSetCC(dl, BoolNVT, ResultHH, HHHiMask, ISD::SETLT);
4835 } else
4836 llvm_unreachable("Illegal scale for signed fixed point mul.");
4837
4838 // Saturate to signed maximum.
4839 APInt MaxHi = APInt::getSignedMaxValue(NVTSize);
4840 APInt MaxLo = APInt::getAllOnes(NVTSize);
4841 Hi = DAG.getSelect(dl, NVT, SatMax, DAG.getConstant(MaxHi, dl, NVT), Hi);
4842 Lo = DAG.getSelect(dl, NVT, SatMax, DAG.getConstant(MaxLo, dl, NVT), Lo);
4843 // Saturate to signed minimum.
4844 APInt MinHi = APInt::getSignedMinValue(NVTSize);
4845 Hi = DAG.getSelect(dl, NVT, SatMin, DAG.getConstant(MinHi, dl, NVT), Hi);
4846 Lo = DAG.getSelect(dl, NVT, SatMin, NVTZero, Lo);
4847}
4848
4849void DAGTypeLegalizer::ExpandIntRes_DIVFIX(SDNode *N, SDValue &Lo,
4850 SDValue &Hi) {
4851 SDLoc dl(N);
4852 // Try expanding in the existing type first.
4853 SDValue Res = TLI.expandFixedPointDiv(N->getOpcode(), dl, N->getOperand(0),
4854 N->getOperand(1),
4855 N->getConstantOperandVal(2), DAG);
4856
4857 if (!Res)
4858 Res = earlyExpandDIVFIX(N, N->getOperand(0), N->getOperand(1),
4859 N->getConstantOperandVal(2), TLI, DAG);
4860 SplitInteger(Res, Lo, Hi);
4861}
4862
4863void DAGTypeLegalizer::ExpandIntRes_SADDSUBO(SDNode *Node,
4864 SDValue &Lo, SDValue &Hi) {
4865 assert((Node->getOpcode() == ISD::SADDO || Node->getOpcode() == ISD::SSUBO) &&
4866 "Node has unexpected Opcode");
4867 SDValue LHS = Node->getOperand(0);
4868 SDValue RHS = Node->getOperand(1);
4869 SDLoc dl(Node);
4870
4871 SDValue Ovf;
4872
4873 bool IsAdd = Node->getOpcode() == ISD::SADDO;
4874 unsigned CarryOp = IsAdd ? ISD::SADDO_CARRY : ISD::SSUBO_CARRY;
4875
4876 bool HasCarryOp = TLI.isOperationLegalOrCustom(
4877 CarryOp, TLI.getTypeToExpandTo(*DAG.getContext(), LHS.getValueType()));
4878
4879 if (HasCarryOp) {
4880 // Expand the subcomponents.
4881 SDValue LHSL, LHSH, RHSL, RHSH;
4882 GetExpandedInteger(LHS, LHSL, LHSH);
4883 GetExpandedInteger(RHS, RHSL, RHSH);
4884 SDVTList VTList = DAG.getVTList(LHSL.getValueType(), Node->getValueType(1));
4885
4886 Lo = DAG.getNode(IsAdd ? ISD::UADDO : ISD::USUBO, dl, VTList, {LHSL, RHSL});
4887 Hi = DAG.getNode(CarryOp, dl, VTList, { LHSH, RHSH, Lo.getValue(1) });
4888
4889 Ovf = Hi.getValue(1);
4890 } else {
4891 // Expand the result by simply replacing it with the equivalent
4892 // non-overflow-checking operation.
4893 SDValue Sum = DAG.getNode(Node->getOpcode() == ISD::SADDO ?
4894 ISD::ADD : ISD::SUB, dl, LHS.getValueType(),
4895 LHS, RHS);
4896 SplitInteger(Sum, Lo, Hi);
4897
4898 // Compute the overflow.
4899 //
4900 // LHSSign -> LHS < 0
4901 // RHSSign -> RHS < 0
4902 // SumSign -> Sum < 0
4903 //
4904 // Add:
4905 // Overflow -> (LHSSign == RHSSign) && (LHSSign != SumSign)
4906 // Sub:
4907 // Overflow -> (LHSSign != RHSSign) && (LHSSign != SumSign)
4908 //
4909 // To get better codegen we can rewrite this by doing bitwise math on
4910 // the integers and extract the final sign bit at the end. So the
4911 // above becomes:
4912 //
4913 // Add:
4914 // Overflow -> (~(LHS ^ RHS) & (LHS ^ Sum)) < 0
4915 // Sub:
4916 // Overflow -> ((LHS ^ RHS) & (LHS ^ Sum)) < 0
4917 //
4918 // NOTE: This is different than the expansion we do in expandSADDSUBO
4919 // because it is more costly to implement the same overflow predicate with
4920 // SETCC nodes when the integers are split.
4921 EVT VT = LHS.getValueType();
4922 SDValue SignsMatch = DAG.getNode(ISD::XOR, dl, VT, LHS, RHS);
4923 if (IsAdd)
4924 SignsMatch = DAG.getNOT(dl, SignsMatch, VT);
4925
4926 SDValue SumSignNE = DAG.getNode(ISD::XOR, dl, VT, LHS, Sum);
4927 Ovf = DAG.getNode(ISD::AND, dl, VT, SignsMatch, SumSignNE);
4928 EVT OType = Node->getValueType(1);
4929 Ovf = DAG.getSetCC(dl, OType, Ovf, DAG.getConstant(0, dl, VT), ISD::SETLT);
4930 }
4931
4932 // Use the calculated overflow everywhere.
4933 ReplaceValueWith(SDValue(Node, 1), Ovf);
4934}
4935
4936void DAGTypeLegalizer::ExpandIntRes_SDIV(SDNode *N,
4937 SDValue &Lo, SDValue &Hi) {
4938 EVT VT = N->getValueType(0);
4939 SDLoc dl(N);
4940 SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
4941
4942 if (TLI.getOperationAction(ISD::SDIVREM, VT) == TargetLowering::Custom) {
4943 SDValue Res = DAG.getNode(ISD::SDIVREM, dl, DAG.getVTList(VT, VT), Ops);
4944 SplitInteger(Res.getValue(0), Lo, Hi);
4945 return;
4946 }
4947
4948 RTLIB::Libcall LC = RTLIB::getSDIV(VT);
4949 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported SDIV!");
4950
4951 TargetLowering::MakeLibCallOptions CallOptions;
4952 CallOptions.setIsSigned(true);
4953 SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, CallOptions, dl).first, Lo, Hi);
4954}
4955
4956void DAGTypeLegalizer::ExpandIntRes_ShiftThroughStack(SDNode *N, SDValue &Lo,
4957 SDValue &Hi) {
4958 SDLoc dl(N);
4959 SDValue Shiftee = N->getOperand(0);
4960 EVT VT = Shiftee.getValueType();
4961 SDValue ShAmt = N->getOperand(1);
4962 EVT ShAmtVT = ShAmt.getValueType();
4963
4964 EVT LoadVT = VT;
4965 do {
4966 LoadVT = TLI.getTypeToTransformTo(*DAG.getContext(), LoadVT);
4967 } while (!TLI.isTypeLegal(LoadVT));
4968
4969 const unsigned ShiftUnitInBits = LoadVT.getStoreSizeInBits();
4970 assert(ShiftUnitInBits <= VT.getScalarSizeInBits());
4971 assert(isPowerOf2_32(ShiftUnitInBits) &&
4972 "Shifting unit is not a a power of two!");
4973
4974 const bool IsOneStepShift =
4975 DAG.computeKnownBits(ShAmt).countMinTrailingZeros() >=
4976 Log2_32(ShiftUnitInBits);
4977
4978 // If we can't do it as one step, we'll have two uses of shift amount,
4979 // and thus must freeze it.
4980 if (!IsOneStepShift)
4981 ShAmt = DAG.getFreeze(ShAmt);
4982
4983 unsigned VTBitWidth = VT.getScalarSizeInBits();
4984 assert(VTBitWidth % 8 == 0 && "Shifting a not byte multiple value?");
4985 unsigned VTByteWidth = VTBitWidth / 8;
4986 assert(isPowerOf2_32(VTByteWidth) &&
4987 "Shiftee type size is not a power of two!");
4988 unsigned StackSlotByteWidth = 2 * VTByteWidth;
4989 unsigned StackSlotBitWidth = 8 * StackSlotByteWidth;
4990 EVT StackSlotVT = EVT::getIntegerVT(*DAG.getContext(), StackSlotBitWidth);
4991
4992 // Get a temporary stack slot 2x the width of our VT.
4993 // FIXME: reuse stack slots?
4994 Align StackAlign = DAG.getReducedAlign(StackSlotVT, /*UseABI=*/false);
4995 SDValue StackPtr =
4996 DAG.CreateStackTemporary(StackSlotVT.getStoreSize(), StackAlign);
4997 EVT PtrTy = StackPtr.getValueType();
4998 SDValue Ch = DAG.getEntryNode();
4999
5000 MachinePointerInfo StackPtrInfo = MachinePointerInfo::getFixedStack(
5001 DAG.getMachineFunction(),
5002 cast<FrameIndexSDNode>(StackPtr.getNode())->getIndex());
5003
5004 // Extend the value, that is being shifted, to the entire stack slot's width.
5005 SDValue Init;
5006 if (N->getOpcode() != ISD::SHL) {
5007 unsigned WideningOpc =
5008 N->getOpcode() == ISD::SRA ? ISD::SIGN_EXTEND : ISD::ZERO_EXTEND;
5009 Init = DAG.getNode(WideningOpc, dl, StackSlotVT, Shiftee);
5010 } else {
5011 // For left-shifts, pad the Shiftee's LSB with zeros to twice it's width.
5012 SDValue AllZeros = DAG.getConstant(0, dl, VT);
5013 Init = DAG.getNode(ISD::BUILD_PAIR, dl, StackSlotVT, AllZeros, Shiftee);
5014 }
5015 // And spill it into the stack slot.
5016 Ch = DAG.getStore(Ch, dl, Init, StackPtr, StackPtrInfo, StackAlign);
5017
5018 // Now, compute the full-byte offset into stack slot from where we can load.
5019 // We have shift amount, which is in bits. Offset should point to an aligned
5020 // address.
5021 SDNodeFlags Flags;
5022 Flags.setExact(IsOneStepShift);
5023 SDValue SrlTmp = DAG.getNode(
5024 ISD::SRL, dl, ShAmtVT, ShAmt,
5025 DAG.getConstant(Log2_32(ShiftUnitInBits), dl, ShAmtVT), Flags);
5026 SDValue BitOffset =
5027 DAG.getNode(ISD::SHL, dl, ShAmtVT, SrlTmp,
5028 DAG.getConstant(Log2_32(ShiftUnitInBits), dl, ShAmtVT));
5029
5030 SDValue ByteOffset =
5031 DAG.getNode(ISD::SRL, dl, ShAmtVT, BitOffset,
5032 DAG.getConstant(3, dl, ShAmtVT), SDNodeFlags::Exact);
5033 // And clamp it, because OOB load is an immediate UB,
5034 // while shift overflow would have *just* been poison.
5035 ByteOffset = DAG.getNode(ISD::AND, dl, ShAmtVT, ByteOffset,
5036 DAG.getConstant(VTByteWidth - 1, dl, ShAmtVT));
5037 // We have exactly two strategies on indexing into stack slot here:
5038 // 1. upwards starting from the beginning of the slot
5039 // 2. downwards starting from the middle of the slot
5040 // On little-endian machine, we pick 1. for right shifts and 2. for left-shift
5041 // and vice versa on big-endian machine.
5042 bool WillIndexUpwards = N->getOpcode() != ISD::SHL;
5043 if (DAG.getDataLayout().isBigEndian())
5044 WillIndexUpwards = !WillIndexUpwards;
5045
5046 SDValue AdjStackPtr;
5047 if (WillIndexUpwards) {
5048 AdjStackPtr = StackPtr;
5049 } else {
5050 AdjStackPtr = DAG.getMemBasePlusOffset(
5051 StackPtr, DAG.getConstant(VTByteWidth, dl, PtrTy), dl);
5052 ByteOffset = DAG.getNegative(ByteOffset, dl, ShAmtVT);
5053 }
5054
5055 // Get the pointer somewhere into the stack slot from which we need to load.
5056 ByteOffset = DAG.getSExtOrTrunc(ByteOffset, dl, PtrTy);
5057 AdjStackPtr = DAG.getMemBasePlusOffset(AdjStackPtr, ByteOffset, dl);
5058
5059 // And load it! While the load is not legal, legalizing it is obvious.
5060 SDValue Res =
5061 DAG.getLoad(VT, dl, Ch, AdjStackPtr,
5062 MachinePointerInfo::getUnknownStack(DAG.getMachineFunction()),
5063 commonAlignment(StackAlign, LoadVT.getStoreSize()));
5064
5065 // If we may still have a remaining bits to shift by, do so now.
5066 if (!IsOneStepShift) {
5067 SDValue ShAmtRem =
5068 DAG.getNode(ISD::AND, dl, ShAmtVT, ShAmt,
5069 DAG.getConstant(ShiftUnitInBits - 1, dl, ShAmtVT));
5070 Res = DAG.getNode(N->getOpcode(), dl, VT, Res, ShAmtRem);
5071 }
5072
5073 // Finally, split the computed value.
5074 SplitInteger(Res, Lo, Hi);
5075}
5076
5077void DAGTypeLegalizer::ExpandIntRes_Shift(SDNode *N,
5078 SDValue &Lo, SDValue &Hi) {
5079 EVT VT = N->getValueType(0);
5080 unsigned Opc = N->getOpcode();
5081 SDLoc dl(N);
5082
5083 // If we can emit an efficient shift operation, do so now. Check to see if
5084 // the RHS is a constant.
5085 if (ConstantSDNode *CN = dyn_cast<ConstantSDNode>(N->getOperand(1)))
5086 return ExpandShiftByConstant(N, CN->getAPIntValue(), Lo, Hi);
5087
5088 // If we can determine that the high bit of the shift is zero or one, even if
5089 // the low bits are variable, emit this shift in an optimized form.
5090 if (ExpandShiftWithKnownAmountBit(N, Lo, Hi))
5091 return;
5092
5093 // If this target supports shift_PARTS, use it. First, map to the _PARTS opc.
5094 unsigned PartsOpc;
5095 if (Opc == ISD::SHL) {
5096 PartsOpc = ISD::SHL_PARTS;
5097 } else if (Opc == ISD::SRL) {
5098 PartsOpc = ISD::SRL_PARTS;
5099 } else {
5100 assert(Opc == ISD::SRA && "Unknown shift!");
5101 PartsOpc = ISD::SRA_PARTS;
5102 }
5103
5104 // Next check to see if the target supports this SHL_PARTS operation or if it
5105 // will custom expand it. Don't lower this to SHL_PARTS when we optimise for
5106 // size, but create a libcall instead.
5107 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
5108 TargetLowering::LegalizeAction Action = TLI.getOperationAction(PartsOpc, NVT);
5109 const bool LegalOrCustom =
5110 (Action == TargetLowering::Legal && TLI.isTypeLegal(NVT)) ||
5111 Action == TargetLowering::Custom;
5112
5113 unsigned ExpansionFactor = 1;
5114 // That VT->NVT expansion is one step. But will we re-expand NVT?
5115 for (EVT TmpVT = NVT;;) {
5116 EVT NewTMPVT = TLI.getTypeToTransformTo(*DAG.getContext(), TmpVT);
5117 if (NewTMPVT == TmpVT)
5118 break;
5119 TmpVT = NewTMPVT;
5120 ++ExpansionFactor;
5121 }
5122
5124 TLI.preferredShiftLegalizationStrategy(DAG, N, ExpansionFactor);
5125
5127 return ExpandIntRes_ShiftThroughStack(N, Lo, Hi);
5128
5129 if (LegalOrCustom &&
5131 // Expand the subcomponents.
5132 SDValue LHSL, LHSH;
5133 GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
5134 EVT VT = LHSL.getValueType();
5135
5136 // If the shift amount operand is coming from a vector legalization it may
5137 // have an illegal type. Fix that first by casting the operand, otherwise
5138 // the new SHL_PARTS operation would need further legalization.
5139 SDValue ShiftOp = N->getOperand(1);
5140 EVT ShiftTy = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
5141 if (ShiftOp.getValueType() != ShiftTy)
5142 ShiftOp = DAG.getZExtOrTrunc(ShiftOp, dl, ShiftTy);
5143
5144 SDValue Ops[] = { LHSL, LHSH, ShiftOp };
5145 Lo = DAG.getNode(PartsOpc, dl, DAG.getVTList(VT, VT), Ops);
5146 Hi = Lo.getValue(1);
5147 return;
5148 }
5149
5150 // Otherwise, emit a libcall.
5151 RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
5152 bool isSigned;
5153 if (Opc == ISD::SHL) {
5154 isSigned = false; /*sign irrelevant*/
5155 LC = RTLIB::getSHL(VT);
5156 } else if (Opc == ISD::SRL) {
5157 isSigned = false;
5158 LC = RTLIB::getSRL(VT);
5159 } else {
5160 assert(Opc == ISD::SRA && "Unknown shift!");
5161 isSigned = true;
5162 LC = RTLIB::getSRA(VT);
5163 }
5164
5165 if (RTLIB::LibcallImpl LibcallImpl = DAG.getLibcalls().getLibcallImpl(LC)) {
5166 EVT ShAmtTy =
5167 EVT::getIntegerVT(*DAG.getContext(), DAG.getLibInfo().getIntSize());
5168 SDValue ShAmt = DAG.getZExtOrTrunc(N->getOperand(1), dl, ShAmtTy);
5169 SDValue Ops[2] = {N->getOperand(0), ShAmt};
5170 TargetLowering::MakeLibCallOptions CallOptions;
5171 CallOptions.setIsSigned(isSigned);
5172 SplitInteger(
5173 TLI.makeLibCall(DAG, LibcallImpl, VT, Ops, CallOptions, dl).first, Lo,
5174 Hi);
5175 return;
5176 }
5177
5178 if (!ExpandShiftWithUnknownAmountBit(N, Lo, Hi))
5179 llvm_unreachable("Unsupported shift!");
5180}
5181
5182void DAGTypeLegalizer::ExpandIntRes_SIGN_EXTEND(SDNode *N,
5183 SDValue &Lo, SDValue &Hi) {
5184 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
5185 SDLoc dl(N);
5186 SDValue Op = N->getOperand(0);
5187 if (Op.getValueType().bitsLE(NVT)) {
5188 // The low part is sign extension of the input (degenerates to a copy).
5189 Lo = DAG.getNode(ISD::SIGN_EXTEND, dl, NVT, N->getOperand(0));
5190 // The high part is obtained by SRA'ing all but one of the bits of low part.
5191 unsigned LoSize = NVT.getSizeInBits();
5192 Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
5193 DAG.getShiftAmountConstant(LoSize - 1, NVT, dl));
5194 } else {
5195 // For example, extension of an i48 to an i64. The operand type necessarily
5196 // promotes to the result type, so will end up being expanded too.
5197 assert(getTypeAction(Op.getValueType()) ==
5199 "Only know how to promote this result!");
5200 SDValue Res = GetPromotedInteger(Op);
5201 assert(Res.getValueType() == N->getValueType(0) &&
5202 "Operand over promoted?");
5203 // Split the promoted operand. This will simplify when it is expanded.
5204 SplitInteger(Res, Lo, Hi);
5205 unsigned ExcessBits = Op.getValueSizeInBits() - NVT.getSizeInBits();
5206 Hi = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Hi.getValueType(), Hi,
5207 DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
5208 ExcessBits)));
5209 }
5210}
5211
5212void DAGTypeLegalizer::
5213ExpandIntRes_SIGN_EXTEND_INREG(SDNode *N, SDValue &Lo, SDValue &Hi) {
5214 SDLoc dl(N);
5215 GetExpandedInteger(N->getOperand(0), Lo, Hi);
5216 EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
5217
5218 if (EVT.bitsLE(Lo.getValueType())) {
5219 // sext_inreg the low part if needed.
5220 Lo = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Lo.getValueType(), Lo,
5221 N->getOperand(1));
5222
5223 // The high part gets the sign extension from the lo-part. This handles
5224 // things like sextinreg V:i64 from i8.
5225 Hi = DAG.getNode(ISD::SRA, dl, Hi.getValueType(), Lo,
5226 DAG.getShiftAmountConstant(Hi.getValueSizeInBits() - 1,
5227 Hi.getValueType(), dl));
5228 } else {
5229 // For example, extension of an i48 to an i64. Leave the low part alone,
5230 // sext_inreg the high part.
5231 unsigned ExcessBits = EVT.getSizeInBits() - Lo.getValueSizeInBits();
5232 Hi = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Hi.getValueType(), Hi,
5233 DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
5234 ExcessBits)));
5235 }
5236}
5237
5238void DAGTypeLegalizer::ExpandIntRes_SREM(SDNode *N,
5239 SDValue &Lo, SDValue &Hi) {
5240 EVT VT = N->getValueType(0);
5241 SDLoc dl(N);
5242 SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
5243
5244 if (TLI.getOperationAction(ISD::SDIVREM, VT) == TargetLowering::Custom) {
5245 SDValue Res = DAG.getNode(ISD::SDIVREM, dl, DAG.getVTList(VT, VT), Ops);
5246 SplitInteger(Res.getValue(1), Lo, Hi);
5247 return;
5248 }
5249
5250 RTLIB::Libcall LC = RTLIB::getSREM(VT);
5251 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported SREM!");
5252
5253 TargetLowering::MakeLibCallOptions CallOptions;
5254 CallOptions.setIsSigned(true);
5255 SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, CallOptions, dl).first, Lo, Hi);
5256}
5257
5258void DAGTypeLegalizer::ExpandIntRes_TRUNCATE(SDNode *N,
5259 SDValue &Lo, SDValue &Hi) {
5260 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
5261 SDValue InOp = N->getOperand(0);
5262 EVT InVT = InOp.getValueType();
5263 SDLoc dl(N);
5264 Lo = DAG.getNode(ISD::TRUNCATE, dl, NVT, InOp);
5265 Hi = DAG.getNode(ISD::SRL, dl, InVT, InOp,
5266 DAG.getShiftAmountConstant(NVT.getSizeInBits(), InVT, dl));
5267 Hi = DAG.getNode(ISD::TRUNCATE, dl, NVT, Hi);
5268}
5269
5270void DAGTypeLegalizer::ExpandIntRes_XMULO(SDNode *N,
5271 SDValue &Lo, SDValue &Hi) {
5272 EVT VT = N->getValueType(0);
5273 SDLoc dl(N);
5274
5275 if (N->getOpcode() == ISD::UMULO) {
5276 // This section expands the operation into the following sequence of
5277 // instructions. `iNh` here refers to a type which has half the bit width of
5278 // the type the original operation operated on.
5279 //
5280 // %0 = %LHS.HI != 0 && %RHS.HI != 0
5281 // %1 = { iNh, i1 } @umul.with.overflow.iNh(iNh %LHS.HI, iNh %RHS.LO)
5282 // %2 = { iNh, i1 } @umul.with.overflow.iNh(iNh %RHS.HI, iNh %LHS.LO)
5283 // %3 = mul nuw iN (%LHS.LOW as iN), (%RHS.LOW as iN)
5284 // %4 = add iNh %1.0, %2.0 as iN
5285 // %5 = { iNh, i1 } @uadd.with.overflow.iNh(iNh %4, iNh %3.HIGH)
5286 //
5287 // %lo = %3.LO
5288 // %hi = %5.0
5289 // %ovf = %0 || %1.1 || %2.1 || %5.1
5290 SDValue LHS = N->getOperand(0), RHS = N->getOperand(1);
5291 SDValue LHSHigh, LHSLow, RHSHigh, RHSLow;
5292 GetExpandedInteger(LHS, LHSLow, LHSHigh);
5293 GetExpandedInteger(RHS, RHSLow, RHSHigh);
5294 EVT HalfVT = LHSLow.getValueType();
5295 EVT BitVT = N->getValueType(1);
5296 SDVTList VTHalfWithO = DAG.getVTList(HalfVT, BitVT);
5297
5298 SDValue HalfZero = DAG.getConstant(0, dl, HalfVT);
5299 SDValue Overflow = DAG.getNode(ISD::AND, dl, BitVT,
5300 DAG.getSetCC(dl, BitVT, LHSHigh, HalfZero, ISD::SETNE),
5301 DAG.getSetCC(dl, BitVT, RHSHigh, HalfZero, ISD::SETNE));
5302
5303 SDValue One = DAG.getNode(ISD::UMULO, dl, VTHalfWithO, LHSHigh, RHSLow);
5304 Overflow = DAG.getNode(ISD::OR, dl, BitVT, Overflow, One.getValue(1));
5305
5306 SDValue Two = DAG.getNode(ISD::UMULO, dl, VTHalfWithO, RHSHigh, LHSLow);
5307 Overflow = DAG.getNode(ISD::OR, dl, BitVT, Overflow, Two.getValue(1));
5308
5309 SDValue HighSum = DAG.getNode(ISD::ADD, dl, HalfVT, One, Two);
5310
5311 // Cannot use `UMUL_LOHI` directly, because some 32-bit targets (ARM) do not
5312 // know how to expand `i64,i64 = umul_lohi a, b` and abort (why isn’t this
5313 // operation recursively legalized?).
5314 //
5315 // Many backends understand this pattern and will convert into LOHI
5316 // themselves, if applicable.
5317 SDValue Three = DAG.getNode(ISD::MUL, dl, VT,
5318 DAG.getNode(ISD::ZERO_EXTEND, dl, VT, LHSLow),
5319 DAG.getNode(ISD::ZERO_EXTEND, dl, VT, RHSLow));
5320 SplitInteger(Three, Lo, Hi);
5321
5322 Hi = DAG.getNode(ISD::UADDO, dl, VTHalfWithO, Hi, HighSum);
5323 Overflow = DAG.getNode(ISD::OR, dl, BitVT, Overflow, Hi.getValue(1));
5324 ReplaceValueWith(SDValue(N, 1), Overflow);
5325 return;
5326 }
5327
5328 Type *RetTy = VT.getTypeForEVT(*DAG.getContext());
5329 EVT PtrVT = TLI.getPointerTy(DAG.getDataLayout());
5330 Type *PtrTy = PtrVT.getTypeForEVT(*DAG.getContext());
5331
5332 // Replace this with a libcall that will check overflow.
5333 RTLIB::Libcall LC = RTLIB::getMULO(VT);
5334 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
5335
5336 // If we don't have the libcall or if the function we are compiling is the
5337 // implementation of the expected libcall (avoid inf-loop), expand inline.
5338 if (LCImpl == RTLIB::Unsupported ||
5340 DAG.getMachineFunction().getName()) {
5341 // FIXME: This is not an optimal expansion, but better than crashing.
5342 SDValue MulLo, MulHi;
5343 TLI.forceExpandWideMUL(DAG, dl, /*Signed=*/true, N->getOperand(0),
5344 N->getOperand(1), MulLo, MulHi);
5345 SDValue SRA = DAG.getNode(
5346 ISD::SRA, dl, VT, MulLo,
5347 DAG.getShiftAmountConstant(VT.getScalarSizeInBits() - 1, VT, dl));
5348 SDValue Overflow =
5349 DAG.getSetCC(dl, N->getValueType(1), MulHi, SRA, ISD::SETNE);
5350 SplitInteger(MulLo, Lo, Hi);
5351 ReplaceValueWith(SDValue(N, 1), Overflow);
5352 return;
5353 }
5354
5355 SDValue Temp = DAG.CreateStackTemporary(PtrVT);
5356 // Temporary for the overflow value, default it to zero.
5357 SDValue Chain =
5358 DAG.getStore(DAG.getEntryNode(), dl, DAG.getConstant(0, dl, PtrVT), Temp,
5359 MachinePointerInfo());
5360
5362 for (const SDValue &Op : N->op_values()) {
5363 EVT ArgVT = Op.getValueType();
5364 Type *ArgTy = ArgVT.getTypeForEVT(*DAG.getContext());
5365 TargetLowering::ArgListEntry Entry(Op, ArgTy);
5366 Entry.IsSExt = true;
5367 Entry.IsZExt = false;
5368 Args.push_back(Entry);
5369 }
5370
5371 // Also pass the address of the overflow check.
5372 TargetLowering::ArgListEntry Entry(
5373 Temp, PointerType::getUnqual(PtrTy->getContext()));
5374 Entry.IsSExt = true;
5375 Entry.IsZExt = false;
5376 Args.push_back(Entry);
5377
5378 SDValue Func = DAG.getExternalSymbol(LCImpl, PtrVT);
5379
5380 TargetLowering::CallLoweringInfo CLI(DAG);
5381 CLI.setDebugLoc(dl)
5382 .setChain(Chain)
5383 .setLibCallee(DAG.getLibcalls().getLibcallImplCallingConv(LCImpl), RetTy,
5384 Func, std::move(Args))
5385 .setSExtResult();
5386
5387 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
5388
5389 SplitInteger(CallInfo.first, Lo, Hi);
5390 SDValue Temp2 =
5391 DAG.getLoad(PtrVT, dl, CallInfo.second, Temp, MachinePointerInfo());
5392 SDValue Ofl = DAG.getSetCC(dl, N->getValueType(1), Temp2,
5393 DAG.getConstant(0, dl, PtrVT),
5394 ISD::SETNE);
5395 // Use the overflow from the libcall everywhere.
5396 ReplaceValueWith(SDValue(N, 1), Ofl);
5397}
5398
5399void DAGTypeLegalizer::ExpandIntRes_UDIV(SDNode *N,
5400 SDValue &Lo, SDValue &Hi) {
5401 EVT VT = N->getValueType(0);
5402 SDLoc dl(N);
5403 SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
5404
5405 if (TLI.getOperationAction(ISD::UDIVREM, VT) == TargetLowering::Custom) {
5406 SDValue Res = DAG.getNode(ISD::UDIVREM, dl, DAG.getVTList(VT, VT), Ops);
5407 SplitInteger(Res.getValue(0), Lo, Hi);
5408 return;
5409 }
5410
5411 // Try to expand UDIV by constant.
5412 if (isa<ConstantSDNode>(N->getOperand(1))) {
5413 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
5414 // Only if the new type is legal.
5415 if (isTypeLegal(NVT)) {
5416 SDValue InL, InH;
5417 GetExpandedInteger(N->getOperand(0), InL, InH);
5419 if (TLI.expandDIVREMByConstant(N, Result, NVT, DAG, InL, InH)) {
5420 Lo = Result[0];
5421 Hi = Result[1];
5422 return;
5423 }
5424 }
5425 }
5426
5427 RTLIB::Libcall LC = RTLIB::getUDIV(VT);
5428 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported UDIV!");
5429
5430 TargetLowering::MakeLibCallOptions CallOptions;
5431 SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, CallOptions, dl).first, Lo, Hi);
5432}
5433
5434void DAGTypeLegalizer::ExpandIntRes_UREM(SDNode *N,
5435 SDValue &Lo, SDValue &Hi) {
5436 EVT VT = N->getValueType(0);
5437 SDLoc dl(N);
5438 SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
5439
5440 if (TLI.getOperationAction(ISD::UDIVREM, VT) == TargetLowering::Custom) {
5441 SDValue Res = DAG.getNode(ISD::UDIVREM, dl, DAG.getVTList(VT, VT), Ops);
5442 SplitInteger(Res.getValue(1), Lo, Hi);
5443 return;
5444 }
5445
5446 // Try to expand UREM by constant.
5447 if (isa<ConstantSDNode>(N->getOperand(1))) {
5448 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
5449 // Only if the new type is legal.
5450 if (isTypeLegal(NVT)) {
5451 SDValue InL, InH;
5452 GetExpandedInteger(N->getOperand(0), InL, InH);
5454 if (TLI.expandDIVREMByConstant(N, Result, NVT, DAG, InL, InH)) {
5455 Lo = Result[0];
5456 Hi = Result[1];
5457 return;
5458 }
5459 }
5460 }
5461
5462 RTLIB::Libcall LC = RTLIB::getUREM(VT);
5463 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported UREM!");
5464
5465 TargetLowering::MakeLibCallOptions CallOptions;
5466 SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, CallOptions, dl).first, Lo, Hi);
5467}
5468
5469void DAGTypeLegalizer::ExpandIntRes_ZERO_EXTEND(SDNode *N,
5470 SDValue &Lo, SDValue &Hi) {
5471 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
5472 SDLoc dl(N);
5473 SDValue Op = N->getOperand(0);
5474 if (Op.getValueType().bitsLE(NVT)) {
5475 // The low part is zero extension of the input (degenerates to a copy).
5476 Lo = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, N->getOperand(0));
5477 Hi = DAG.getConstant(0, dl, NVT); // The high part is just a zero.
5478 } else {
5479 // For example, extension of an i48 to an i64. The operand type necessarily
5480 // promotes to the result type, so will end up being expanded too.
5481 assert(getTypeAction(Op.getValueType()) ==
5483 "Only know how to promote this result!");
5484 SDValue Res = GetPromotedInteger(Op);
5485 assert(Res.getValueType() == N->getValueType(0) &&
5486 "Operand over promoted?");
5487 // Split the promoted operand. This will simplify when it is expanded.
5488 SplitInteger(Res, Lo, Hi);
5489 unsigned ExcessBits = Op.getValueSizeInBits() - NVT.getSizeInBits();
5490 Hi = DAG.getZeroExtendInReg(Hi, dl,
5491 EVT::getIntegerVT(*DAG.getContext(),
5492 ExcessBits));
5493 }
5494}
5495
5496void DAGTypeLegalizer::ExpandIntRes_ATOMIC_LOAD(SDNode *N,
5497 SDValue &Lo, SDValue &Hi) {
5498 SDLoc dl(N);
5499 EVT VT = cast<AtomicSDNode>(N)->getMemoryVT();
5500 SDVTList VTs = DAG.getVTList(VT, MVT::i1, MVT::Other);
5501 SDValue Zero = DAG.getConstant(0, dl, VT);
5502 SDValue Swap = DAG.getAtomicCmpSwap(
5504 cast<AtomicSDNode>(N)->getMemoryVT(), VTs, N->getOperand(0),
5505 N->getOperand(1), Zero, Zero, cast<AtomicSDNode>(N)->getMemOperand());
5506
5507 ReplaceValueWith(SDValue(N, 0), Swap.getValue(0));
5508 ReplaceValueWith(SDValue(N, 1), Swap.getValue(2));
5509}
5510
5511void DAGTypeLegalizer::ExpandIntRes_VECREDUCE(SDNode *N,
5512 SDValue &Lo, SDValue &Hi) {
5513 // TODO For VECREDUCE_(AND|OR|XOR) we could split the vector and calculate
5514 // both halves independently.
5515 SDValue Res = TLI.expandVecReduce(N, DAG);
5516 SplitInteger(Res, Lo, Hi);
5517}
5518
5519void DAGTypeLegalizer::ExpandIntRes_Rotate(SDNode *N,
5520 SDValue &Lo, SDValue &Hi) {
5521 // Delegate to funnel-shift expansion.
5522 SDLoc DL(N);
5523 unsigned Opcode = N->getOpcode() == ISD::ROTL ? ISD::FSHL : ISD::FSHR;
5524 SDValue Res = DAG.getNode(Opcode, DL, N->getValueType(0), N->getOperand(0),
5525 N->getOperand(0), N->getOperand(1));
5526 SplitInteger(Res, Lo, Hi);
5527}
5528
5529void DAGTypeLegalizer::ExpandIntRes_FunnelShift(SDNode *N, SDValue &Lo,
5530 SDValue &Hi) {
5531 // Values numbered from least significant to most significant.
5532 SDValue In1, In2, In3, In4;
5533 GetExpandedInteger(N->getOperand(0), In3, In4);
5534 GetExpandedInteger(N->getOperand(1), In1, In2);
5535 EVT HalfVT = In1.getValueType();
5536
5537 SDLoc DL(N);
5538 unsigned Opc = N->getOpcode();
5539 SDValue ShAmt = N->getOperand(2);
5540 EVT ShAmtVT = ShAmt.getValueType();
5541 EVT ShAmtCCVT = getSetCCResultType(ShAmtVT);
5542
5543 // If the shift amount is at least half the bitwidth, swap the inputs.
5544 unsigned HalfVTBits = HalfVT.getScalarSizeInBits();
5545 SDValue AndNode = DAG.getNode(ISD::AND, DL, ShAmtVT, ShAmt,
5546 DAG.getConstant(HalfVTBits, DL, ShAmtVT));
5547 SDValue Cond =
5548 DAG.getSetCC(DL, ShAmtCCVT, AndNode, DAG.getConstant(0, DL, ShAmtVT),
5550
5551 // Expand to a pair of funnel shifts.
5552 EVT NewShAmtVT = TLI.getShiftAmountTy(HalfVT, DAG.getDataLayout());
5553 SDValue NewShAmt = DAG.getAnyExtOrTrunc(ShAmt, DL, NewShAmtVT);
5554
5555 SDValue Select1 = DAG.getNode(ISD::SELECT, DL, HalfVT, Cond, In1, In2);
5556 SDValue Select2 = DAG.getNode(ISD::SELECT, DL, HalfVT, Cond, In2, In3);
5557 SDValue Select3 = DAG.getNode(ISD::SELECT, DL, HalfVT, Cond, In3, In4);
5558 Lo = DAG.getNode(Opc, DL, HalfVT, Select2, Select1, NewShAmt);
5559 Hi = DAG.getNode(Opc, DL, HalfVT, Select3, Select2, NewShAmt);
5560}
5561
5562void DAGTypeLegalizer::ExpandIntRes_CLMUL(SDNode *N, SDValue &Lo, SDValue &Hi) {
5563 if (N->getOpcode() != ISD::CLMUL) {
5564 SDValue Res = TLI.expandCLMUL(N, DAG);
5565 return SplitInteger(Res, Lo, Hi);
5566 }
5567
5568 SDValue LL, LH, RL, RH;
5569 GetExpandedInteger(N->getOperand(0), LL, LH);
5570 GetExpandedInteger(N->getOperand(1), RL, RH);
5571 EVT HalfVT = LL.getValueType();
5572 SDLoc DL(N);
5573
5574 // The low bits are a direct CLMUL of the the low bits.
5575 Lo = DAG.getNode(ISD::CLMUL, DL, HalfVT, LL, RL);
5576
5577 // We compute two Hi-Lo cross-products, XOR them, and XOR it with the overflow
5578 // of the CLMUL of the low bits (given by CLMULH of the low bits) to yield the
5579 // final high bits.
5580 SDValue LoH = DAG.getNode(ISD::CLMULH, DL, HalfVT, LL, RL);
5581 SDValue HiLoCross1 = DAG.getNode(ISD::CLMUL, DL, HalfVT, LL, RH);
5582 SDValue HiLoCross2 = DAG.getNode(ISD::CLMUL, DL, HalfVT, LH, RL);
5583 SDValue HiLoCross = DAG.getNode(ISD::XOR, DL, HalfVT, HiLoCross1, HiLoCross2);
5584 Hi = DAG.getNode(ISD::XOR, DL, HalfVT, LoH, HiLoCross);
5585}
5586
5587void DAGTypeLegalizer::ExpandIntRes_PEXT(SDNode *N, SDValue &Lo, SDValue &Hi) {
5588 SDValue Res = TLI.expandPEXT(N, DAG);
5589 SplitInteger(Res, Lo, Hi);
5590}
5591
5592void DAGTypeLegalizer::ExpandIntRes_PDEP(SDNode *N, SDValue &Lo, SDValue &Hi) {
5593 SDValue Res = TLI.expandPDEP(N, DAG);
5594 SplitInteger(Res, Lo, Hi);
5595}
5596
5597void DAGTypeLegalizer::ExpandIntRes_MULH(SDNode *N, SDValue &Lo, SDValue &Hi) {
5598 SDValue Res = TLI.expandMULH(N, DAG);
5599 SplitInteger(Res, Lo, Hi);
5600}
5601
5602void DAGTypeLegalizer::ExpandIntRes_VSCALE(SDNode *N, SDValue &Lo,
5603 SDValue &Hi) {
5604 EVT VT = N->getValueType(0);
5605 EVT HalfVT =
5606 EVT::getIntegerVT(*DAG.getContext(), N->getValueSizeInBits(0) / 2);
5607 SDLoc dl(N);
5608
5609 // We assume VSCALE(1) fits into a legal integer.
5610 APInt One(HalfVT.getSizeInBits(), 1);
5611 SDValue VScaleBase = DAG.getVScale(dl, HalfVT, One);
5612 VScaleBase = DAG.getNode(ISD::ZERO_EXTEND, dl, VT, VScaleBase);
5613 SDValue Res = DAG.getNode(ISD::MUL, dl, VT, VScaleBase, N->getOperand(0));
5614 SplitInteger(Res, Lo, Hi);
5615}
5616
5617void DAGTypeLegalizer::ExpandIntRes_READ_REGISTER(SDNode *N, SDValue &Lo,
5618 SDValue &Hi) {
5619 const Function &Fn = DAG.getMachineFunction().getFunction();
5620 Fn.getContext().diagnose(DiagnosticInfoLegalizationFailure(
5621 "cannot use llvm.read_register with illegal type", Fn, N->getDebugLoc()));
5622 ReplaceValueWith(SDValue(N, 1), N->getOperand(0));
5623 EVT LoVT, HiVT;
5624 std::tie(LoVT, HiVT) = DAG.GetSplitDestVTs(N->getValueType(0));
5625 Lo = DAG.getPOISON(LoVT);
5626 Hi = DAG.getPOISON(HiVT);
5627}
5628
5629void DAGTypeLegalizer::ExpandIntRes_CTTZ_ELTS(SDNode *N, SDValue &Lo,
5630 SDValue &Hi) {
5631 // Assume that the maximum number of vector elements fits in getVectorIdxTy
5632 // and expand to that.
5633 EVT VT = N->getSimpleValueType(0);
5634 EVT IdxVT = TLI.getVectorIdxTy(DAG.getDataLayout());
5635 assert(IdxVT.bitsLT(VT) &&
5636 "VectorIdxTy should be smaller than type to be expanded?");
5637
5638 SDValue Res = DAG.getNode(N->getOpcode(), SDLoc(N), IdxVT, N->getOperand(0));
5639 Res = DAG.getNode(ISD::ZERO_EXTEND, SDLoc(N), VT, Res);
5640 SplitInteger(Res, Lo, Hi);
5641}
5642
5643//===----------------------------------------------------------------------===//
5644// Integer Operand Expansion
5645//===----------------------------------------------------------------------===//
5646
5647/// ExpandIntegerOperand - This method is called when the specified operand of
5648/// the specified node is found to need expansion. At this point, all of the
5649/// result types of the node are known to be legal, but other operands of the
5650/// node may need promotion or expansion as well as the specified one.
5651bool DAGTypeLegalizer::ExpandIntegerOperand(SDNode *N, unsigned OpNo) {
5652 LLVM_DEBUG(dbgs() << "Expand integer operand: "; N->dump(&DAG));
5653 SDValue Res = SDValue();
5654
5655 if (CustomLowerNode(N, N->getOperand(OpNo).getValueType(), false))
5656 return false;
5657
5658 switch (N->getOpcode()) {
5659 default:
5660 #ifndef NDEBUG
5661 dbgs() << "ExpandIntegerOperand Op #" << OpNo << ": ";
5662 N->dump(&DAG); dbgs() << "\n";
5663 #endif
5664 report_fatal_error("do not know how to expand this operator's operand!");
5665
5666 case ISD::BITCAST: Res = ExpandOp_BITCAST(N); break;
5667 case ISD::BR_CC: Res = ExpandIntOp_BR_CC(N); break;
5668 case ISD::BUILD_VECTOR: Res = ExpandOp_BUILD_VECTOR(N); break;
5669 case ISD::EXTRACT_ELEMENT: Res = ExpandOp_EXTRACT_ELEMENT(N); break;
5670 case ISD::FAKE_USE:
5671 Res = ExpandOp_FAKE_USE(N);
5672 break;
5675 Res = TLI.expandLoopDependenceMask(N, DAG);
5676 break;
5677 case ISD::INSERT_VECTOR_ELT: Res = ExpandOp_INSERT_VECTOR_ELT(N); break;
5678 case ISD::SCALAR_TO_VECTOR: Res = ExpandOp_SCALAR_TO_VECTOR(N); break;
5679 case ISD::SPLAT_VECTOR: Res = ExpandIntOp_SPLAT_VECTOR(N); break;
5680 case ISD::SELECT_CC: Res = ExpandIntOp_SELECT_CC(N); break;
5681 case ISD::SETCC: Res = ExpandIntOp_SETCC(N); break;
5682 case ISD::SETCCCARRY: Res = ExpandIntOp_SETCCCARRY(N); break;
5684 case ISD::SINT_TO_FP:
5686 case ISD::UINT_TO_FP: Res = ExpandIntOp_XINT_TO_FP(N); break;
5687 case ISD::STORE: Res = ExpandIntOp_STORE(cast<StoreSDNode>(N), OpNo); break;
5688 case ISD::TRUNCATE: Res = ExpandIntOp_TRUNCATE(N); break;
5689
5690 case ISD::SHL:
5691 case ISD::SRA:
5692 case ISD::SRL:
5693 case ISD::ROTL:
5694 case ISD::ROTR: Res = ExpandIntOp_Shift(N); break;
5695 case ISD::RETURNADDR:
5696 case ISD::FRAMEADDR: Res = ExpandIntOp_RETURNADDR(N); break;
5697
5698 case ISD::SCMP:
5699 case ISD::UCMP: Res = ExpandIntOp_CMP(N); break;
5700
5701 case ISD::ATOMIC_STORE: Res = ExpandIntOp_ATOMIC_STORE(N); break;
5702 case ISD::STACKMAP:
5703 Res = ExpandIntOp_STACKMAP(N, OpNo);
5704 break;
5705 case ISD::PATCHPOINT:
5706 Res = ExpandIntOp_PATCHPOINT(N, OpNo);
5707 break;
5708 case ISD::EXPERIMENTAL_VP_STRIDED_LOAD:
5709 case ISD::EXPERIMENTAL_VP_STRIDED_STORE:
5710 Res = ExpandIntOp_VP_STRIDED(N, OpNo);
5711 break;
5713 Res = ExpandIntOp_WRITE_REGISTER(N, OpNo);
5714 break;
5715 }
5716
5717 // If the result is null, the sub-method took care of registering results etc.
5718 if (!Res.getNode()) return false;
5719
5720 // If the result is N, the sub-method updated N in place. Tell the legalizer
5721 // core about this.
5722 if (Res.getNode() == N)
5723 return true;
5724
5725 assert(Res.getValueType() == N->getValueType(0) && N->getNumValues() == 1 &&
5726 "Invalid operand expansion");
5727
5728 ReplaceValueWith(SDValue(N, 0), Res);
5729 return false;
5730}
5731
5732/// IntegerExpandSetCCOperands - Expand the operands of a comparison. This code
5733/// is shared among BR_CC, SELECT_CC, and SETCC handlers.
5734void DAGTypeLegalizer::IntegerExpandSetCCOperands(SDValue &NewLHS,
5735 SDValue &NewRHS,
5736 ISD::CondCode &CCCode,
5737 const SDLoc &dl) {
5738 SDValue LHSLo, LHSHi, RHSLo, RHSHi;
5739 GetExpandedInteger(NewLHS, LHSLo, LHSHi);
5740 GetExpandedInteger(NewRHS, RHSLo, RHSHi);
5741
5742 if (CCCode == ISD::SETEQ || CCCode == ISD::SETNE) {
5743 if (RHSLo == RHSHi && isAllOnesConstant(RHSLo)) {
5744 // Equality comparison to -1.
5745 NewLHS = DAG.getNode(ISD::AND, dl, LHSLo.getValueType(), LHSLo, LHSHi);
5746 NewRHS = RHSLo;
5747 return;
5748 }
5749
5750 NewLHS = DAG.getNode(ISD::XOR, dl, LHSLo.getValueType(), LHSLo, RHSLo);
5751 NewRHS = DAG.getNode(ISD::XOR, dl, LHSLo.getValueType(), LHSHi, RHSHi);
5752 NewLHS = DAG.getNode(ISD::OR, dl, NewLHS.getValueType(), NewLHS, NewRHS);
5753 NewRHS = DAG.getConstant(0, dl, NewLHS.getValueType());
5754 return;
5755 }
5756
5757 // If this is a comparison of the sign bit, just look at the top part.
5758 // X > -1, x < 0
5759 if (ConstantSDNode *CST = dyn_cast<ConstantSDNode>(NewRHS))
5760 if ((CCCode == ISD::SETLT && CST->isZero()) || // X < 0
5761 (CCCode == ISD::SETGT && CST->isAllOnes())) { // X > -1
5762 NewLHS = LHSHi;
5763 NewRHS = RHSHi;
5764 return;
5765 }
5766
5767 // FIXME: This generated code sucks.
5768 ISD::CondCode LowCC;
5769 switch (CCCode) {
5770 default: llvm_unreachable("Unknown integer setcc!");
5771 case ISD::SETLT:
5772 case ISD::SETULT: LowCC = ISD::SETULT; break;
5773 case ISD::SETGT:
5774 case ISD::SETUGT: LowCC = ISD::SETUGT; break;
5775 case ISD::SETLE:
5776 case ISD::SETULE: LowCC = ISD::SETULE; break;
5777 case ISD::SETGE:
5778 case ISD::SETUGE: LowCC = ISD::SETUGE; break;
5779 }
5780
5781 // LoCmp = lo(op1) < lo(op2) // Always unsigned comparison
5782 // HiCmp = hi(op1) < hi(op2) // Signedness depends on operands
5783 // dest = hi(op1) == hi(op2) ? LoCmp : HiCmp;
5784
5785 // NOTE: on targets without efficient SELECT of bools, we can always use
5786 // this identity: (B1 ? B2 : B3) --> (B1 & B2)|(!B1&B3)
5787 TargetLowering::DAGCombinerInfo DagCombineInfo(DAG, AfterLegalizeTypes, true,
5788 nullptr);
5789 SDValue LoCmp, HiCmp;
5790 if (TLI.isTypeLegal(LHSLo.getValueType()))
5791 LoCmp = TLI.SimplifySetCC(getSetCCResultType(LHSLo.getValueType()), LHSLo,
5792 RHSLo, LowCC, false, DagCombineInfo, dl);
5793 if (!LoCmp.getNode())
5794 LoCmp = DAG.getSetCC(dl, getSetCCResultType(LHSLo.getValueType()), LHSLo,
5795 RHSLo, LowCC);
5796 if (TLI.isTypeLegal(LHSHi.getValueType()))
5797 HiCmp = TLI.SimplifySetCC(getSetCCResultType(LHSHi.getValueType()), LHSHi,
5798 RHSHi, CCCode, false, DagCombineInfo, dl);
5799 if (!HiCmp.getNode())
5800 HiCmp =
5801 DAG.getNode(ISD::SETCC, dl, getSetCCResultType(LHSHi.getValueType()),
5802 LHSHi, RHSHi, DAG.getCondCode(CCCode));
5803
5804 ConstantSDNode *LoCmpC = dyn_cast<ConstantSDNode>(LoCmp.getNode());
5805 ConstantSDNode *HiCmpC = dyn_cast<ConstantSDNode>(HiCmp.getNode());
5806
5807 bool EqAllowed = ISD::isTrueWhenEqual(CCCode);
5808
5809 // FIXME: Is the HiCmpC->isOne() here correct for
5810 // ZeroOrNegativeOneBooleanContent.
5811 if ((EqAllowed && (HiCmpC && HiCmpC->isZero())) ||
5812 (!EqAllowed &&
5813 ((HiCmpC && HiCmpC->isOne()) || (LoCmpC && LoCmpC->isZero())))) {
5814 // For LE / GE, if high part is known false, ignore the low part.
5815 // For LT / GT: if low part is known false, return the high part.
5816 // if high part is known true, ignore the low part.
5817 NewLHS = HiCmp;
5818 NewRHS = SDValue();
5819 return;
5820 }
5821
5822 if (LHSHi == RHSHi) {
5823 // Comparing the low bits is enough.
5824 NewLHS = LoCmp;
5825 NewRHS = SDValue();
5826 return;
5827 }
5828
5829 // Lower with SETCCCARRY if the target supports it.
5830 EVT HiVT = LHSHi.getValueType();
5831 EVT ExpandVT = TLI.getTypeToExpandTo(*DAG.getContext(), HiVT);
5832 bool HasSETCCCARRY = TLI.isOperationLegalOrCustom(ISD::SETCCCARRY, ExpandVT);
5833
5834 // FIXME: Make all targets support this, then remove the other lowering.
5835 if (HasSETCCCARRY) {
5836 // SETCCCARRY can detect < and >= directly. For > and <=, flip
5837 // operands and condition code.
5838 bool FlipOperands = false;
5839 switch (CCCode) {
5840 case ISD::SETGT: CCCode = ISD::SETLT; FlipOperands = true; break;
5841 case ISD::SETUGT: CCCode = ISD::SETULT; FlipOperands = true; break;
5842 case ISD::SETLE: CCCode = ISD::SETGE; FlipOperands = true; break;
5843 case ISD::SETULE: CCCode = ISD::SETUGE; FlipOperands = true; break;
5844 default: break;
5845 }
5846 if (FlipOperands) {
5847 std::swap(LHSLo, RHSLo);
5848 std::swap(LHSHi, RHSHi);
5849 }
5850 // Perform a wide subtraction, feeding the carry from the low part into
5851 // SETCCCARRY. The SETCCCARRY operation is essentially looking at the high
5852 // part of the result of LHS - RHS. It is negative iff LHS < RHS. It is
5853 // zero or positive iff LHS >= RHS.
5854 EVT LoVT = LHSLo.getValueType();
5855 SDVTList VTList = DAG.getVTList(LoVT, getSetCCResultType(LoVT));
5856 SDValue LowCmp = DAG.getNode(ISD::USUBO, dl, VTList, LHSLo, RHSLo);
5857 SDValue Res = DAG.getNode(ISD::SETCCCARRY, dl, getSetCCResultType(HiVT),
5858 LHSHi, RHSHi, LowCmp.getValue(1),
5859 DAG.getCondCode(CCCode));
5860 NewLHS = Res;
5861 NewRHS = SDValue();
5862 return;
5863 }
5864
5865 NewLHS = TLI.SimplifySetCC(getSetCCResultType(HiVT), LHSHi, RHSHi, ISD::SETEQ,
5866 false, DagCombineInfo, dl);
5867 if (!NewLHS.getNode())
5868 NewLHS =
5869 DAG.getSetCC(dl, getSetCCResultType(HiVT), LHSHi, RHSHi, ISD::SETEQ);
5870 NewLHS = DAG.getSelect(dl, LoCmp.getValueType(), NewLHS, LoCmp, HiCmp);
5871 NewRHS = SDValue();
5872}
5873
5874SDValue DAGTypeLegalizer::ExpandIntOp_BR_CC(SDNode *N) {
5875 SDValue NewLHS = N->getOperand(2), NewRHS = N->getOperand(3);
5876 ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(1))->get();
5877 IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
5878
5879 // If ExpandSetCCOperands returned a scalar, we need to compare the result
5880 // against zero to select between true and false values.
5881 if (!NewRHS.getNode()) {
5882 NewRHS = DAG.getConstant(0, SDLoc(N), NewLHS.getValueType());
5883 CCCode = ISD::SETNE;
5884 }
5885
5886 // Update N to have the operands specified.
5887 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
5888 DAG.getCondCode(CCCode), NewLHS, NewRHS,
5889 N->getOperand(4)), 0);
5890}
5891
5892SDValue DAGTypeLegalizer::ExpandIntOp_SELECT_CC(SDNode *N) {
5893 SDValue NewLHS = N->getOperand(0), NewRHS = N->getOperand(1);
5894 ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(4))->get();
5895 IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
5896
5897 // If ExpandSetCCOperands returned a scalar, we need to compare the result
5898 // against zero to select between true and false values.
5899 if (!NewRHS.getNode()) {
5900 NewRHS = DAG.getConstant(0, SDLoc(N), NewLHS.getValueType());
5901 CCCode = ISD::SETNE;
5902 }
5903
5904 // Update N to have the operands specified.
5905 return SDValue(DAG.UpdateNodeOperands(N, NewLHS, NewRHS,
5906 N->getOperand(2), N->getOperand(3),
5907 DAG.getCondCode(CCCode)), 0);
5908}
5909
5910SDValue DAGTypeLegalizer::ExpandIntOp_SETCC(SDNode *N) {
5911 SDValue NewLHS = N->getOperand(0), NewRHS = N->getOperand(1);
5912 ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(2))->get();
5913 IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
5914
5915 // If ExpandSetCCOperands returned a scalar, use it.
5916 if (!NewRHS.getNode()) {
5917 assert(NewLHS.getValueType() == N->getValueType(0) &&
5918 "Unexpected setcc expansion!");
5919 return NewLHS;
5920 }
5921
5922 // Otherwise, update N to have the operands specified.
5923 return SDValue(
5924 DAG.UpdateNodeOperands(N, NewLHS, NewRHS, DAG.getCondCode(CCCode)), 0);
5925}
5926
5927SDValue DAGTypeLegalizer::ExpandIntOp_SETCCCARRY(SDNode *N) {
5928 SDValue LHS = N->getOperand(0);
5929 SDValue RHS = N->getOperand(1);
5930 SDValue Carry = N->getOperand(2);
5931 SDValue Cond = N->getOperand(3);
5932 SDLoc dl = SDLoc(N);
5933
5934 SDValue LHSLo, LHSHi, RHSLo, RHSHi;
5935 GetExpandedInteger(LHS, LHSLo, LHSHi);
5936 GetExpandedInteger(RHS, RHSLo, RHSHi);
5937
5938 // Expand to a USUBO_CARRY for the low part and a SETCCCARRY for the high.
5939 SDVTList VTList = DAG.getVTList(LHSLo.getValueType(), Carry.getValueType());
5940 SDValue LowCmp =
5941 DAG.getNode(ISD::USUBO_CARRY, dl, VTList, LHSLo, RHSLo, Carry);
5942 return DAG.getNode(ISD::SETCCCARRY, dl, N->getValueType(0), LHSHi, RHSHi,
5943 LowCmp.getValue(1), Cond);
5944}
5945
5946SDValue DAGTypeLegalizer::ExpandIntOp_SPLAT_VECTOR(SDNode *N) {
5947 // Split the operand and replace with SPLAT_VECTOR_PARTS.
5948 SDValue Lo, Hi;
5949 GetExpandedInteger(N->getOperand(0), Lo, Hi);
5950 return DAG.getNode(ISD::SPLAT_VECTOR_PARTS, SDLoc(N), N->getValueType(0), Lo,
5951 Hi);
5952}
5953
5954SDValue DAGTypeLegalizer::ExpandIntOp_Shift(SDNode *N) {
5955 // The value being shifted is legal, but the shift amount is too big.
5956 // It follows that either the result of the shift is undefined, or the
5957 // upper half of the shift amount is zero. Just use the lower half.
5958 SDValue Lo, Hi;
5959 GetExpandedInteger(N->getOperand(1), Lo, Hi);
5960 return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Lo), 0);
5961}
5962
5963SDValue DAGTypeLegalizer::ExpandIntOp_CMP(SDNode *N) {
5964 return TLI.expandCMP(N, DAG);
5965}
5966
5967SDValue DAGTypeLegalizer::ExpandIntOp_RETURNADDR(SDNode *N) {
5968 // The argument of RETURNADDR / FRAMEADDR builtin is 32 bit contant. This
5969 // surely makes pretty nice problems on 8/16 bit targets. Just truncate this
5970 // constant to valid type.
5971 SDValue Lo, Hi;
5972 GetExpandedInteger(N->getOperand(0), Lo, Hi);
5973 return SDValue(DAG.UpdateNodeOperands(N, Lo), 0);
5974}
5975
5976SDValue DAGTypeLegalizer::ExpandIntOp_XINT_TO_FP(SDNode *N) {
5977 bool IsStrict = N->isStrictFPOpcode();
5978 bool IsSigned = N->getOpcode() == ISD::SINT_TO_FP ||
5979 N->getOpcode() == ISD::STRICT_SINT_TO_FP;
5980 SDValue Chain = IsStrict ? N->getOperand(0) : SDValue();
5981 SDValue Op = N->getOperand(IsStrict ? 1 : 0);
5982 EVT DstVT = N->getValueType(0);
5983 RTLIB::Libcall LC = IsSigned ? RTLIB::getSINTTOFP(Op.getValueType(), DstVT)
5984 : RTLIB::getUINTTOFP(Op.getValueType(), DstVT);
5985 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
5986 "Don't know how to expand this XINT_TO_FP!");
5987 TargetLowering::MakeLibCallOptions CallOptions;
5988 CallOptions.setIsSigned(true);
5989 std::pair<SDValue, SDValue> Tmp =
5990 TLI.makeLibCall(DAG, LC, DstVT, Op, CallOptions, SDLoc(N), Chain);
5991
5992 if (!IsStrict)
5993 return Tmp.first;
5994
5995 ReplaceValueWith(SDValue(N, 1), Tmp.second);
5996 ReplaceValueWith(SDValue(N, 0), Tmp.first);
5997 return SDValue();
5998}
5999
6000SDValue DAGTypeLegalizer::ExpandIntOp_STORE(StoreSDNode *N, unsigned OpNo) {
6001 assert(!N->isAtomic() && "Should have been a ATOMIC_STORE?");
6002
6003 if (ISD::isNormalStore(N))
6004 return ExpandOp_NormalStore(N, OpNo);
6005
6006 assert(ISD::isUNINDEXEDStore(N) && "Indexed store during type legalization!");
6007 assert(OpNo == 1 && "Can only expand the stored value so far");
6008
6009 EVT VT = N->getOperand(1).getValueType();
6010 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6011 SDValue Ch = N->getChain();
6012 SDValue Ptr = N->getBasePtr();
6013 MachineMemOperand::Flags MMOFlags = N->getMemOperand()->getFlags();
6014 MMOMetadata Metadata = N->getMMOMetadataForSubAccess();
6015 SDLoc dl(N);
6016 SDValue Lo, Hi;
6017
6018 assert(NVT.isByteSized() && "Expanded type not byte sized!");
6019
6020 if (N->getMemoryVT().bitsLE(NVT)) {
6021 GetExpandedInteger(N->getValue(), Lo, Hi);
6022 return DAG.getTruncStore(Ch, dl, Lo, Ptr, N->getPointerInfo(),
6023 N->getMemoryVT(), N->getBaseAlign(), MMOFlags,
6024 Metadata);
6025 }
6026
6027 if (DAG.getDataLayout().isLittleEndian()) {
6028 // Little-endian - low bits are at low addresses.
6029 GetExpandedInteger(N->getValue(), Lo, Hi);
6030
6031 Lo = DAG.getStore(Ch, dl, Lo, Ptr, N->getPointerInfo(), N->getBaseAlign(),
6032 MMOFlags, Metadata);
6033
6034 unsigned ExcessBits =
6035 N->getMemoryVT().getSizeInBits() - NVT.getSizeInBits();
6036 EVT NEVT = EVT::getIntegerVT(*DAG.getContext(), ExcessBits);
6037
6038 // Increment the pointer to the other half.
6039 unsigned IncrementSize = NVT.getSizeInBits()/8;
6040 Ptr = DAG.getObjectPtrOffset(dl, Ptr, TypeSize::getFixed(IncrementSize));
6041 Hi = DAG.getTruncStore(Ch, dl, Hi, Ptr,
6042 N->getPointerInfo().getWithOffset(IncrementSize),
6043 NEVT, N->getBaseAlign(), MMOFlags, Metadata);
6044 return DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
6045 }
6046
6047 // Big-endian - high bits are at low addresses. Favor aligned stores at
6048 // the cost of some bit-fiddling.
6049 GetExpandedInteger(N->getValue(), Lo, Hi);
6050
6051 EVT ExtVT = N->getMemoryVT();
6052 unsigned EBytes = ExtVT.getStoreSize();
6053 unsigned IncrementSize = NVT.getSizeInBits()/8;
6054 unsigned ExcessBits = (EBytes - IncrementSize)*8;
6055 EVT HiVT = EVT::getIntegerVT(*DAG.getContext(),
6056 ExtVT.getSizeInBits() - ExcessBits);
6057
6058 if (ExcessBits < NVT.getSizeInBits()) {
6059 // Transfer high bits from the top of Lo to the bottom of Hi.
6060 Hi = DAG.getNode(
6061 ISD::SHL, dl, NVT, Hi,
6062 DAG.getShiftAmountConstant(NVT.getSizeInBits() - ExcessBits, NVT, dl));
6063 Hi = DAG.getNode(
6064 ISD::OR, dl, NVT, Hi,
6065 DAG.getNode(ISD::SRL, dl, NVT, Lo,
6066 DAG.getShiftAmountConstant(ExcessBits, NVT, dl)));
6067 }
6068
6069 // Store both the high bits and maybe some of the low bits.
6070 Hi = DAG.getTruncStore(Ch, dl, Hi, Ptr, N->getPointerInfo(), HiVT,
6071 N->getBaseAlign(), MMOFlags, Metadata);
6072
6073 // Increment the pointer to the other half.
6074 Ptr = DAG.getObjectPtrOffset(dl, Ptr, TypeSize::getFixed(IncrementSize));
6075 // Store the lowest ExcessBits bits in the second half.
6076 Lo = DAG.getTruncStore(Ch, dl, Lo, Ptr,
6077 N->getPointerInfo().getWithOffset(IncrementSize),
6078 EVT::getIntegerVT(*DAG.getContext(), ExcessBits),
6079 N->getBaseAlign(), MMOFlags, Metadata);
6080 return DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
6081}
6082
6083SDValue DAGTypeLegalizer::ExpandIntOp_TRUNCATE(SDNode *N) {
6084 SDValue InL, InH;
6085 GetExpandedInteger(N->getOperand(0), InL, InH);
6086 // Just truncate the low part of the source.
6087 return DAG.getNode(ISD::TRUNCATE, SDLoc(N), N->getValueType(0), InL);
6088}
6089
6090SDValue DAGTypeLegalizer::ExpandIntOp_ATOMIC_STORE(SDNode *N) {
6091 SDLoc dl(N);
6092 SDValue Swap =
6093 DAG.getAtomic(ISD::ATOMIC_SWAP, dl, cast<AtomicSDNode>(N)->getMemoryVT(),
6094 N->getOperand(0), N->getOperand(2), N->getOperand(1),
6095 cast<AtomicSDNode>(N)->getMemOperand());
6096 return Swap.getValue(1);
6097}
6098
6099SDValue DAGTypeLegalizer::ExpandIntOp_VP_STRIDED(SDNode *N, unsigned OpNo) {
6100 assert((N->getOpcode() == ISD::EXPERIMENTAL_VP_STRIDED_LOAD && OpNo == 3) ||
6101 (N->getOpcode() == ISD::EXPERIMENTAL_VP_STRIDED_STORE && OpNo == 4));
6102
6103 SDValue Hi; // The upper half is dropped out.
6104 SmallVector<SDValue, 8> NewOps(N->ops());
6105 GetExpandedInteger(NewOps[OpNo], NewOps[OpNo], Hi);
6106
6107 return SDValue(DAG.UpdateNodeOperands(N, NewOps), 0);
6108}
6109
6110SDValue DAGTypeLegalizer::ExpandIntOp_WRITE_REGISTER(SDNode *N, unsigned OpNo) {
6111 const Function &Fn = DAG.getMachineFunction().getFunction();
6112 Fn.getContext().diagnose(DiagnosticInfoLegalizationFailure(
6113 "cannot use llvm.write_register with illegal type", Fn,
6114 N->getDebugLoc()));
6115
6116 return N->getOperand(0);
6117}
6118
6119SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_SPLICE(SDNode *N) {
6120 SDLoc dl(N);
6121
6122 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6123 SDValue V1 = GetPromotedInteger(N->getOperand(1));
6124 EVT OutVT = V0.getValueType();
6125
6126 return DAG.getNode(N->getOpcode(), dl, OutVT, V0, V1, N->getOperand(2));
6127}
6128
6129SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_REPEAT(SDNode *N) {
6130 SDLoc DL(N);
6131
6132 EVT OutVT = N->getValueType(0);
6133 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6134 EVT NInVT = N->getOperand(0).getValueType().changeVectorElementType(
6135 *DAG.getContext(), NOutVT.getVectorElementType());
6136
6137 SDValue Op = DAG.getNode(ISD::ANY_EXTEND, DL, NInVT, N->getOperand(0));
6138 return DAG.getNode(N->getOpcode(), DL, NOutVT, Op);
6139}
6140
6141SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_INTERLEAVE_DEINTERLEAVE(SDNode *N) {
6142 SDLoc DL(N);
6143 unsigned Factor = N->getNumOperands();
6144
6146 for (unsigned i = 0; i != Factor; i++)
6147 Ops[i] = GetPromotedInteger(N->getOperand(i));
6148
6149 SmallVector<EVT, 8> ResVTs(Factor, Ops[0].getValueType());
6150 SDValue Res = DAG.getNode(N->getOpcode(), DL, DAG.getVTList(ResVTs), Ops);
6151
6152 for (unsigned i = 0; i != Factor; i++)
6153 SetPromotedInteger(SDValue(N, i), Res.getValue(i));
6154
6155 return SDValue();
6156}
6157
6158SDValue DAGTypeLegalizer::PromoteIntRes_EXTRACT_SUBVECTOR(SDNode *N) {
6159
6160 EVT OutVT = N->getValueType(0);
6161 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6162 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6163 EVT NOutVTElem = NOutVT.getVectorElementType();
6164
6165 SDLoc dl(N);
6166 SDValue BaseIdx = N->getOperand(1);
6167
6168 // TODO: We may be able to use this for types other than scalable
6169 // vectors and fix those tests that expect BUILD_VECTOR to be used
6170 if (OutVT.isScalableVector()) {
6171 SDValue InOp0 = N->getOperand(0);
6172 EVT InVT = InOp0.getValueType();
6173
6174 // Try and extract from a smaller type so that it eventually falls
6175 // into the promotion code below.
6176 if (getTypeAction(InVT) == TargetLowering::TypeSplitVector ||
6177 getTypeAction(InVT) == TargetLowering::TypeLegal) {
6178 EVT NInVT = InVT.getHalfNumVectorElementsVT(*DAG.getContext());
6179 unsigned NElts = NInVT.getVectorMinNumElements();
6180 uint64_t IdxVal = BaseIdx->getAsZExtVal();
6181
6182 SDValue Step1 = DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, NInVT, InOp0,
6183 DAG.getConstant(alignDown(IdxVal, NElts), dl,
6184 BaseIdx.getValueType()));
6185 SDValue Step2 = DAG.getNode(
6186 ISD::EXTRACT_SUBVECTOR, dl, OutVT, Step1,
6187 DAG.getConstant(IdxVal % NElts, dl, BaseIdx.getValueType()));
6188 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, Step2);
6189 }
6190
6191 // Try and extract from a widened type.
6192 if (getTypeAction(InVT) == TargetLowering::TypeWidenVector) {
6193 SDValue Ops[] = {GetWidenedVector(InOp0), BaseIdx};
6194 SDValue Ext = DAG.getNode(ISD::EXTRACT_SUBVECTOR, SDLoc(N), OutVT, Ops);
6195 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, Ext);
6196 }
6197
6198 // Promote operands and see if this is handled by target lowering,
6199 // Otherwise, use the BUILD_VECTOR approach below
6200 if (getTypeAction(InVT) == TargetLowering::TypePromoteInteger) {
6201 // Collect the (promoted) operands
6202 SDValue Ops[] = { GetPromotedInteger(InOp0), BaseIdx };
6203
6204 EVT PromEltVT = Ops[0].getValueType().getVectorElementType();
6205 assert(PromEltVT.bitsLE(NOutVTElem) &&
6206 "Promoted operand has an element type greater than result");
6207
6208 EVT ExtVT = NOutVT.changeVectorElementType(*DAG.getContext(), PromEltVT);
6209 SDValue Ext = DAG.getNode(ISD::EXTRACT_SUBVECTOR, SDLoc(N), ExtVT, Ops);
6210 return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, Ext);
6211 }
6212 }
6213
6214 if (OutVT.isScalableVector())
6215 report_fatal_error("Unable to promote scalable types using BUILD_VECTOR");
6216
6217 SDValue InOp0 = N->getOperand(0);
6218 if (getTypeAction(InOp0.getValueType()) == TargetLowering::TypePromoteInteger)
6219 InOp0 = GetPromotedInteger(InOp0);
6220
6221 EVT InVT = InOp0.getValueType();
6222 EVT InSVT = InVT.getVectorElementType();
6223
6224 unsigned OutNumElems = OutVT.getVectorNumElements();
6226 Ops.reserve(OutNumElems);
6227 for (unsigned i = 0; i != OutNumElems; ++i) {
6228 // Extract the element from the original vector.
6229 SDValue Index = DAG.getNode(ISD::ADD, dl, BaseIdx.getValueType(), BaseIdx,
6230 DAG.getConstant(i, dl, BaseIdx.getValueType()));
6231 SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, InSVT,
6232 N->getOperand(0), Index);
6233 SDValue Op = DAG.getAnyExtOrTrunc(Ext, dl, NOutVTElem);
6234 // Insert the converted element to the new vector.
6235 Ops.push_back(Op);
6236 }
6237
6238 return DAG.getBuildVector(NOutVT, dl, Ops);
6239}
6240
6241SDValue DAGTypeLegalizer::PromoteIntRes_INSERT_SUBVECTOR(SDNode *N) {
6242 EVT OutVT = N->getValueType(0);
6243 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6244 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6245
6246 SDLoc dl(N);
6247 SDValue Vec = N->getOperand(0);
6248 SDValue SubVec = N->getOperand(1);
6249 SDValue Idx = N->getOperand(2);
6250
6251 EVT SubVecVT = SubVec.getValueType();
6252 EVT NSubVT =
6253 EVT::getVectorVT(*DAG.getContext(), NOutVT.getVectorElementType(),
6254 SubVecVT.getVectorElementCount());
6255
6256 Vec = GetPromotedInteger(Vec);
6257 SubVec = DAG.getNode(ISD::ANY_EXTEND, dl, NSubVT, SubVec);
6258
6259 return DAG.getNode(ISD::INSERT_SUBVECTOR, dl, NOutVT, Vec, SubVec, Idx);
6260}
6261
6262SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_REVERSE(SDNode *N) {
6263 SDLoc dl(N);
6264
6265 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6266 EVT OutVT = V0.getValueType();
6267
6268 return DAG.getNode(ISD::VECTOR_REVERSE, dl, OutVT, V0);
6269}
6270
6271SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_SHUFFLE(SDNode *N) {
6272 ShuffleVectorSDNode *SV = cast<ShuffleVectorSDNode>(N);
6273 EVT VT = N->getValueType(0);
6274 SDLoc dl(N);
6275
6276 ArrayRef<int> NewMask = SV->getMask().slice(0, VT.getVectorNumElements());
6277
6278 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6279 SDValue V1 = GetPromotedInteger(N->getOperand(1));
6280 EVT OutVT = V0.getValueType();
6281
6282 return DAG.getVectorShuffle(OutVT, dl, V0, V1, NewMask);
6283}
6284
6285SDValue DAGTypeLegalizer::PromoteIntRes_BUILD_VECTOR(SDNode *N) {
6286 EVT OutVT = N->getValueType(0);
6287 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6288 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6289 unsigned NumElems = N->getNumOperands();
6290 EVT NOutVTElem = NOutVT.getVectorElementType();
6291 TargetLoweringBase::BooleanContent NOutBoolType = TLI.getBooleanContents(NOutVT);
6292 unsigned NOutExtOpc = TargetLowering::getExtendForContent(NOutBoolType);
6293 SDLoc dl(N);
6294
6296 Ops.reserve(NumElems);
6297 for (unsigned i = 0; i != NumElems; ++i) {
6298 SDValue Op = N->getOperand(i);
6299 EVT OpVT = Op.getValueType();
6300 // BUILD_VECTOR integer operand types are allowed to be larger than the
6301 // result's element type. This may still be true after the promotion. For
6302 // example, we might be promoting (<v?i1> = BV <i32>, <i32>, ...) to
6303 // (v?i16 = BV <i32>, <i32>, ...), and we can't any_extend <i32> to <i16>.
6304 if (OpVT.bitsLT(NOutVTElem)) {
6305 unsigned ExtOpc = ISD::ANY_EXTEND;
6306 // Attempt to extend constant bool vectors to match target's BooleanContent.
6307 // While not necessary, this improves chances of the constant correctly
6308 // folding with compare results (e.g. for NOT patterns).
6309 if (OpVT == MVT::i1 && Op.getOpcode() == ISD::Constant)
6310 ExtOpc = NOutExtOpc;
6311 Op = DAG.getNode(ExtOpc, dl, NOutVTElem, Op);
6312 }
6313 Ops.push_back(Op);
6314 }
6315
6316 return DAG.getBuildVector(NOutVT, dl, Ops);
6317}
6318
6319SDValue DAGTypeLegalizer::PromoteIntRes_ScalarOp(SDNode *N) {
6320
6321 SDLoc dl(N);
6322
6323 assert(!N->getOperand(0).getValueType().isVector() &&
6324 "Input must be a scalar");
6325
6326 EVT OutVT = N->getValueType(0);
6327 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6328 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6329 EVT NOutElemVT = NOutVT.getVectorElementType();
6330
6331 SDValue Op = DAG.getNode(ISD::ANY_EXTEND, dl, NOutElemVT, N->getOperand(0));
6332 return DAG.getNode(N->getOpcode(), dl, NOutVT, Op);
6333}
6334
6335SDValue DAGTypeLegalizer::PromoteIntRes_STEP_VECTOR(SDNode *N) {
6336 SDLoc dl(N);
6337 EVT OutVT = N->getValueType(0);
6338 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6339 assert(NOutVT.isScalableVector() &&
6340 "Type must be promoted to a scalable vector type");
6341 const APInt &StepVal = N->getConstantOperandAPInt(0);
6342 return DAG.getStepVector(dl, NOutVT,
6343 StepVal.sext(NOutVT.getScalarSizeInBits()));
6344}
6345
6346SDValue DAGTypeLegalizer::PromoteIntRes_CONCAT_VECTORS(SDNode *N) {
6347 SDLoc dl(N);
6348
6349 EVT OutVT = N->getValueType(0);
6350 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6351 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6352
6353 unsigned NumOperands = N->getNumOperands();
6354 unsigned NumOutElem = NOutVT.getVectorMinNumElements();
6355 EVT OutElemTy = NOutVT.getVectorElementType();
6356 if (OutVT.isScalableVector()) {
6357 EVT OpVT = N->getOperand(0).getValueType();
6358 TargetLowering::LegalizeTypeAction OpAction = getTypeAction(OpVT);
6359 assert((OpAction == TargetLowering::TypeLegal ||
6361 OpAction == TargetLowering::TypeWidenVector) &&
6362 "Unhandled legalization type");
6363
6364 EVT ExtendedOpVT =
6365 OpVT.changeVectorElementType(*DAG.getContext(), OutElemTy);
6366
6368 for (unsigned I = 0; I < NumOperands; ++I) {
6369 SDValue Op = N->getOperand(I);
6370 if (OpAction == TargetLowering::TypePromoteInteger)
6371 Op = GetPromotedInteger(Op);
6372 else if (OpAction == TargetLowering::TypeWidenVector)
6373 Op = DAG.getNode(ISD::ANY_EXTEND, dl, ExtendedOpVT, Op);
6374 Ops.push_back(Op);
6375 }
6376
6377 // Do the CONCAT on the legalized operands' element type, then extend
6378 // or truncate to the promoted result type.
6379 EVT ConcatVT = OutVT.changeVectorElementType(
6380 *DAG.getContext(), Ops[0].getValueType().getVectorElementType());
6381 return DAG.getAnyExtOrTrunc(
6382 DAG.getNode(ISD::CONCAT_VECTORS, dl, ConcatVT, Ops), dl, NOutVT);
6383 }
6384
6385 unsigned NumElem = N->getOperand(0).getValueType().getVectorNumElements();
6386 assert(NumElem * NumOperands == NumOutElem &&
6387 "Unexpected number of elements");
6388
6389 // Take the elements from the first vector.
6390 SmallVector<SDValue, 8> Ops(NumOutElem);
6391 for (unsigned i = 0; i < NumOperands; ++i) {
6392 SDValue Op = N->getOperand(i);
6393 if (getTypeAction(Op.getValueType()) == TargetLowering::TypePromoteInteger)
6394 Op = GetPromotedInteger(Op);
6395 EVT SclrTy = Op.getValueType().getVectorElementType();
6396 assert(NumElem == Op.getValueType().getVectorNumElements() &&
6397 "Unexpected number of elements");
6398
6399 for (unsigned j = 0; j < NumElem; ++j) {
6400 SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, SclrTy, Op,
6401 DAG.getVectorIdxConstant(j, dl));
6402 Ops[i * NumElem + j] = DAG.getAnyExtOrTrunc(Ext, dl, OutElemTy);
6403 }
6404 }
6405
6406 return DAG.getBuildVector(NOutVT, dl, Ops);
6407}
6408
6409SDValue DAGTypeLegalizer::PromoteIntRes_EXTEND_VECTOR_INREG(SDNode *N) {
6410 EVT VT = N->getValueType(0);
6411 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6412 assert(NVT.isVector() && "This type must be promoted to a vector type");
6413
6414 SDLoc dl(N);
6415
6416 // For operands whose TypeAction is to promote, extend the promoted node
6417 // appropriately (ZERO_EXTEND or SIGN_EXTEND) from the original pre-promotion
6418 // type, and then construct a new *_EXTEND_VECTOR_INREG node to the promote-to
6419 // type..
6420 if (getTypeAction(N->getOperand(0).getValueType())
6422 SDValue Promoted;
6423
6424 switch(N->getOpcode()) {
6426 Promoted = SExtPromotedInteger(N->getOperand(0));
6427 break;
6429 Promoted = ZExtPromotedInteger(N->getOperand(0));
6430 break;
6432 Promoted = GetPromotedInteger(N->getOperand(0));
6433 break;
6434 default:
6435 llvm_unreachable("Node has unexpected Opcode");
6436 }
6437 unsigned NewSize = NVT.getSizeInBits();
6438 if (Promoted.getValueType().getSizeInBits() > NewSize) {
6439 EVT ExtractVT = EVT::getVectorVT(
6440 *DAG.getContext(), Promoted.getValueType().getVectorElementType(),
6441 NewSize / Promoted.getScalarValueSizeInBits());
6442
6443 Promoted = DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, ExtractVT, Promoted,
6444 DAG.getVectorIdxConstant(0, dl));
6445 }
6446 return DAG.getNode(N->getOpcode(), dl, NVT, Promoted);
6447 }
6448
6449 // Directly extend to the appropriate transform-to type.
6450 return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
6451}
6452
6453SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_FIND_LAST_ACTIVE(SDNode *N) {
6454 EVT VT = N->getValueType(0);
6455 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6456 return DAG.getNode(ISD::VECTOR_FIND_LAST_ACTIVE, SDLoc(N), NVT, N->ops());
6457}
6458
6459SDValue DAGTypeLegalizer::PromoteIntRes_GET_ACTIVE_LANE_MASK(SDNode *N) {
6460 EVT VT = N->getValueType(0);
6461 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6462 return DAG.getNode(ISD::GET_ACTIVE_LANE_MASK, SDLoc(N), NVT, N->ops());
6463}
6464
6465SDValue DAGTypeLegalizer::PromoteIntRes_MASK_BEFOREFIRST(SDNode *N) {
6466 EVT VT = N->getValueType(0);
6467 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6468 SDValue Op = PromoteTargetBoolean(N->getOperand(0), NVT);
6469 return DAG.getNode(ISD::MASK_BEFOREFIRST, SDLoc(N), NVT, Op);
6470}
6471
6472SDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_MATCH(SDNode *N) {
6473 EVT VT = N->getValueType(0);
6474 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6475 SmallVector<SDValue, 3> NewOps(N->ops());
6476 NewOps[2] = PromoteTargetBoolean(N->getOperand(2), NVT);
6477 return DAG.getNode(ISD::VECTOR_MATCH, SDLoc(N), NVT, NewOps, N->getFlags());
6478}
6479
6480SDValue DAGTypeLegalizer::PromoteIntRes_PARTIAL_REDUCE_MLA(SDNode *N) {
6481 SDLoc DL(N);
6482 EVT VT = N->getValueType(0);
6483 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
6484 SDValue ExtAcc = GetPromotedInteger(N->getOperand(0));
6485 return DAG.getNode(N->getOpcode(), DL, NVT, ExtAcc, N->getOperand(1),
6486 N->getOperand(2));
6487}
6488
6489SDValue DAGTypeLegalizer::PromoteIntRes_INSERT_VECTOR_ELT(SDNode *N) {
6490 EVT OutVT = N->getValueType(0);
6491 EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
6492 assert(NOutVT.isVector() && "This type must be promoted to a vector type");
6493
6494 EVT NOutVTElem = NOutVT.getVectorElementType();
6495
6496 SDLoc dl(N);
6497 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6498
6499 SDValue ConvElem = DAG.getNode(ISD::ANY_EXTEND, dl,
6500 NOutVTElem, N->getOperand(1));
6501 return DAG.getNode(ISD::INSERT_VECTOR_ELT, dl, NOutVT,
6502 V0, ConvElem, N->getOperand(2));
6503}
6504
6505SDValue DAGTypeLegalizer::PromoteIntRes_VECREDUCE(SDNode *N) {
6506 // The VECREDUCE result size may be larger than the element size, so
6507 // we can simply change the result type.
6508 SDLoc dl(N);
6509 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
6510 return DAG.getNode(N->getOpcode(), dl, NVT, N->ops());
6511}
6512
6513SDValue DAGTypeLegalizer::PromoteIntRes_VP_REDUCE(SDNode *N) {
6514 // The VP_REDUCE result size may be larger than the element size, so we can
6515 // simply change the result type. However the start value and result must be
6516 // the same.
6517 SDLoc DL(N);
6518 SDValue Start = PromoteIntOpVectorReduction(N, N->getOperand(0));
6519 return DAG.getNode(N->getOpcode(), DL, Start.getValueType(), Start,
6520 N->getOperand(1), N->getOperand(2), N->getOperand(3));
6521}
6522
6523SDValue DAGTypeLegalizer::PromoteIntRes_PATCHPOINT(SDNode *N) {
6524 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
6525 SDLoc dl(N);
6526
6527 assert(N->getNumValues() == 3 && "Expected 3 values for PATCHPOINT");
6528 SDVTList VTList = DAG.getVTList({NVT, MVT::Other, MVT::Glue});
6529
6530 SmallVector<SDValue> Ops(N->ops());
6531 SDValue Res = DAG.getNode(ISD::PATCHPOINT, dl, VTList, Ops);
6532
6533 // Replace chain and glue uses with the new patchpoint.
6534 SDValue From[] = {SDValue(N, 1), SDValue(N, 2)};
6535 SDValue To[] = {Res.getValue(1), Res.getValue(2)};
6536 DAG.ReplaceAllUsesOfValuesWith(From, To, 2);
6537
6538 return Res.getValue(0);
6539}
6540
6541SDValue DAGTypeLegalizer::PromoteIntRes_READ_REGISTER(SDNode *N) {
6542 const Function &Fn = DAG.getMachineFunction().getFunction();
6543 Fn.getContext().diagnose(DiagnosticInfoLegalizationFailure(
6544 "cannot use llvm.read_register with illegal type", Fn, N->getDebugLoc()));
6545
6546 EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
6547 ReplaceValueWith(SDValue(N, 1), N->getOperand(0));
6548 return DAG.getPOISON(NVT);
6549}
6550
6551SDValue DAGTypeLegalizer::PromoteIntOp_EXTRACT_VECTOR_ELT(SDNode *N) {
6552 SDLoc dl(N);
6553 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6554 SDValue V1 = DAG.getZExtOrTrunc(N->getOperand(1), dl,
6555 TLI.getVectorIdxTy(DAG.getDataLayout()));
6556 SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl,
6557 V0->getValueType(0).getScalarType(), V0, V1);
6558
6559 // EXTRACT_VECTOR_ELT can return types which are wider than the incoming
6560 // element types. If this is the case then we need to expand the outgoing
6561 // value and not truncate it.
6562 return DAG.getAnyExtOrTrunc(Ext, dl, N->getValueType(0));
6563}
6564
6565SDValue DAGTypeLegalizer::PromoteIntOp_INSERT_SUBVECTOR(SDNode *N) {
6566 SDLoc dl(N);
6567 // The result type is equal to the first input operand's type, so the
6568 // type that needs promoting must be the second source vector.
6569 SDValue V0 = N->getOperand(0);
6570 SDValue V1 = GetPromotedInteger(N->getOperand(1));
6571 SDValue Idx = N->getOperand(2);
6572 EVT PromVT = EVT::getVectorVT(*DAG.getContext(),
6573 V1.getValueType().getVectorElementType(),
6574 V0.getValueType().getVectorElementCount());
6575 V0 = DAG.getAnyExtOrTrunc(V0, dl, PromVT);
6576 SDValue Ext = DAG.getNode(ISD::INSERT_SUBVECTOR, dl, PromVT, V0, V1, Idx);
6577 return DAG.getAnyExtOrTrunc(Ext, dl, N->getValueType(0));
6578}
6579
6580// FIXME: We wouldn't need this if clang could promote short integers
6581// that are arguments to FAKE_USE.
6582SDValue DAGTypeLegalizer::PromoteIntOp_FAKE_USE(SDNode *N) {
6583 SDLoc dl(N);
6584 SDValue V0 = N->getOperand(0);
6585 SDValue V1 = N->getOperand(1);
6586 EVT InVT1 = V1.getValueType();
6587 SDValue VPromoted =
6588 DAG.getNode(ISD::ANY_EXTEND, dl,
6589 TLI.getTypeToTransformTo(*DAG.getContext(), InVT1), V1);
6590 return DAG.getNode(N->getOpcode(), dl, N->getValueType(0), V0, VPromoted);
6591}
6592
6593SDValue DAGTypeLegalizer::PromoteIntOp_EXTRACT_SUBVECTOR(SDNode *N) {
6594 SDLoc dl(N);
6595 SDValue V0 = GetPromotedInteger(N->getOperand(0));
6596 MVT InVT = V0.getValueType().getSimpleVT();
6597 MVT OutVT = MVT::getVectorVT(InVT.getVectorElementType(),
6598 N->getValueType(0).getVectorNumElements());
6599 SDValue Ext = DAG.getNode(ISD::EXTRACT_SUBVECTOR, dl, OutVT, V0, N->getOperand(1));
6600 return DAG.getNode(ISD::TRUNCATE, dl, N->getValueType(0), Ext);
6601}
6602
6603SDValue DAGTypeLegalizer::PromoteIntOp_CONCAT_VECTORS(SDNode *N) {
6604 SDLoc dl(N);
6605
6606 EVT ResVT = N->getValueType(0);
6607 unsigned NumElems = N->getNumOperands();
6608
6609 if (ResVT.isScalableVector()) {
6610 SDValue ResVec = DAG.getPOISON(ResVT);
6611
6612 for (unsigned OpIdx = 0; OpIdx < NumElems; ++OpIdx) {
6613 SDValue Op = N->getOperand(OpIdx);
6614 unsigned OpNumElts = Op.getValueType().getVectorMinNumElements();
6615 ResVec = DAG.getNode(ISD::INSERT_SUBVECTOR, dl, ResVT, ResVec, Op,
6616 DAG.getIntPtrConstant(OpIdx * OpNumElts, dl));
6617 }
6618
6619 return ResVec;
6620 }
6621
6622 EVT RetSclrTy = N->getValueType(0).getVectorElementType();
6623
6625 NewOps.reserve(NumElems);
6626
6627 // For each incoming vector
6628 for (unsigned VecIdx = 0; VecIdx != NumElems; ++VecIdx) {
6629 SDValue Incoming = GetPromotedInteger(N->getOperand(VecIdx));
6630 EVT SclrTy = Incoming->getValueType(0).getVectorElementType();
6631 unsigned NumElem = Incoming->getValueType(0).getVectorNumElements();
6632
6633 for (unsigned i=0; i<NumElem; ++i) {
6634 // Extract element from incoming vector
6635 SDValue Ex = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, SclrTy, Incoming,
6636 DAG.getVectorIdxConstant(i, dl));
6637 SDValue Tr = DAG.getNode(ISD::TRUNCATE, dl, RetSclrTy, Ex);
6638 NewOps.push_back(Tr);
6639 }
6640 }
6641
6642 return DAG.getBuildVector(N->getValueType(0), dl, NewOps);
6643}
6644
6645SDValue DAGTypeLegalizer::ExpandIntOp_STACKMAP(SDNode *N, unsigned OpNo) {
6646 assert(OpNo > 1);
6647 SDValue Op = N->getOperand(OpNo);
6648
6649 // FIXME: Non-constant operands are not yet handled:
6650 // - https://github.com/llvm/llvm-project/issues/26431
6651 // - https://github.com/llvm/llvm-project/issues/55957
6652 ConstantSDNode *CN = dyn_cast<ConstantSDNode>(Op);
6653 if (!CN)
6654 return SDValue();
6655
6656 // Copy operands before the one being expanded.
6657 SmallVector<SDValue> NewOps;
6658 for (unsigned I = 0; I < OpNo; I++)
6659 NewOps.push_back(N->getOperand(I));
6660
6661 EVT Ty = Op.getValueType();
6662 SDLoc DL = SDLoc(N);
6663 if (CN->getConstantIntValue()->getValue().getActiveBits() < 64) {
6664 NewOps.push_back(
6665 DAG.getTargetConstant(StackMaps::ConstantOp, DL, MVT::i64));
6666 NewOps.push_back(DAG.getTargetConstant(CN->getZExtValue(), DL, Ty));
6667 } else {
6668 // FIXME: https://github.com/llvm/llvm-project/issues/55609
6669 return SDValue();
6670 }
6671
6672 // Copy remaining operands.
6673 for (unsigned I = OpNo + 1; I < N->getNumOperands(); I++)
6674 NewOps.push_back(N->getOperand(I));
6675
6676 SDValue NewNode = DAG.getNode(N->getOpcode(), DL, N->getVTList(), NewOps);
6677
6678 for (unsigned ResNum = 0; ResNum < N->getNumValues(); ResNum++)
6679 ReplaceValueWith(SDValue(N, ResNum), NewNode.getValue(ResNum));
6680
6681 return SDValue(); // Signal that we have replaced the node already.
6682}
6683
6684SDValue DAGTypeLegalizer::ExpandIntOp_PATCHPOINT(SDNode *N, unsigned OpNo) {
6685 assert(OpNo >= 7);
6686 SDValue Op = N->getOperand(OpNo);
6687
6688 // FIXME: Non-constant operands are not yet handled:
6689 // - https://github.com/llvm/llvm-project/issues/26431
6690 // - https://github.com/llvm/llvm-project/issues/55957
6691 ConstantSDNode *CN = dyn_cast<ConstantSDNode>(Op);
6692 if (!CN)
6693 return SDValue();
6694
6695 // Copy operands before the one being expanded.
6696 SmallVector<SDValue> NewOps;
6697 for (unsigned I = 0; I < OpNo; I++)
6698 NewOps.push_back(N->getOperand(I));
6699
6700 EVT Ty = Op.getValueType();
6701 SDLoc DL = SDLoc(N);
6702 if (CN->getConstantIntValue()->getValue().getActiveBits() < 64) {
6703 NewOps.push_back(
6704 DAG.getTargetConstant(StackMaps::ConstantOp, DL, MVT::i64));
6705 NewOps.push_back(DAG.getTargetConstant(CN->getZExtValue(), DL, Ty));
6706 } else {
6707 // FIXME: https://github.com/llvm/llvm-project/issues/55609
6708 return SDValue();
6709 }
6710
6711 // Copy remaining operands.
6712 for (unsigned I = OpNo + 1; I < N->getNumOperands(); I++)
6713 NewOps.push_back(N->getOperand(I));
6714
6715 SDValue NewNode = DAG.getNode(N->getOpcode(), DL, N->getVTList(), NewOps);
6716
6717 for (unsigned ResNum = 0; ResNum < N->getNumValues(); ResNum++)
6718 ReplaceValueWith(SDValue(N, ResNum), NewNode.getValue(ResNum));
6719
6720 return SDValue(); // Signal that we have replaced the node already.
6721}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
unsigned uint64_t
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
#define X(NUM, ENUM, NAME)
Definition ELF.h:857
dxil translate DXIL Translate Metadata
static bool isSigned(unsigned Opcode)
const size_t AbstractManglingParser< Derived, Alloc >::NumOps
const AbstractManglingParser< Derived, Alloc >::OperatorInfo AbstractManglingParser< Derived, Alloc >::Ops[]
static SDValue SaturateWidenedDIVFIX(SDValue V, SDLoc &dl, unsigned SatW, bool Signed, const TargetLowering &TLI, SelectionDAG &DAG)
static SDValue fpExtendHelper(SDValue Op, SDValue &Chain, bool IsStrict, EVT VT, SDLoc DL, SelectionDAG &DAG)
static SDValue earlyExpandDIVFIX(SDNode *N, SDValue LHS, SDValue RHS, unsigned Scale, const TargetLowering &TLI, SelectionDAG &DAG, unsigned SatW=0)
static unsigned getExtendForIntVecReduction(SDNode *N)
static std::pair< ISD::CondCode, ISD::NodeType > getExpandedMinMaxOps(int Op)
static bool isZero(Value *V, const DataLayout &DL, DominatorTree *DT, AssumptionCache *AC)
Definition Lint.cpp:540
#define I(x, y, z)
Definition MD5.cpp:57
const SmallVectorImpl< MachineOperand > & Cond
#define LLVM_DEBUG(...)
Definition Debug.h:119
static TableGen::Emitter::Opt Y("gen-skeleton-entry", EmitSkeleton, "Generate example skeleton entry")
This file describes how to lower LLVM code to machine code.
Value * RHS
Value * LHS
Class for arbitrary precision integers.
Definition APInt.h:78
static APInt getAllOnes(unsigned numBits)
Return an APInt of a specified width with all bits set.
Definition APInt.h:230
unsigned getActiveBits() const
Compute the number of active bits in the value.
Definition APInt.h:1532
LLVM_ABI APInt trunc(unsigned width) const
Truncate to new width.
Definition APInt.cpp:970
static APInt getMaxValue(unsigned numBits)
Gets maximum unsigned value of APInt for specific bit width.
Definition APInt.h:202
unsigned countLeadingOnes() const
Definition APInt.h:1644
bool ugt(const APInt &RHS) const
Unsigned greater than comparison.
Definition APInt.h:1186
static APInt getSignedMaxValue(unsigned numBits)
Gets maximum signed value of APInt for a specific bit width.
Definition APInt.h:205
static APInt getSignedMinValue(unsigned numBits)
Gets minimum signed value of APInt for a specific bit width.
Definition APInt.h:215
unsigned countTrailingZeros() const
Definition APInt.h:1667
unsigned countLeadingZeros() const
Definition APInt.h:1626
LLVM_ABI APInt sext(unsigned width) const
Sign extend to a new width.
Definition APInt.cpp:1030
bool isSubsetOf(const APInt &RHS) const
This operation checks that all bits set in this APInt are also set in RHS.
Definition APInt.h:1261
static APInt getLowBitsSet(unsigned numBits, unsigned loBitsSet)
Constructs an APInt value that has the bottom loBitsSet bits set.
Definition APInt.h:302
static APInt getHighBitsSet(unsigned numBits, unsigned hiBitsSet)
Constructs an APInt value that has the top hiBitsSet bits set.
Definition APInt.h:292
unsigned countTrailingOnes() const
Definition APInt.h:1682
static APInt getOneBitSet(unsigned numBits, unsigned BitNo)
Return an APInt with exactly one bit set in the result.
Definition APInt.h:235
APInt lshr(unsigned shiftAmt) const
Logical right-shift function.
Definition APInt.h:853
bool uge(const APInt &RHS) const
Unsigned greater or equal comparison.
Definition APInt.h:1225
This is an SDNode representing atomic operations.
const APInt & getValue() const
Return the constant as an APInt value reference.
Definition Constants.h:159
const ConstantInt * getConstantIntValue() const
uint64_t getZExtValue() const
@ NewNode
This is a new node, not before seen, that was created in the process of legalizing some other node.
const Function & getFunction() const
Definition Function.h:167
LLVMContext & getContext() const
getContext - Return a reference to the LLVMContext associated with this function.
Definition Function.cpp:356
LLVM_ABI void diagnose(const DiagnosticInfo &DI)
Report a message to the currently installed diagnostic handler.
This class is used to represent ISD::LOAD nodes.
unsigned getVectorNumElements() const
TypeSize getSizeInBits() const
Returns the size of the specified MVT in bits.
static MVT getVectorVT(MVT VT, unsigned NumElements)
MVT getVectorElementType() const
Flags
Flags values. These may be or'd together.
This class is used to represent an MGATHER node.
This class is used to represent an MLOAD node.
This class is used to represent an MSCATTER node.
This class is used to represent an MSTORE node.
MachineMemOperand * getMemOperand() const
Return the unique MachineMemOperand object describing the memory reference performed by operation.
EVT getMemoryVT() const
Return the type of the in-memory value.
static PointerType * getUnqual(LLVMContext &C)
This constructs an opaque pointer to an object in the default address space (address space zero).
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
Represents one node in the SelectionDAG.
bool isStrictFPOpcode()
Test if this node is a strict floating point pseudo-op.
unsigned getOpcode() const
Return the SelectionDAG opcode value for this node.
SDNodeFlags getFlags() const
uint64_t getAsZExtVal() const
Helper method returns the zero-extended integer value of a ConstantSDNode.
const SDValue & getOperand(unsigned Num) const
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.
uint64_t getScalarValueSizeInBits() const
This is used to represent a portion of an LLVM function in a low-level Data Dependence DAG representa...
SDValue getExtOrTrunc(SDValue Op, const SDLoc &DL, EVT VT, unsigned Opcode)
Convert Op, which must be of integer type, to the integer type VT, by either any/sign/zero-extending ...
LLVM_ABI SDValue getConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isTarget=false, bool isOpaque=false)
Create a ConstantSDNode wrapping a constant value.
LLVM_ABI SDValue getNode(unsigned Opcode, const SDLoc &DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
LLVM_ABI SDValue getZExtOrTrunc(SDValue Op, const SDLoc &DL, EVT VT)
Convert Op, which must be of integer type, to the integer type VT, by either zero-extending or trunca...
LLVMContext * getContext() const
void reserve(size_type N)
void push_back(const T &Elt)
This class is used to represent ISD::STORE nodes.
LegalizeAction
This enum indicates whether operations are valid for a target, and if not, what action should be used...
ShiftLegalizationStrategy
Return the preferred strategy to legalize tihs SHIFT instruction, with ExpansionFactor being the recu...
LegalizeTypeAction
This enum indicates whether a types are legal for a target, and if not, what action should be used to...
BooleanContent
Enum that describes how the target represents true/false values.
std::vector< ArgListEntry > ArgListTy
static ISD::NodeType getExtendForContent(BooleanContent Content)
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
SDValue expandFixedPointDiv(unsigned Opcode, const SDLoc &dl, SDValue LHS, SDValue RHS, unsigned Scale, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::[US]DIVFIX[SAT].
static constexpr TypeSize getFixed(ScalarTy ExactSize)
Definition TypeSize.h:339
LLVMContext & getContext() const
Return the LLVMContext in which this type was uniqued.
Definition Type.h:130
This class is used to represent a VP_LOAD node.
This class is used to represent a VP_STORE node.
constexpr bool hasKnownScalarFactor(const FixedOrScalableQuantity &RHS) const
Returns true if there exists a value X where RHS*X will result in a value whose quantity matches our ...
Definition TypeSize.h:265
constexpr ScalarTy getKnownScalarFactor(const FixedOrScalableQuantity &RHS) const
Returns a value X where RHS*X will result in a value whose quantity matches our own.
Definition TypeSize.h:273
constexpr ScalarTy getKnownMinValue() const
Returns the minimum value this quantity can represent.
Definition TypeSize.h:165
constexpr LeafTy divideCoefficientBy(ScalarTy RHS) const
We do not provide the '/' operator here because division for polynomial types does not work in the sa...
Definition TypeSize.h:252
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
constexpr char Args[]
Key for Kernel::Metadata::mArgs.
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.
@ Entry
Definition COFF.h:862
bool isNON_EXTLoad(const SDNode *N)
Returns true if the specified node is a non-extending load.
NodeType
ISD::NodeType enum - This enum defines the target-independent operators for a SelectionDAG.
Definition ISDOpcodes.h:43
@ SETCC
SetCC operator - This evaluates to a true value iff the condition is true.
Definition ISDOpcodes.h:837
@ MERGE_VALUES
MERGE_VALUES - This node takes multiple discrete operands and returns them all as its individual resu...
Definition ISDOpcodes.h:263
@ STRICT_FSETCC
STRICT_FSETCC/STRICT_FSETCCS - Constrained versions of SETCC, used for floating-point operands only.
Definition ISDOpcodes.h:516
@ POISON
POISON - A poison node.
Definition ISDOpcodes.h:238
@ PARTIAL_REDUCE_SMLA
PARTIAL_REDUCE_[U|S]MLA(Accumulator, Input1, Input2) The partial reduction nodes sign or zero extend ...
@ LOOP_DEPENDENCE_RAW_MASK
@ MASK_BEFOREFIRST
Has one mask vector operand.
@ COND_LOOP
COND_LOOP is a conditional branch to self, used for implementing efficient conditional traps.
@ MLOAD
Masked load and store - consecutive vector load and store operations with additional mask operand tha...
@ SMUL_LOHI
SMUL_LOHI/UMUL_LOHI - Multiply two integers of type iN, producing a signed/unsigned value of type i[2...
Definition ISDOpcodes.h:277
@ INSERT_SUBVECTOR
INSERT_SUBVECTOR(VECTOR1, VECTOR2, IDX) - Returns a vector with VECTOR2 inserted into VECTOR1.
Definition ISDOpcodes.h:605
@ BSWAP
Byte Swap and Counting operators.
Definition ISDOpcodes.h:797
@ SMULFIX
RESULT = [US]MULFIX(LHS, RHS, SCALE) - Perform fixed point multiplication on 2 integers with the same...
Definition ISDOpcodes.h:397
@ ATOMIC_STORE
OUTCHAIN = ATOMIC_STORE(INCHAIN, val, ptr) This corresponds to "store atomic" instruction.
@ ADDC
Carry-setting nodes for multiple precision addition and subtraction.
Definition ISDOpcodes.h:296
@ ADD
Simple integer binary arithmetic operators.
Definition ISDOpcodes.h:266
@ LOAD
LOAD and STORE have token chains as their first operand, then the same operands as an LLVM load/store...
@ SMULFIXSAT
Same as the corresponding unsaturated fixed point instructions, but the result is clamped between the...
Definition ISDOpcodes.h:403
@ ANY_EXTEND
ANY_EXTEND - Used for integer types. The high bits are undefined.
Definition ISDOpcodes.h:871
@ CTTZ_ELTS
Returns the number of number of trailing (least significant) zero elements in a vector.
@ VECTOR_FIND_LAST_ACTIVE
Finds the index of the last active mask element Operands: Mask.
@ ATOMIC_CMP_SWAP_WITH_SUCCESS
Val, Success, OUTCHAIN = ATOMIC_CMP_SWAP_WITH_SUCCESS(INCHAIN, ptr, cmp, swap) N.b.
@ SINT_TO_FP
[SU]INT_TO_FP - These operators convert integers (whose interpreted sign depends on the first letter)...
Definition ISDOpcodes.h:898
@ CONCAT_VECTORS
CONCAT_VECTORS(VECTOR0, VECTOR1, ...) - Given a number of values of vector type with the same length ...
Definition ISDOpcodes.h:589
@ ABS
ABS - Determine the unsigned absolute value of a signed integer value of the same bitwidth.
Definition ISDOpcodes.h:757
@ SIGN_EXTEND_VECTOR_INREG
SIGN_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register sign-extension of the low ...
Definition ISDOpcodes.h:928
@ SDIVREM
SDIVREM/UDIVREM - Divide two integers and produce both a quotient and remainder result.
Definition ISDOpcodes.h:282
@ FP16_TO_FP
FP16_TO_FP, FP_TO_FP16 - These operators are used to perform promotions and truncation for half-preci...
@ FAKE_USE
FAKE_USE represents a use of the operand but does not do anything.
@ 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.
Definition ISDOpcodes.h:256
@ CLMUL
Carry-less multiplication operations.
Definition ISDOpcodes.h:788
@ FLDEXP
FLDEXP - ldexp, inspired by libm (op0 * 2**op1).
@ SDIVFIX
RESULT = [US]DIVFIX(LHS, RHS, SCALE) - Perform fixed point division on 2 integers with the same width...
Definition ISDOpcodes.h:410
@ CONVERT_FROM_ARBITRARY_FP
CONVERT_FROM_ARBITRARY_FP - This operator converts from an arbitrary floating-point represented as an...
@ CTLZ_ZERO_POISON
Definition ISDOpcodes.h:806
@ SET_ROUNDING
Set rounding mode.
Definition ISDOpcodes.h:993
@ PARTIAL_REDUCE_UMLA
@ SIGN_EXTEND
Conversion operators.
Definition ISDOpcodes.h:862
@ AVGCEILS
AVGCEILS/AVGCEILU - Rounding averaging add - Add two integers using an integer of type i[N+2],...
Definition ISDOpcodes.h:725
@ STRICT_UINT_TO_FP
Definition ISDOpcodes.h:490
@ SCALAR_TO_VECTOR
SCALAR_TO_VECTOR(VAL) - This represents the operation of loading a scalar value into element 0 of the...
Definition ISDOpcodes.h:675
@ READSTEADYCOUNTER
READSTEADYCOUNTER - This corresponds to the readfixedcounter intrinsic.
@ SETCCCARRY
Like SetCC, ops #0 and #1 are the LHS and RHS operands to compare, but op #2 is a boolean indicating ...
Definition ISDOpcodes.h:845
@ BR_CC
BR_CC - Conditional branch.
@ SSUBO
Same for subtraction.
Definition ISDOpcodes.h:355
@ VECTOR_INTERLEAVE
VECTOR_INTERLEAVE(VEC1, VEC2, ...) - Returns N vectors from N input vectors, where N is the factor to...
Definition ISDOpcodes.h:640
@ STEP_VECTOR
STEP_VECTOR(IMM) - Returns a scalable vector whose lanes are comprised of a linear sequence of unsign...
Definition ISDOpcodes.h:701
@ IS_FPCLASS
Performs a check of floating point class property, defined by IEEE-754.
Definition ISDOpcodes.h:553
@ SSUBSAT
RESULT = [US]SUBSAT(LHS, RHS) - Perform saturation subtraction on 2 integers with the same bit width ...
Definition ISDOpcodes.h:377
@ SELECT
Select(COND, TRUEVAL, FALSEVAL).
Definition ISDOpcodes.h:814
@ ATOMIC_LOAD
Val, OUTCHAIN = ATOMIC_LOAD(INCHAIN, ptr) This corresponds to "load atomic" instruction.
@ UNDEF
UNDEF - An undefined node.
Definition ISDOpcodes.h:235
@ EXTRACT_ELEMENT
EXTRACT_ELEMENT - This is used to get the lower or upper (determined by a Constant,...
Definition ISDOpcodes.h:249
@ SPLAT_VECTOR
SPLAT_VECTOR(VAL) - Returns a vector with the scalar value VAL duplicated in all lanes.
Definition ISDOpcodes.h:682
@ GET_ACTIVE_LANE_MASK
GET_ACTIVE_LANE_MASK - this corrosponds to the llvm.get.active.lane.mask intrinsic.
@ SADDO
RESULT, BOOL = [SU]ADDO(LHS, RHS) - Overflow-aware nodes for addition.
Definition ISDOpcodes.h:351
@ ARITH_FENCE
ARITH_FENCE - This corresponds to a arithmetic fence intrinsic.
@ CTLS
Count leading redundant sign bits.
Definition ISDOpcodes.h:810
@ VECREDUCE_ADD
Integer reductions may have a result type larger than the vector element type.
@ GET_ROUNDING
Returns current rounding mode: -1 Undefined 0 Round to 0 1 Round to nearest, ties to even 2 Round to ...
Definition ISDOpcodes.h:988
@ STRICT_FP_TO_FP16
@ MULHU
MULHU/MULHS - Multiply high - Multiply two integers of type iN, producing an unsigned/signed value of...
Definition ISDOpcodes.h:714
@ STRICT_FP16_TO_FP
@ SHL
Shift and rotation operations.
Definition ISDOpcodes.h:779
@ VECTOR_SHUFFLE
VECTOR_SHUFFLE(VEC1, VEC2) - Returns a vector, of the same type as VEC1/VEC2.
Definition ISDOpcodes.h:659
@ EXTRACT_SUBVECTOR
EXTRACT_SUBVECTOR(VECTOR, IDX) - Returns a subvector from VECTOR.
Definition ISDOpcodes.h:619
@ READ_REGISTER
READ_REGISTER, WRITE_REGISTER - This node represents llvm.register on the DAG, which implements the n...
Definition ISDOpcodes.h:141
@ EXTRACT_VECTOR_ELT
EXTRACT_VECTOR_ELT(VECTOR, IDX) - Returns a single element from VECTOR identified by the (potentially...
Definition ISDOpcodes.h:581
@ ZERO_EXTEND
ZERO_EXTEND - Used for integer types, zeroing the new bits.
Definition ISDOpcodes.h:868
@ SELECT_CC
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
Definition ISDOpcodes.h:829
@ VSCALE
VSCALE(IMM) - Returns the runtime scaling factor used to calculate the number of elements within a sc...
@ ATOMIC_CMP_SWAP
Val, OUTCHAIN = ATOMIC_CMP_SWAP(INCHAIN, ptr, cmp, swap) For double-word atomic operations: ValLo,...
@ SSHLSAT
RESULT = [US]SHLSAT(LHS, RHS) - Perform saturation left shift.
Definition ISDOpcodes.h:389
@ PATCHPOINT
The llvm.experimental.patchpoint.
@ SMULO
Same for multiplication.
Definition ISDOpcodes.h:359
@ VECTOR_SPLICE_LEFT
VECTOR_SPLICE_LEFT(VEC1, VEC2, OFFSET) - Shifts CONCAT_VECTORS(VEC1, VEC2) left by OFFSET elements an...
Definition ISDOpcodes.h:663
@ ANY_EXTEND_VECTOR_INREG
ANY_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register any-extension of the low la...
Definition ISDOpcodes.h:917
@ SIGN_EXTEND_INREG
SIGN_EXTEND_INREG - This operator atomically performs a SHL/SRA pair to sign extend a small value in ...
Definition ISDOpcodes.h:906
@ SMIN
[US]{MIN/MAX} - Binary minimum or maximum of signed or unsigned integers.
Definition ISDOpcodes.h:737
@ MASKED_UDIV
Masked vector arithmetic that returns poison on disabled lanes.
@ VECTOR_REVERSE
VECTOR_REVERSE(VECTOR) - Returns a vector, of the same type as VECTOR, whose elements are shuffled us...
Definition ISDOpcodes.h:650
@ SDIVFIXSAT
Same as the corresponding unsaturated fixed point instructions, but the result is clamped between the...
Definition ISDOpcodes.h:416
@ FP_EXTEND
X = FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
Definition ISDOpcodes.h:996
@ VSELECT
Select with a vector condition (op #0) and two vector operands (ops #1 and #2), returning a vector re...
Definition ISDOpcodes.h:823
@ UADDO_CARRY
Carry-using nodes for multiple precision addition and subtraction.
Definition ISDOpcodes.h:331
@ STRICT_SINT_TO_FP
STRICT_[US]INT_TO_FP - Convert a signed or unsigned integer to a floating point value.
Definition ISDOpcodes.h:489
@ MGATHER
Masked gather and scatter - load and store operations for a vector of random addresses with additiona...
@ BF16_TO_FP
BF16_TO_FP, FP_TO_BF16 - These operators are used to perform promotions and truncation for bfloat16.
@ FRAMEADDR
FRAMEADDR, RETURNADDR - These nodes represent llvm.frameaddress and llvm.returnaddress on the DAG.
Definition ISDOpcodes.h:112
@ STRICT_FP_TO_UINT
Definition ISDOpcodes.h:483
@ PEXT
Parallel bit extract (compress) and parallel bit deposit (expand).
Definition ISDOpcodes.h:793
@ STRICT_FP_TO_SINT
STRICT_FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
Definition ISDOpcodes.h:482
@ FP_TO_SINT
FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
Definition ISDOpcodes.h:944
@ READCYCLECOUNTER
READCYCLECOUNTER - This corresponds to the readcyclecounter intrinsic.
@ STRICT_FP_EXTEND
X = STRICT_FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
Definition ISDOpcodes.h:510
@ AND
Bitwise operators - logical and, logical or, logical xor.
Definition ISDOpcodes.h:749
@ STRICT_FP_TO_BF16
@ SCMP
[US]CMP - 3-way comparison of signed or unsigned integers.
Definition ISDOpcodes.h:745
@ AVGFLOORS
AVGFLOORS/AVGFLOORU - Averaging add - Add two integers using an integer of type i[N+1],...
Definition ISDOpcodes.h:720
@ VECTOR_MATCH
VECTOR_MATCH - this corresponds to the llvm.experimental.vector.match intrinsic.
@ VECTOR_SPLICE_RIGHT
VECTOR_SPLICE_RIGHT(VEC1, VEC2, OFFSET) - Shifts CONCAT_VECTORS(VEC1,VEC2) right by OFFSET elements a...
Definition ISDOpcodes.h:667
@ ADDE
Carry-using nodes for multiple precision addition and subtraction.
Definition ISDOpcodes.h:306
@ STACKMAP
The llvm.experimental.stackmap intrinsic.
@ SPLAT_VECTOR_PARTS
SPLAT_VECTOR_PARTS(SCALAR1, SCALAR2, ...) - Returns a vector with the scalar values joined together a...
Definition ISDOpcodes.h:691
@ FREEZE
FREEZE - FREEZE(VAL) returns an arbitrary value if VAL is UNDEF (or is evaluated to UNDEF),...
Definition ISDOpcodes.h:243
@ INSERT_VECTOR_ELT
INSERT_VECTOR_ELT(VECTOR, VAL, IDX) - Returns VECTOR with the element at IDX replaced with VAL.
Definition ISDOpcodes.h:570
@ TokenFactor
TokenFactor - This node takes multiple tokens as input and produces a single token result.
Definition ISDOpcodes.h:55
@ ATOMIC_SWAP
Val, OUTCHAIN = ATOMIC_SWAP(INCHAIN, ptr, amt) Val, OUTCHAIN = ATOMIC_LOAD_[OpName](INCHAIN,...
@ CTTZ_ZERO_POISON
Bit counting operators with a poisoned result for zero inputs.
Definition ISDOpcodes.h:805
@ FFREXP
FFREXP - frexp, extract fractional and exponent component of a floating-point value.
@ VECTOR_COMPRESS
VECTOR_COMPRESS(Vec, Mask, Passthru) consecutively place vector elements based on mask e....
Definition ISDOpcodes.h:709
@ ZERO_EXTEND_VECTOR_INREG
ZERO_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register zero-extension of the low ...
Definition ISDOpcodes.h:939
@ EXPERIMENTAL_VECTOR_HISTOGRAM
Experimental vector histogram intrinsic Operands: Input Chain, Inc, Mask, Base, Index,...
@ FP_TO_SINT_SAT
FP_TO_[US]INT_SAT - Convert floating point value in operand 0 to a signed or unsigned scalar integer ...
Definition ISDOpcodes.h:963
@ TRUNCATE
TRUNCATE - Completely drop the high bits.
Definition ISDOpcodes.h:874
@ VAARG
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
@ BRCOND
BRCOND - Conditional branch.
@ CONVERT_TO_ARBITRARY_FP
CONVERT_TO_ARBITRARY_FP - Converts a native FP value to an arbitrary floating-point format,...
@ SHL_PARTS
SHL_PARTS/SRA_PARTS/SRL_PARTS - These operators are used for expanded integer shift operations.
Definition ISDOpcodes.h:851
@ AssertSext
AssertSext, AssertZext - These nodes record if a register contains a value that has already been zero...
Definition ISDOpcodes.h:64
@ PARTIAL_REDUCE_SUMLA
@ SADDSAT
RESULT = [US]ADDSAT(LHS, RHS) - Perform saturation addition on 2 integers with the same bit width (W)...
Definition ISDOpcodes.h:368
@ VECTOR_REPEAT
VECTOR_REPEAT(FIXED_LENGTH_VECTOR) Repeatedly copies the elements of the source fixed-length vector t...
Definition ISDOpcodes.h:645
@ VECTOR_DEINTERLEAVE
VECTOR_DEINTERLEAVE(VEC1, VEC2, ...) - Returns N vectors from N input vectors, where N is the factor ...
Definition ISDOpcodes.h:629
@ CTTZ_ELTS_ZERO_POISON
@ ABDS
ABDS/ABDU - Absolute difference - Return the absolute difference between two numbers interpreted as s...
Definition ISDOpcodes.h:732
@ SADDO_CARRY
Carry-using overflow-aware nodes for multiple precision addition and subtraction.
Definition ISDOpcodes.h:341
@ ABS_MIN_POISON
ABS with a poison result for INT_MIN.
Definition ISDOpcodes.h:761
@ BUILD_VECTOR
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a fixed-width vector with the specified,...
Definition ISDOpcodes.h:561
@ LOOP_DEPENDENCE_WAR_MASK
The llvm.loop.dependence.
bool isNormalStore(const SDNode *N)
Returns true if the specified node is a non-truncating and unindexed store.
bool isTrueWhenEqual(CondCode Cond)
Return true if the specified condition returns true if the two operands to the condition are equal.
bool isUNINDEXEDLoad(const SDNode *N)
Returns true if the specified node is an unindexed load.
bool isSignedIntSetCC(CondCode Code)
Return true if this is a setcc instruction that performs a signed comparison when used with integer o...
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,...
LoadExtType
LoadExtType enum - This enum defines the three variants of LOADEXT (load with extension).
bool isUnsignedIntSetCC(CondCode Code)
Return true if this is a setcc instruction that performs an unsigned comparison when used with intege...
bool isNormalLoad(const SDNode *N)
Returns true if the specified node is a non-extending and unindexed load.
bool isIntEqualitySetCC(CondCode Code)
Return true if this is a setcc instruction that performs an equality comparison when used with intege...
LLVM_ABI Libcall getSINTTOFP(EVT OpVT, EVT RetVT)
getSINTTOFP - Return the SINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getUREM(EVT VT)
LLVM_ABI Libcall getSHL(EVT VT)
LLVM_ABI Libcall getSYNC(unsigned Opc, MVT VT)
Return the SYNC_FETCH_AND_* value for the given opcode and type, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getUINTTOFP(EVT OpVT, EVT RetVT)
getUINTTOFP - Return the UINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSDIV(EVT VT)
LLVM_ABI Libcall getSRL(EVT VT)
LLVM_ABI Libcall getSRA(EVT VT)
LLVM_ABI Libcall getUDIV(EVT VT)
LLVM_ABI Libcall getFPTOUINT(EVT OpVT, EVT RetVT)
getFPTOUINT - Return the FPTOUINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getFPTOSINT(EVT OpVT, EVT RetVT)
getFPTOSINT - Return the FPTOSINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getOUTLINE_ATOMIC(unsigned Opc, AtomicOrdering Order, MVT VT)
Return the outline atomics value for the given opcode, atomic ordering and type, or UNKNOWN_LIBCALL i...
LLVM_ABI Libcall getSREM(EVT VT)
LLVM_ABI Libcall getMUL(EVT VT)
LLVM_ABI Libcall getCTPOP(EVT VT)
LLVM_ABI Libcall getMULO(EVT VT)
NodeAddr< NodeBase * > Node
Definition RDFGraph.h:381
NodeAddr< FuncNode * > Func
Definition RDFGraph.h:393
Type * getValueType(Value *V, bool ReVec, bool LookThroughCmp)
Returns the "element type" of the given value/instruction V.
This is an optimization pass for GlobalISel generic memory operations.
LLVM_ABI bool isNullConstant(SDValue V)
Returns true if V is a constant integer zero.
@ Known
Known to have no common set bits.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
constexpr T alignDown(U Value, V Align, W Skew=0)
Returns the largest unsigned integer less than or equal to Value and is Skew mod Align.
Definition MathExtras.h:541
unsigned Log2_32(uint32_t Value)
Return the floor log base 2 of the specified value, -1 if the value is zero.
Definition MathExtras.h:326
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
Definition MathExtras.h:280
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:209
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
Definition Error.cpp:163
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Definition Casting.h:547
@ Success
The lock was released successfully.
AtomicOrdering
Atomic ordering for LLVM's memory model.
@ AfterLegalizeTypes
Definition DAGCombine.h:17
@ Or
Bitwise or logical OR of integers.
@ Mul
Product of integers.
@ Xor
Bitwise or logical XOR of integers.
@ Add
Sum of integers.
DWARFExpression::Operation Op
ArrayRef(const T &OneElt) -> ArrayRef< T >
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
LLVM_ABI bool isOneConstant(SDValue V)
Returns true if V is a constant integer one.
Align commonAlignment(Align A, uint64_t Offset)
Returns the alignment that satisfies both alignments.
Definition Alignment.h:201
LLVM_ABI bool isAllOnesConstant(SDValue V)
Returns true if V is an integer constant with all bits set.
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition BitVector.h:880
#define N
Extended Value Type.
Definition ValueTypes.h:35
TypeSize getStoreSize() const
Return the number of bytes overwritten by a store of the specified value type.
Definition ValueTypes.h:418
bool isSimple() const
Test if the given EVT is simple (as opposed to being extended).
Definition ValueTypes.h:145
static EVT getVectorVT(LLVMContext &Context, EVT VT, unsigned NumElements, bool IsScalable=false)
Returns the EVT that represents a vector NumElements in length, where each element is of type VT.
Definition ValueTypes.h:70
bool bitsLT(EVT VT) const
Return true if this has less bits than VT.
Definition ValueTypes.h:323
ElementCount getVectorElementCount() const
Definition ValueTypes.h:373
TypeSize getSizeInBits() const
Return the size of the specified value type in bits.
Definition ValueTypes.h:396
bool isByteSized() const
Return true if the bit size is a multiple of 8.
Definition ValueTypes.h:266
unsigned getVectorMinNumElements() const
Given a vector type, return the minimum number of elements it contains.
Definition ValueTypes.h:382
uint64_t getScalarSizeInBits() const
Definition ValueTypes.h:408
TypeSize getStoreSizeInBits() const
Return the number of bits overwritten by a store of the specified value type.
Definition ValueTypes.h:435
EVT changeVectorElementType(LLVMContext &Context, EVT EltVT) const
Return a VT for a vector type whose attributes match ourselves with the exception of the element type...
Definition ValueTypes.h:98
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
Definition ValueTypes.h:339
static EVT getIntegerVT(LLVMContext &Context, unsigned BitWidth)
Returns the EVT that represents an integer with the given number of bits.
Definition ValueTypes.h:61
bool isVector() const
Return true if this is a vector value type.
Definition ValueTypes.h:176
EVT getScalarType() const
If this is a vector type, return the element type, otherwise return this.
Definition ValueTypes.h:346
bool bitsGE(EVT VT) const
Return true if this has no less bits than VT.
Definition ValueTypes.h:315
bool bitsEq(EVT VT) const
Return true if this has the same number of bits as VT.
Definition ValueTypes.h:279
LLVM_ABI Type * getTypeForEVT(LLVMContext &Context) const
This method returns an LLVM type corresponding to the specified EVT.
bool isScalableVector() const
Return true if this is a vector type where the runtime length is machine dependent.
Definition ValueTypes.h:187
EVT getVectorElementType() const
Given a vector type, return the type of each element.
Definition ValueTypes.h:351
EVT changeElementType(LLVMContext &Context, EVT EltVT) const
Return a VT for a type whose attributes match ourselves with the exception of the element type that i...
Definition ValueTypes.h:121
unsigned getVectorNumElements() const
Given a vector type, return the number of elements it contains.
Definition ValueTypes.h:359
bool bitsLE(EVT VT) const
Return true if this has no more bits than VT.
Definition ValueTypes.h:331
EVT getHalfNumVectorElementsVT(LLVMContext &Context) const
Definition ValueTypes.h:484
static LLVM_ABI MachinePointerInfo getUnknownStack(MachineFunction &MF)
Stack memory without other information.
static LLVM_ABI MachinePointerInfo getFixedStack(MachineFunction &MF, int FI, int64_t Offset=0)
Return a MachinePointerInfo record that refers to the specified FrameIndex.
static StringRef getLibcallImplName(RTLIB::LibcallImpl CallImpl)
Get the libcall routine name for the specified libcall implementation.
MakeLibCallOptions & setTypeListBeforeSoften(ArrayRef< EVT > OpsVT, EVT RetVT)
MakeLibCallOptions & setIsSigned(bool Value=true)