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