LLVM 23.0.0git
LegalizeDAG.cpp
Go to the documentation of this file.
1//===- LegalizeDAG.cpp - Implement SelectionDAG::Legalize -----------------===//
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 the SelectionDAG::Legalize method.
10//
11//===----------------------------------------------------------------------===//
12
13#include "llvm/ADT/APFloat.h"
14#include "llvm/ADT/APInt.h"
15#include "llvm/ADT/ArrayRef.h"
17#include "llvm/ADT/SetVector.h"
19#include "llvm/ADT/SmallSet.h"
21#include "llvm/ADT/StringRef.h"
37#include "llvm/IR/CallingConv.h"
38#include "llvm/IR/Constants.h"
39#include "llvm/IR/DataLayout.h"
41#include "llvm/IR/Function.h"
42#include "llvm/IR/Metadata.h"
43#include "llvm/IR/Type.h"
46#include "llvm/Support/Debug.h"
52#include <cassert>
53#include <cstdint>
54#include <tuple>
55#include <utility>
56
57using namespace llvm;
58
59#define DEBUG_TYPE "legalizedag"
60
61namespace {
62
63/// Keeps track of state when getting the sign of a floating-point value as an
64/// integer.
65struct FloatSignAsInt {
66 EVT FloatVT;
67 SDValue Chain;
68 SDValue FloatPtr;
69 SDValue IntPtr;
70 MachinePointerInfo IntPointerInfo;
71 MachinePointerInfo FloatPointerInfo;
72 SDValue IntValue;
73 APInt SignMask;
74 uint8_t SignBit;
75};
76
77//===----------------------------------------------------------------------===//
78/// This takes an arbitrary SelectionDAG as input and
79/// hacks on it until the target machine can handle it. This involves
80/// eliminating value sizes the machine cannot handle (promoting small sizes to
81/// large sizes or splitting up large values into small values) as well as
82/// eliminating operations the machine cannot handle.
83///
84/// This code also does a small amount of optimization and recognition of idioms
85/// as part of its processing. For example, if a target does not support a
86/// 'setcc' instruction efficiently, but does support 'brcc' instruction, this
87/// will attempt merge setcc and brc instructions into brcc's.
88class SelectionDAGLegalize {
89 const TargetMachine &TM;
90 const TargetLowering &TLI;
91 SelectionDAG &DAG;
92
93 /// The set of nodes which have already been legalized. We hold a
94 /// reference to it in order to update as necessary on node deletion.
95 SmallPtrSetImpl<SDNode *> &LegalizedNodes;
96
97 /// A set of all the nodes updated during legalization.
98 SmallSetVector<SDNode *, 16> *UpdatedNodes;
99
100 EVT getSetCCResultType(EVT VT) const {
101 return TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), VT);
102 }
103
104 // Libcall insertion helpers.
105
106public:
107 SelectionDAGLegalize(SelectionDAG &DAG,
108 SmallPtrSetImpl<SDNode *> &LegalizedNodes,
109 SmallSetVector<SDNode *, 16> *UpdatedNodes = nullptr)
110 : TM(DAG.getTarget()), TLI(DAG.getTargetLoweringInfo()), DAG(DAG),
111 LegalizedNodes(LegalizedNodes), UpdatedNodes(UpdatedNodes) {}
112
113 /// Legalizes the given operation.
114 void LegalizeOp(SDNode *Node);
115
116private:
117 SDValue OptimizeFloatStore(StoreSDNode *ST);
118
119 void LegalizeLoadOps(SDNode *Node);
120 void LegalizeStoreOps(SDNode *Node);
121
122 SDValue ExpandINSERT_VECTOR_ELT(SDValue Op);
123
124 /// Return a vector shuffle operation which
125 /// performs the same shuffe in terms of order or result bytes, but on a type
126 /// whose vector element type is narrower than the original shuffle type.
127 /// e.g. <v4i32> <0, 1, 0, 1> -> v8i16 <0, 1, 2, 3, 0, 1, 2, 3>
128 SDValue ShuffleWithNarrowerEltType(EVT NVT, EVT VT, const SDLoc &dl,
129 SDValue N1, SDValue N2,
130 ArrayRef<int> Mask) const;
131
132 std::pair<SDValue, SDValue> ExpandLibCall(RTLIB::Libcall LC, SDNode *Node,
134 bool IsSigned, EVT RetVT);
135 std::pair<SDValue, SDValue> ExpandLibCall(RTLIB::Libcall LC, SDNode *Node, bool isSigned);
136
137 void ExpandFPLibCall(SDNode *Node, RTLIB::Libcall LC,
139 void ExpandFPLibCall(SDNode *Node, RTLIB::Libcall Call_F32,
140 RTLIB::Libcall Call_F64, RTLIB::Libcall Call_F80,
141 RTLIB::Libcall Call_F128,
142 RTLIB::Libcall Call_PPCF128,
144
145 void
146 ExpandFastFPLibCall(SDNode *Node, bool IsFast,
147 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F32,
148 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F64,
149 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F80,
150 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F128,
151 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_PPCF128,
153
154 SDValue ExpandIntLibCall(SDNode *Node, bool isSigned, RTLIB::Libcall Call_I8,
155 RTLIB::Libcall Call_I16, RTLIB::Libcall Call_I32,
156 RTLIB::Libcall Call_I64, RTLIB::Libcall Call_I128);
157 void ExpandArgFPLibCall(SDNode *Node,
158 RTLIB::Libcall Call_F32, RTLIB::Libcall Call_F64,
159 RTLIB::Libcall Call_F80, RTLIB::Libcall Call_F128,
160 RTLIB::Libcall Call_PPCF128,
162 SDValue ExpandBitCountingLibCall(SDNode *Node, RTLIB::Libcall CallI32,
163 RTLIB::Libcall CallI64,
164 RTLIB::Libcall CallI128);
165 void ExpandDivRemLibCall(SDNode *Node, SmallVectorImpl<SDValue> &Results);
166
167 SDValue ExpandSincosStretLibCall(SDNode *Node) const;
168
169 SDValue EmitStackConvert(SDValue SrcOp, EVT SlotVT, EVT DestVT,
170 const SDLoc &dl);
171 SDValue EmitStackConvert(SDValue SrcOp, EVT SlotVT, EVT DestVT,
172 const SDLoc &dl, SDValue ChainIn);
173 SDValue ExpandBUILD_VECTOR(SDNode *Node);
174 SDValue ExpandSPLAT_VECTOR(SDNode *Node);
175 SDValue ExpandSCALAR_TO_VECTOR(SDNode *Node);
176 void ExpandDYNAMIC_STACKALLOC(SDNode *Node,
178 void getSignAsIntValue(FloatSignAsInt &State, const SDLoc &DL,
179 SDValue Value) const;
180 SDValue modifySignAsInt(const FloatSignAsInt &State, const SDLoc &DL,
181 SDValue NewIntValue) const;
182 SDValue ExpandFCOPYSIGN(SDNode *Node) const;
183 SDValue ExpandFABS(SDNode *Node) const;
184 SDValue ExpandFNEG(SDNode *Node) const;
185 SDValue expandLdexp(SDNode *Node) const;
186 SDValue expandFrexp(SDNode *Node) const;
187 SDValue expandModf(SDNode *Node) const;
188
189 SDValue ExpandLegalINT_TO_FP(SDNode *Node, SDValue &Chain);
190 void PromoteLegalINT_TO_FP(SDNode *N, const SDLoc &dl,
192 void PromoteLegalFP_TO_INT(SDNode *N, const SDLoc &dl,
194 SDValue PromoteLegalFP_TO_INT_SAT(SDNode *Node, const SDLoc &dl);
195
196 /// Implements vector reduce operation promotion.
197 ///
198 /// All vector operands are promoted to a vector type with larger element
199 /// type, and the start value is promoted to a larger scalar type. Then the
200 /// result is truncated back to the original scalar type.
201 SDValue PromoteReduction(SDNode *Node);
202
203 SDValue ExpandPARITY(SDValue Op, const SDLoc &dl);
204
205 SDValue ExpandExtractFromVectorThroughStack(SDValue Op);
206 SDValue ExpandInsertToVectorThroughStack(SDValue Op);
207 SDValue ExpandVectorBuildThroughStack(SDNode* Node);
208 SDValue ExpandConcatVectors(SDNode *Node);
209
210 SDValue ExpandConstantFP(ConstantFPSDNode *CFP, bool UseCP);
211 SDValue ExpandConstant(ConstantSDNode *CP);
212
213 // if ExpandNode returns false, LegalizeOp falls back to ConvertNodeToLibcall
214 bool ExpandNode(SDNode *Node);
215 void ConvertNodeToLibcall(SDNode *Node);
216 void PromoteNode(SDNode *Node);
217
218public:
219 // Node replacement helpers
220
221 void ReplacedNode(SDNode *N) {
222 LegalizedNodes.erase(N);
223 if (UpdatedNodes)
224 UpdatedNodes->insert(N);
225 }
226
227 void ReplaceNode(SDNode *Old, SDNode *New) {
228 LLVM_DEBUG(dbgs() << " ... replacing: "; Old->dump(&DAG);
229 dbgs() << " with: "; New->dump(&DAG));
230
231 assert(Old->getNumValues() == New->getNumValues() &&
232 "Replacing one node with another that produces a different number "
233 "of values!");
234 DAG.ReplaceAllUsesWith(Old, New);
235 if (UpdatedNodes)
236 UpdatedNodes->insert(New);
237 ReplacedNode(Old);
238 }
239
240 void ReplaceNode(SDValue Old, SDValue New) {
241 LLVM_DEBUG(dbgs() << " ... replacing: "; Old->dump(&DAG);
242 dbgs() << " with: "; New->dump(&DAG));
243
244 DAG.ReplaceAllUsesWith(Old, New);
245 if (UpdatedNodes)
246 UpdatedNodes->insert(New.getNode());
247 ReplacedNode(Old.getNode());
248 }
249
250 void ReplaceNode(SDNode *Old, const SDValue *New) {
251 LLVM_DEBUG(dbgs() << " ... replacing: "; Old->dump(&DAG));
252
253 DAG.ReplaceAllUsesWith(Old, New);
254 for (unsigned i = 0, e = Old->getNumValues(); i != e; ++i) {
255 LLVM_DEBUG(dbgs() << (i == 0 ? " with: " : " and: ");
256 New[i]->dump(&DAG));
257 if (UpdatedNodes)
258 UpdatedNodes->insert(New[i].getNode());
259 }
260 ReplacedNode(Old);
261 }
262
263 void ReplaceNodeWithValue(SDValue Old, SDValue New) {
264 LLVM_DEBUG(dbgs() << " ... replacing: "; Old->dump(&DAG);
265 dbgs() << " with: "; New->dump(&DAG));
266
267 DAG.ReplaceAllUsesOfValueWith(Old, New);
268 if (UpdatedNodes)
269 UpdatedNodes->insert(New.getNode());
270 ReplacedNode(Old.getNode());
271 }
272};
273
274} // end anonymous namespace
275
276// Helper function that generates an MMO that considers the alignment of the
277// stack, and the size of the stack object
279 MachineFunction &MF,
280 bool isObjectScalable) {
281 auto &MFI = MF.getFrameInfo();
282 int FI = cast<FrameIndexSDNode>(StackPtr)->getIndex();
284 LocationSize ObjectSize = isObjectScalable
286 : LocationSize::precise(MFI.getObjectSize(FI));
288 ObjectSize, MFI.getObjectAlign(FI));
289}
290
291/// Return a vector shuffle operation which
292/// performs the same shuffle in terms of order or result bytes, but on a type
293/// whose vector element type is narrower than the original shuffle type.
294/// e.g. <v4i32> <0, 1, 0, 1> -> v8i16 <0, 1, 2, 3, 0, 1, 2, 3>
295SDValue SelectionDAGLegalize::ShuffleWithNarrowerEltType(
296 EVT NVT, EVT VT, const SDLoc &dl, SDValue N1, SDValue N2,
297 ArrayRef<int> Mask) const {
298 unsigned NumMaskElts = VT.getVectorNumElements();
299 unsigned NumDestElts = NVT.getVectorNumElements();
300 unsigned NumEltsGrowth = NumDestElts / NumMaskElts;
301
302 assert(NumEltsGrowth && "Cannot promote to vector type with fewer elts!");
303
304 if (NumEltsGrowth == 1)
305 return DAG.getVectorShuffle(NVT, dl, N1, N2, Mask);
306
307 SmallVector<int, 8> NewMask;
308 for (unsigned i = 0; i != NumMaskElts; ++i) {
309 int Idx = Mask[i];
310 for (unsigned j = 0; j != NumEltsGrowth; ++j) {
311 if (Idx < 0)
312 NewMask.push_back(-1);
313 else
314 NewMask.push_back(Idx * NumEltsGrowth + j);
315 }
316 }
317 assert(NewMask.size() == NumDestElts && "Non-integer NumEltsGrowth?");
318 assert(TLI.isShuffleMaskLegal(NewMask, NVT) && "Shuffle not legal?");
319 return DAG.getVectorShuffle(NVT, dl, N1, N2, NewMask);
320}
321
322/// Expands the ConstantFP node to an integer constant or
323/// a load from the constant pool.
325SelectionDAGLegalize::ExpandConstantFP(ConstantFPSDNode *CFP, bool UseCP) {
326 bool Extend = false;
327 SDLoc dl(CFP);
328
329 // If a FP immediate is precise when represented as a float and if the
330 // target can do an extending load from float to double, we put it into
331 // the constant pool as a float, even if it's is statically typed as a
332 // double. This shrinks FP constants and canonicalizes them for targets where
333 // an FP extending load is the same cost as a normal load (such as on the x87
334 // fp stack or PPC FP unit).
335 EVT VT = CFP->getValueType(0);
336 ConstantFP *LLVMC = const_cast<ConstantFP*>(CFP->getConstantFPValue());
337 if (!UseCP) {
338 assert((VT == MVT::f64 || VT == MVT::f32) && "Invalid type expansion");
339 return DAG.getConstant(LLVMC->getValueAPF().bitcastToAPInt(), dl,
340 (VT == MVT::f64) ? MVT::i64 : MVT::i32);
341 }
342
343 APFloat APF = CFP->getValueAPF();
344 EVT OrigVT = VT;
345 EVT SVT = VT;
346
347 // We don't want to shrink SNaNs. Converting the SNaN back to its real type
348 // can cause it to be changed into a QNaN on some platforms (e.g. on SystemZ).
349 if (!APF.isSignaling()) {
350 while (SVT != MVT::f32 && SVT != MVT::f16 && SVT != MVT::bf16) {
351 SVT = (MVT::SimpleValueType)(SVT.getSimpleVT().SimpleTy - 1);
353 // Only do this if the target has a native EXTLOAD instruction from
354 // smaller type.
355 TLI.isLoadLegal(
356 OrigVT, SVT,
358 SVT.getTypeForEVT(*DAG.getContext()))),
360 .getAddrSpace(),
361 ISD::EXTLOAD, false) &&
362 TLI.ShouldShrinkFPConstant(OrigVT)) {
363 Type *SType = SVT.getTypeForEVT(*DAG.getContext());
365 Instruction::FPTrunc, LLVMC, SType, DAG.getDataLayout()));
366 VT = SVT;
367 Extend = true;
368 }
369 }
370 }
371
372 SDValue CPIdx =
373 DAG.getConstantPool(LLVMC, TLI.getPointerTy(DAG.getDataLayout()));
374 Align Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlign();
375 if (Extend) {
377 ISD::EXTLOAD, dl, OrigVT, DAG.getEntryNode(), CPIdx,
379 Alignment);
380 return Result;
381 }
382 SDValue Result = DAG.getLoad(
383 OrigVT, dl, DAG.getEntryNode(), CPIdx,
385 return Result;
386}
387
388/// Expands the Constant node to a load from the constant pool.
389SDValue SelectionDAGLegalize::ExpandConstant(ConstantSDNode *CP) {
390 SDLoc dl(CP);
391 EVT VT = CP->getValueType(0);
393 TLI.getPointerTy(DAG.getDataLayout()));
394 Align Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlign();
395 SDValue Result = DAG.getLoad(
396 VT, dl, DAG.getEntryNode(), CPIdx,
398 return Result;
399}
400
401SDValue SelectionDAGLegalize::ExpandINSERT_VECTOR_ELT(SDValue Op) {
402 SDValue Vec = Op.getOperand(0);
403 SDValue Val = Op.getOperand(1);
404 SDValue Idx = Op.getOperand(2);
405 SDLoc dl(Op);
406
407 if (ConstantSDNode *InsertPos = dyn_cast<ConstantSDNode>(Idx)) {
408 // SCALAR_TO_VECTOR requires that the type of the value being inserted
409 // match the element type of the vector being created, except for
410 // integers in which case the inserted value can be over width.
411 EVT EltVT = Vec.getValueType().getVectorElementType();
412 if (Val.getValueType() == EltVT ||
413 (EltVT.isInteger() && Val.getValueType().bitsGE(EltVT))) {
414 SDValue ScVec = DAG.getNode(ISD::SCALAR_TO_VECTOR, dl,
415 Vec.getValueType(), Val);
416
417 unsigned NumElts = Vec.getValueType().getVectorNumElements();
418 // We generate a shuffle of InVec and ScVec, so the shuffle mask
419 // should be 0,1,2,3,4,5... with the appropriate element replaced with
420 // elt 0 of the RHS.
421 SmallVector<int, 8> ShufOps;
422 for (unsigned i = 0; i != NumElts; ++i)
423 ShufOps.push_back(i != InsertPos->getZExtValue() ? i : NumElts);
424
425 return DAG.getVectorShuffle(Vec.getValueType(), dl, Vec, ScVec, ShufOps);
426 }
427 }
428 return ExpandInsertToVectorThroughStack(Op);
429}
430
431SDValue SelectionDAGLegalize::OptimizeFloatStore(StoreSDNode* ST) {
432 if (!ISD::isNormalStore(ST))
433 return SDValue();
434
435 LLVM_DEBUG(dbgs() << "Optimizing float store operations\n");
436 // Turn 'store float 1.0, Ptr' -> 'store int 0x12345678, Ptr'
437 // FIXME: move this to the DAG Combiner! Note that we can't regress due
438 // to phase ordering between legalized code and the dag combiner. This
439 // probably means that we need to integrate dag combiner and legalizer
440 // together.
441 // We generally can't do this one for long doubles.
442 SDValue Chain = ST->getChain();
443 SDValue Ptr = ST->getBasePtr();
444 SDValue Value = ST->getValue();
445 MachineMemOperand::Flags MMOFlags = ST->getMemOperand()->getFlags();
446 AAMDNodes AAInfo = ST->getAAInfo();
447 SDLoc dl(ST);
448
449 // Don't optimise TargetConstantFP
450 if (Value.getOpcode() == ISD::TargetConstantFP)
451 return SDValue();
452
453 if (ConstantFPSDNode *CFP = dyn_cast<ConstantFPSDNode>(Value)) {
454 if (CFP->getValueType(0) == MVT::f32 &&
455 TLI.isTypeLegal(MVT::i32)) {
456 SDValue Con = DAG.getConstant(CFP->getValueAPF().
457 bitcastToAPInt().zextOrTrunc(32),
458 SDLoc(CFP), MVT::i32);
459 return DAG.getStore(Chain, dl, Con, Ptr, ST->getPointerInfo(),
460 ST->getBaseAlign(), MMOFlags, AAInfo);
461 }
462
463 if (CFP->getValueType(0) == MVT::f64 &&
464 !TLI.isFPImmLegal(CFP->getValueAPF(), MVT::f64)) {
465 // If this target supports 64-bit registers, do a single 64-bit store.
466 if (TLI.isTypeLegal(MVT::i64)) {
468 zextOrTrunc(64), SDLoc(CFP), MVT::i64);
469 return DAG.getStore(Chain, dl, Con, Ptr, ST->getPointerInfo(),
470 ST->getBaseAlign(), MMOFlags, AAInfo);
471 }
472
473 if (TLI.isTypeLegal(MVT::i32) && !ST->isVolatile()) {
474 // Otherwise, if the target supports 32-bit registers, use 2 32-bit
475 // stores. If the target supports neither 32- nor 64-bits, this
476 // xform is certainly not worth it.
477 const APInt &IntVal = CFP->getValueAPF().bitcastToAPInt();
478 SDValue Lo = DAG.getConstant(IntVal.trunc(32), dl, MVT::i32);
479 SDValue Hi = DAG.getConstant(IntVal.lshr(32).trunc(32), dl, MVT::i32);
480 if (DAG.getDataLayout().isBigEndian())
481 std::swap(Lo, Hi);
482
483 Lo = DAG.getStore(Chain, dl, Lo, Ptr, ST->getPointerInfo(),
484 ST->getBaseAlign(), MMOFlags, AAInfo);
485 Ptr = DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(4), dl);
486 Hi = DAG.getStore(Chain, dl, Hi, Ptr,
487 ST->getPointerInfo().getWithOffset(4),
488 ST->getBaseAlign(), MMOFlags, AAInfo);
489
490 return DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
491 }
492 }
493 }
494 return SDValue();
495}
496
497void SelectionDAGLegalize::LegalizeStoreOps(SDNode *Node) {
498 StoreSDNode *ST = cast<StoreSDNode>(Node);
499 SDValue Chain = ST->getChain();
500 SDValue Ptr = ST->getBasePtr();
501 SDLoc dl(Node);
502
503 MachineMemOperand::Flags MMOFlags = ST->getMemOperand()->getFlags();
504 AAMDNodes AAInfo = ST->getAAInfo();
505
506 if (!ST->isTruncatingStore()) {
507 LLVM_DEBUG(dbgs() << "Legalizing store operation\n");
508 if (SDNode *OptStore = OptimizeFloatStore(ST).getNode()) {
509 ReplaceNode(ST, OptStore);
510 return;
511 }
512
513 SDValue Value = ST->getValue();
514 MVT VT = Value.getSimpleValueType();
515 switch (TLI.getOperationAction(ISD::STORE, VT)) {
516 default: llvm_unreachable("This action is not supported yet!");
517 case TargetLowering::Legal: {
518 // If this is an unaligned store and the target doesn't support it,
519 // expand it.
520 EVT MemVT = ST->getMemoryVT();
521 const DataLayout &DL = DAG.getDataLayout();
522 if (!TLI.allowsMemoryAccessForAlignment(*DAG.getContext(), DL, MemVT,
523 *ST->getMemOperand())) {
524 LLVM_DEBUG(dbgs() << "Expanding unsupported unaligned store\n");
525 SDValue Result = TLI.expandUnalignedStore(ST, DAG);
526 ReplaceNode(SDValue(ST, 0), Result);
527 } else
528 LLVM_DEBUG(dbgs() << "Legal store\n");
529 break;
530 }
531 case TargetLowering::Custom: {
532 LLVM_DEBUG(dbgs() << "Trying custom lowering\n");
533 SDValue Res = TLI.LowerOperation(SDValue(Node, 0), DAG);
534 if (Res && Res != SDValue(Node, 0))
535 ReplaceNode(SDValue(Node, 0), Res);
536 return;
537 }
538 case TargetLowering::Promote: {
539 MVT NVT = TLI.getTypeToPromoteTo(ISD::STORE, VT);
540 assert(NVT.getSizeInBits() == VT.getSizeInBits() &&
541 "Can only promote stores to same size type");
542 Value = DAG.getNode(ISD::BITCAST, dl, NVT, Value);
543 SDValue Result = DAG.getStore(Chain, dl, Value, Ptr, ST->getPointerInfo(),
544 ST->getBaseAlign(), MMOFlags, AAInfo);
545 ReplaceNode(SDValue(Node, 0), Result);
546 break;
547 }
548 }
549 return;
550 }
551
552 LLVM_DEBUG(dbgs() << "Legalizing truncating store operations\n");
553 SDValue Value = ST->getValue();
554 EVT StVT = ST->getMemoryVT();
555 TypeSize StWidth = StVT.getSizeInBits();
556 TypeSize StSize = StVT.getStoreSizeInBits();
557 auto &DL = DAG.getDataLayout();
558
559 if (StWidth != StSize) {
560 // Promote to a byte-sized store with upper bits zero if not
561 // storing an integral number of bytes. For example, promote
562 // TRUNCSTORE:i1 X -> TRUNCSTORE:i8 (and X, 1)
563 EVT NVT = EVT::getIntegerVT(*DAG.getContext(), StSize.getFixedValue());
564 Value = DAG.getZeroExtendInReg(Value, dl, StVT);
566 DAG.getTruncStore(Chain, dl, Value, Ptr, ST->getPointerInfo(), NVT,
567 ST->getBaseAlign(), MMOFlags, AAInfo);
568 ReplaceNode(SDValue(Node, 0), Result);
569 } else if (!StVT.isVector() && !isPowerOf2_64(StWidth.getFixedValue())) {
570 // If not storing a power-of-2 number of bits, expand as two stores.
571 assert(!StVT.isVector() && "Unsupported truncstore!");
572 unsigned StWidthBits = StWidth.getFixedValue();
573 unsigned LogStWidth = Log2_32(StWidthBits);
574 assert(LogStWidth < 32);
575 unsigned RoundWidth = 1 << LogStWidth;
576 assert(RoundWidth < StWidthBits);
577 unsigned ExtraWidth = StWidthBits - RoundWidth;
578 assert(ExtraWidth < RoundWidth);
579 assert(!(RoundWidth % 8) && !(ExtraWidth % 8) &&
580 "Store size not an integral number of bytes!");
581 EVT RoundVT = EVT::getIntegerVT(*DAG.getContext(), RoundWidth);
582 EVT ExtraVT = EVT::getIntegerVT(*DAG.getContext(), ExtraWidth);
583 SDValue Lo, Hi;
584 unsigned IncrementSize;
585
586 if (DL.isLittleEndian()) {
587 // TRUNCSTORE:i24 X -> TRUNCSTORE:i16 X, TRUNCSTORE@+2:i8 (srl X, 16)
588 // Store the bottom RoundWidth bits.
589 Lo = DAG.getTruncStore(Chain, dl, Value, Ptr, ST->getPointerInfo(),
590 RoundVT, ST->getBaseAlign(), MMOFlags, AAInfo);
591
592 // Store the remaining ExtraWidth bits.
593 IncrementSize = RoundWidth / 8;
594 Ptr =
595 DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(IncrementSize), dl);
596 Hi = DAG.getNode(
597 ISD::SRL, dl, Value.getValueType(), Value,
598 DAG.getShiftAmountConstant(RoundWidth, Value.getValueType(), dl));
599 Hi = DAG.getTruncStore(Chain, dl, Hi, Ptr,
600 ST->getPointerInfo().getWithOffset(IncrementSize),
601 ExtraVT, ST->getBaseAlign(), MMOFlags, AAInfo);
602 } else {
603 // Big endian - avoid unaligned stores.
604 // TRUNCSTORE:i24 X -> TRUNCSTORE:i16 (srl X, 8), TRUNCSTORE@+2:i8 X
605 // Store the top RoundWidth bits.
606 Hi = DAG.getNode(
607 ISD::SRL, dl, Value.getValueType(), Value,
608 DAG.getShiftAmountConstant(ExtraWidth, Value.getValueType(), dl));
609 Hi = DAG.getTruncStore(Chain, dl, Hi, Ptr, ST->getPointerInfo(), RoundVT,
610 ST->getBaseAlign(), MMOFlags, AAInfo);
611
612 // Store the remaining ExtraWidth bits.
613 IncrementSize = RoundWidth / 8;
614 Ptr = DAG.getNode(ISD::ADD, dl, Ptr.getValueType(), Ptr,
615 DAG.getConstant(IncrementSize, dl,
616 Ptr.getValueType()));
617 Lo = DAG.getTruncStore(Chain, dl, Value, Ptr,
618 ST->getPointerInfo().getWithOffset(IncrementSize),
619 ExtraVT, ST->getBaseAlign(), MMOFlags, AAInfo);
620 }
621
622 // The order of the stores doesn't matter.
623 SDValue Result = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
624 ReplaceNode(SDValue(Node, 0), Result);
625 } else {
626 switch (TLI.getTruncStoreAction(ST->getValue().getValueType(), StVT,
627 ST->getAlign(), ST->getAddressSpace())) {
628 default:
629 llvm_unreachable("This action is not supported yet!");
630 case TargetLowering::Legal: {
631 EVT MemVT = ST->getMemoryVT();
632 // If this is an unaligned store and the target doesn't support it,
633 // expand it.
634 if (!TLI.allowsMemoryAccessForAlignment(*DAG.getContext(), DL, MemVT,
635 *ST->getMemOperand())) {
636 SDValue Result = TLI.expandUnalignedStore(ST, DAG);
637 ReplaceNode(SDValue(ST, 0), Result);
638 }
639 break;
640 }
641 case TargetLowering::Custom: {
642 SDValue Res = TLI.LowerOperation(SDValue(Node, 0), DAG);
643 if (Res && Res != SDValue(Node, 0))
644 ReplaceNode(SDValue(Node, 0), Res);
645 return;
646 }
647 case TargetLowering::Expand:
648 assert(!StVT.isVector() &&
649 "Vector Stores are handled in LegalizeVectorOps");
650
652
653 // TRUNCSTORE:i16 i32 -> STORE i16
654 if (TLI.isTypeLegal(StVT)) {
655 Value = DAG.getNode(ISD::TRUNCATE, dl, StVT, Value);
656 Result = DAG.getStore(Chain, dl, Value, Ptr, ST->getPointerInfo(),
657 ST->getBaseAlign(), MMOFlags, AAInfo);
658 } else {
659 // The in-memory type isn't legal. Truncate to the type it would promote
660 // to, and then do a truncstore.
661 Value = DAG.getNode(ISD::TRUNCATE, dl,
662 TLI.getTypeToTransformTo(*DAG.getContext(), StVT),
663 Value);
664 Result = DAG.getTruncStore(Chain, dl, Value, Ptr, ST->getPointerInfo(),
665 StVT, ST->getBaseAlign(), MMOFlags, AAInfo);
666 }
667
668 ReplaceNode(SDValue(Node, 0), Result);
669 break;
670 }
671 }
672}
673
674void SelectionDAGLegalize::LegalizeLoadOps(SDNode *Node) {
675 LoadSDNode *LD = cast<LoadSDNode>(Node);
676 SDValue Chain = LD->getChain(); // The chain.
677 SDValue Ptr = LD->getBasePtr(); // The base pointer.
678 SDValue Value; // The value returned by the load op.
679 SDLoc dl(Node);
680
681 ISD::LoadExtType ExtType = LD->getExtensionType();
682 if (ExtType == ISD::NON_EXTLOAD) {
683 LLVM_DEBUG(dbgs() << "Legalizing non-extending load operation\n");
684 MVT VT = Node->getSimpleValueType(0);
685 SDValue RVal = SDValue(Node, 0);
686 SDValue RChain = SDValue(Node, 1);
687
688 switch (TLI.getOperationAction(Node->getOpcode(), VT)) {
689 default: llvm_unreachable("This action is not supported yet!");
690 case TargetLowering::Legal: {
691 EVT MemVT = LD->getMemoryVT();
692 const DataLayout &DL = DAG.getDataLayout();
693 // If this is an unaligned load and the target doesn't support it,
694 // expand it.
695 if (!TLI.allowsMemoryAccessForAlignment(*DAG.getContext(), DL, MemVT,
696 *LD->getMemOperand())) {
697 std::tie(RVal, RChain) = TLI.expandUnalignedLoad(LD, DAG);
698 }
699 break;
700 }
701 case TargetLowering::Custom:
702 if (SDValue Res = TLI.LowerOperation(RVal, DAG)) {
703 RVal = Res;
704 RChain = Res.getValue(1);
705 }
706 break;
707
708 case TargetLowering::Promote: {
709 MVT NVT = TLI.getTypeToPromoteTo(Node->getOpcode(), VT);
710 assert(NVT.getSizeInBits() == VT.getSizeInBits() &&
711 "Can only promote loads to same size type");
712
713 // If the range metadata type does not match the legalized memory
714 // operation type, remove the range metadata.
715 if (const MDNode *MD = LD->getRanges()) {
716 ConstantInt *Lower = mdconst::extract<ConstantInt>(MD->getOperand(0));
717 if (Lower->getBitWidth() != NVT.getScalarSizeInBits() ||
718 !NVT.isInteger())
719 LD->getMemOperand()->clearRanges();
720 }
721 SDValue Res = DAG.getLoad(NVT, dl, Chain, Ptr, LD->getMemOperand());
722 RVal = DAG.getNode(ISD::BITCAST, dl, VT, Res);
723 RChain = Res.getValue(1);
724 break;
725 }
726 }
727 if (RChain.getNode() != Node) {
728 assert(RVal.getNode() != Node && "Load must be completely replaced");
729 DAG.ReplaceAllUsesOfValueWith(SDValue(Node, 0), RVal);
730 DAG.ReplaceAllUsesOfValueWith(SDValue(Node, 1), RChain);
731 if (UpdatedNodes) {
732 UpdatedNodes->insert(RVal.getNode());
733 UpdatedNodes->insert(RChain.getNode());
734 }
735 ReplacedNode(Node);
736 }
737 return;
738 }
739
740 LLVM_DEBUG(dbgs() << "Legalizing extending load operation\n");
741 EVT SrcVT = LD->getMemoryVT();
742 TypeSize SrcWidth = SrcVT.getSizeInBits();
743 MachineMemOperand::Flags MMOFlags = LD->getMemOperand()->getFlags();
744 AAMDNodes AAInfo = LD->getAAInfo();
745
746 if (SrcWidth != SrcVT.getStoreSizeInBits() &&
747 // Some targets pretend to have an i1 loading operation, and actually
748 // load an i8. This trick is correct for ZEXTLOAD because the top 7
749 // bits are guaranteed to be zero; it helps the optimizers understand
750 // that these bits are zero. It is also useful for EXTLOAD, since it
751 // tells the optimizers that those bits are undefined. It would be
752 // nice to have an effective generic way of getting these benefits...
753 // Until such a way is found, don't insist on promoting i1 here.
754 (SrcVT != MVT::i1 ||
755 TLI.getLoadAction(Node->getValueType(0), MVT::i1, LD->getAlign(),
756 LD->getAddressSpace(), ExtType,
757 false) == TargetLowering::Promote)) {
758 // Promote to a byte-sized load if not loading an integral number of
759 // bytes. For example, promote EXTLOAD:i20 -> EXTLOAD:i24.
760 unsigned NewWidth = SrcVT.getStoreSizeInBits();
761 EVT NVT = EVT::getIntegerVT(*DAG.getContext(), NewWidth);
762 SDValue Ch;
763
764 // The extra bits are guaranteed to be zero, since we stored them that
765 // way. A zext load from NVT thus automatically gives zext from SrcVT.
766
767 ISD::LoadExtType NewExtType =
769
770 SDValue Result = DAG.getExtLoad(NewExtType, dl, Node->getValueType(0),
771 Chain, Ptr, LD->getPointerInfo(), NVT,
772 LD->getBaseAlign(), MMOFlags, AAInfo);
773
774 Ch = Result.getValue(1); // The chain.
775
776 if (ExtType == ISD::SEXTLOAD)
777 // Having the top bits zero doesn't help when sign extending.
779 Result.getValueType(),
780 Result, DAG.getValueType(SrcVT));
781 else if (ExtType == ISD::ZEXTLOAD || NVT == Result.getValueType())
782 // All the top bits are guaranteed to be zero - inform the optimizers.
784 Result.getValueType(), Result,
785 DAG.getValueType(SrcVT));
786
787 Value = Result;
788 Chain = Ch;
789 } else if (!isPowerOf2_64(SrcWidth.getKnownMinValue())) {
790 // If not loading a power-of-2 number of bits, expand as two loads.
791 assert(!SrcVT.isVector() && "Unsupported extload!");
792 unsigned SrcWidthBits = SrcWidth.getFixedValue();
793 unsigned LogSrcWidth = Log2_32(SrcWidthBits);
794 assert(LogSrcWidth < 32);
795 unsigned RoundWidth = 1 << LogSrcWidth;
796 assert(RoundWidth < SrcWidthBits);
797 unsigned ExtraWidth = SrcWidthBits - RoundWidth;
798 assert(ExtraWidth < RoundWidth);
799 assert(!(RoundWidth % 8) && !(ExtraWidth % 8) &&
800 "Load size not an integral number of bytes!");
801 EVT RoundVT = EVT::getIntegerVT(*DAG.getContext(), RoundWidth);
802 EVT ExtraVT = EVT::getIntegerVT(*DAG.getContext(), ExtraWidth);
803 SDValue Lo, Hi, Ch;
804 unsigned IncrementSize;
805 auto &DL = DAG.getDataLayout();
806
807 if (DL.isLittleEndian()) {
808 // EXTLOAD:i24 -> ZEXTLOAD:i16 | (shl EXTLOAD@+2:i8, 16)
809 // Load the bottom RoundWidth bits.
810 Lo = DAG.getExtLoad(ISD::ZEXTLOAD, dl, Node->getValueType(0), Chain, Ptr,
811 LD->getPointerInfo(), RoundVT, LD->getBaseAlign(),
812 MMOFlags, AAInfo);
813
814 // Load the remaining ExtraWidth bits.
815 IncrementSize = RoundWidth / 8;
816 Ptr =
817 DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(IncrementSize), dl);
818 Hi = DAG.getExtLoad(ExtType, dl, Node->getValueType(0), Chain, Ptr,
819 LD->getPointerInfo().getWithOffset(IncrementSize),
820 ExtraVT, LD->getBaseAlign(), MMOFlags, AAInfo);
821
822 // Build a factor node to remember that this load is independent of
823 // the other one.
824 Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
825 Hi.getValue(1));
826
827 // Move the top bits to the right place.
828 Hi = DAG.getNode(
829 ISD::SHL, dl, Hi.getValueType(), Hi,
830 DAG.getShiftAmountConstant(RoundWidth, Hi.getValueType(), dl));
831
832 // Join the hi and lo parts.
833 Value = DAG.getNode(ISD::OR, dl, Node->getValueType(0), Lo, Hi);
834 } else {
835 // Big endian - avoid unaligned loads.
836 // EXTLOAD:i24 -> (shl EXTLOAD:i16, 8) | ZEXTLOAD@+2:i8
837 // Load the top RoundWidth bits.
838 Hi = DAG.getExtLoad(ExtType, dl, Node->getValueType(0), Chain, Ptr,
839 LD->getPointerInfo(), RoundVT, LD->getBaseAlign(),
840 MMOFlags, AAInfo);
841
842 // Load the remaining ExtraWidth bits.
843 IncrementSize = RoundWidth / 8;
844 Ptr =
845 DAG.getMemBasePlusOffset(Ptr, TypeSize::getFixed(IncrementSize), dl);
846 Lo = DAG.getExtLoad(ISD::ZEXTLOAD, dl, Node->getValueType(0), Chain, Ptr,
847 LD->getPointerInfo().getWithOffset(IncrementSize),
848 ExtraVT, LD->getBaseAlign(), MMOFlags, AAInfo);
849
850 // Build a factor node to remember that this load is independent of
851 // the other one.
852 Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
853 Hi.getValue(1));
854
855 // Move the top bits to the right place.
856 Hi = DAG.getNode(
857 ISD::SHL, dl, Hi.getValueType(), Hi,
858 DAG.getShiftAmountConstant(ExtraWidth, Hi.getValueType(), dl));
859
860 // Join the hi and lo parts.
861 Value = DAG.getNode(ISD::OR, dl, Node->getValueType(0), Lo, Hi);
862 }
863
864 Chain = Ch;
865 } else {
866 bool isCustom = false;
867 switch (TLI.getLoadAction(Node->getValueType(0), SrcVT.getSimpleVT(),
868 LD->getAlign(), LD->getAddressSpace(), ExtType,
869 false)) {
870 default:
871 llvm_unreachable("This action is not supported yet!");
872 case TargetLowering::Custom:
873 isCustom = true;
874 [[fallthrough]];
875 case TargetLowering::Legal:
876 Value = SDValue(Node, 0);
877 Chain = SDValue(Node, 1);
878
879 if (isCustom) {
880 if (SDValue Res = TLI.LowerOperation(SDValue(Node, 0), DAG)) {
881 Value = Res;
882 Chain = Res.getValue(1);
883 }
884 } else {
885 // If this is an unaligned load and the target doesn't support it,
886 // expand it.
887 EVT MemVT = LD->getMemoryVT();
888 const DataLayout &DL = DAG.getDataLayout();
889 if (!TLI.allowsMemoryAccess(*DAG.getContext(), DL, MemVT,
890 *LD->getMemOperand())) {
891 std::tie(Value, Chain) = TLI.expandUnalignedLoad(LD, DAG);
892 }
893 }
894 break;
895
896 case TargetLowering::Expand: {
897 EVT DestVT = Node->getValueType(0);
898 if (!TLI.isLoadLegal(DestVT, SrcVT, LD->getAlign(), LD->getAddressSpace(),
899 ISD::EXTLOAD, false)) {
900 // If the source type is not legal, see if there is a legal extload to
901 // an intermediate type that we can then extend further.
902 EVT LoadVT = TLI.getRegisterType(SrcVT.getSimpleVT());
903 if ((LoadVT.isFloatingPoint() == SrcVT.isFloatingPoint()) &&
904 (TLI.isTypeLegal(SrcVT) || // Same as SrcVT == LoadVT?
905 TLI.isLoadLegal(LoadVT, SrcVT, LD->getAlign(),
906 LD->getAddressSpace(), ExtType, false))) {
907 // If we are loading a legal type, this is a non-extload followed by a
908 // full extend.
909 ISD::LoadExtType MidExtType =
910 (LoadVT == SrcVT) ? ISD::NON_EXTLOAD : ExtType;
911
912 SDValue Load = DAG.getExtLoad(MidExtType, dl, LoadVT, Chain, Ptr,
913 SrcVT, LD->getMemOperand());
914 unsigned ExtendOp =
916 Value = DAG.getNode(ExtendOp, dl, Node->getValueType(0), Load);
917 Chain = Load.getValue(1);
918 break;
919 }
920
921 // Handle the special case of fp16 extloads. EXTLOAD doesn't have the
922 // normal undefined upper bits behavior to allow using an in-reg extend
923 // with the illegal FP type, so load as an integer and do the
924 // from-integer conversion.
925 EVT SVT = SrcVT.getScalarType();
926 if (SVT == MVT::f16 || SVT == MVT::bf16) {
927 EVT ISrcVT = SrcVT.changeTypeToInteger();
928 EVT IDestVT = DestVT.changeTypeToInteger();
929 EVT ILoadVT = TLI.getRegisterType(IDestVT.getSimpleVT());
930
931 SDValue Result = DAG.getExtLoad(ISD::ZEXTLOAD, dl, ILoadVT, Chain,
932 Ptr, ISrcVT, LD->getMemOperand());
933 Value =
934 DAG.getNode(SVT == MVT::f16 ? ISD::FP16_TO_FP : ISD::BF16_TO_FP,
935 dl, DestVT, Result);
936 Chain = Result.getValue(1);
937 break;
938 }
939 }
940
941 assert(!SrcVT.isVector() &&
942 "Vector Loads are handled in LegalizeVectorOps");
943
944 // FIXME: This does not work for vectors on most targets. Sign-
945 // and zero-extend operations are currently folded into extending
946 // loads, whether they are legal or not, and then we end up here
947 // without any support for legalizing them.
948 assert(ExtType != ISD::EXTLOAD &&
949 "EXTLOAD should always be supported!");
950 // Turn the unsupported load into an EXTLOAD followed by an
951 // explicit zero/sign extend inreg.
953 Node->getValueType(0),
954 Chain, Ptr, SrcVT,
955 LD->getMemOperand());
956 SDValue ValRes;
957 if (ExtType == ISD::SEXTLOAD)
958 ValRes = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl,
959 Result.getValueType(),
960 Result, DAG.getValueType(SrcVT));
961 else
962 ValRes = DAG.getZeroExtendInReg(Result, dl, SrcVT);
963 Value = ValRes;
964 Chain = Result.getValue(1);
965 break;
966 }
967 }
968 }
969
970 // Since loads produce two values, make sure to remember that we legalized
971 // both of them.
972 if (Chain.getNode() != Node) {
973 assert(Value.getNode() != Node && "Load must be completely replaced");
975 DAG.ReplaceAllUsesOfValueWith(SDValue(Node, 1), Chain);
976 if (UpdatedNodes) {
977 UpdatedNodes->insert(Value.getNode());
978 UpdatedNodes->insert(Chain.getNode());
979 }
980 ReplacedNode(Node);
981 }
982}
983
984/// Return a legal replacement for the given operation, with all legal operands.
985void SelectionDAGLegalize::LegalizeOp(SDNode *Node) {
986 LLVM_DEBUG(dbgs() << "\nLegalizing: "; Node->dump(&DAG));
987
988 // Allow illegal target nodes and illegal registers.
989 if (Node->getOpcode() == ISD::TargetConstant ||
990 Node->getOpcode() == ISD::Register)
991 return;
992
993#ifndef NDEBUG
994 for (unsigned i = 0, e = Node->getNumValues(); i != e; ++i)
995 assert(TLI.getTypeAction(*DAG.getContext(), Node->getValueType(i)) ==
996 TargetLowering::TypeLegal &&
997 "Unexpected illegal type!");
998
999 for (const SDValue &Op : Node->op_values())
1000 assert((TLI.getTypeAction(*DAG.getContext(), Op.getValueType()) ==
1001 TargetLowering::TypeLegal ||
1002 Op.getOpcode() == ISD::TargetConstant ||
1003 Op.getOpcode() == ISD::Register) &&
1004 "Unexpected illegal type!");
1005#endif
1006
1007 // Figure out the correct action; the way to query this varies by opcode
1008 TargetLowering::LegalizeAction Action = TargetLowering::Legal;
1009 bool SimpleFinishLegalizing = true;
1010 switch (Node->getOpcode()) {
1011 case ISD::POISON: {
1012 // TODO: Currently, POISON is being lowered to UNDEF here. However, there is
1013 // an open concern that this transformation may not be ideal, as targets
1014 // should ideally handle POISON directly. Changing this behavior would
1015 // require adding support for POISON in TableGen, which is a large change.
1016 // Additionally, many existing test cases rely on the current behavior
1017 // (e.g., llvm/test/CodeGen/PowerPC/vec_shuffle.ll). A broader discussion
1018 // and incremental changes might be needed to properly support POISON
1019 // without breaking existing targets and tests.
1020 SDValue UndefNode = DAG.getUNDEF(Node->getValueType(0));
1021 ReplaceNode(Node, UndefNode.getNode());
1022 return;
1023 }
1027 case ISD::STACKSAVE:
1028 case ISD::STACKADDRESS:
1029 Action = TLI.getOperationAction(Node->getOpcode(), MVT::Other);
1030 break;
1032 Action = TLI.getOperationAction(Node->getOpcode(),
1033 Node->getValueType(0));
1034 break;
1035 case ISD::VAARG:
1036 Action = TLI.getOperationAction(Node->getOpcode(),
1037 Node->getValueType(0));
1038 if (Action != TargetLowering::Promote)
1039 Action = TLI.getOperationAction(Node->getOpcode(), MVT::Other);
1040 break;
1041 case ISD::SET_FPENV:
1042 case ISD::SET_FPMODE:
1043 Action = TLI.getOperationAction(Node->getOpcode(),
1044 Node->getOperand(1).getValueType());
1045 break;
1046 case ISD::FP_TO_FP16:
1047 case ISD::FP_TO_BF16:
1048 case ISD::SINT_TO_FP:
1049 case ISD::UINT_TO_FP:
1051 case ISD::LROUND:
1052 case ISD::LLROUND:
1053 case ISD::LRINT:
1054 case ISD::LLRINT:
1055 Action = TLI.getOperationAction(Node->getOpcode(),
1056 Node->getOperand(0).getValueType());
1057 break;
1062 case ISD::STRICT_LRINT:
1063 case ISD::STRICT_LLRINT:
1064 case ISD::STRICT_LROUND:
1066 // These pseudo-ops are the same as the other STRICT_ ops except
1067 // they are registered with setOperationAction() using the input type
1068 // instead of the output type.
1069 Action = TLI.getOperationAction(Node->getOpcode(),
1070 Node->getOperand(1).getValueType());
1071 break;
1073 EVT InnerType = cast<VTSDNode>(Node->getOperand(1))->getVT();
1074 Action = TLI.getOperationAction(Node->getOpcode(), InnerType);
1075 break;
1076 }
1077 case ISD::ATOMIC_STORE:
1078 Action = TLI.getOperationAction(Node->getOpcode(),
1079 Node->getOperand(1).getValueType());
1080 break;
1081 case ISD::SELECT_CC:
1082 case ISD::STRICT_FSETCC:
1084 case ISD::SETCC:
1085 case ISD::SETCCCARRY:
1086 case ISD::VP_SETCC:
1087 case ISD::BR_CC: {
1088 unsigned Opc = Node->getOpcode();
1089 unsigned CCOperand = Opc == ISD::SELECT_CC ? 4
1090 : Opc == ISD::STRICT_FSETCC ? 3
1091 : Opc == ISD::STRICT_FSETCCS ? 3
1092 : Opc == ISD::SETCCCARRY ? 3
1093 : (Opc == ISD::SETCC || Opc == ISD::VP_SETCC) ? 2
1094 : 1;
1095 unsigned CompareOperand = Opc == ISD::BR_CC ? 2
1096 : Opc == ISD::STRICT_FSETCC ? 1
1097 : Opc == ISD::STRICT_FSETCCS ? 1
1098 : 0;
1099 MVT OpVT = Node->getOperand(CompareOperand).getSimpleValueType();
1100 ISD::CondCode CCCode =
1101 cast<CondCodeSDNode>(Node->getOperand(CCOperand))->get();
1102 Action = TLI.getCondCodeAction(CCCode, OpVT);
1103 if (Action == TargetLowering::Legal) {
1104 if (Node->getOpcode() == ISD::SELECT_CC)
1105 Action = TLI.getOperationAction(Node->getOpcode(),
1106 Node->getValueType(0));
1107 else
1108 Action = TLI.getOperationAction(Node->getOpcode(), OpVT);
1109 }
1110 break;
1111 }
1112 case ISD::LOAD:
1113 case ISD::STORE:
1114 // FIXME: Model these properly. LOAD and STORE are complicated, and
1115 // STORE expects the unlegalized operand in some cases.
1116 SimpleFinishLegalizing = false;
1117 break;
1118 case ISD::CALLSEQ_START:
1119 case ISD::CALLSEQ_END:
1120 // FIXME: This shouldn't be necessary. These nodes have special properties
1121 // dealing with the recursive nature of legalization. Removing this
1122 // special case should be done as part of making LegalizeDAG non-recursive.
1123 SimpleFinishLegalizing = false;
1124 break;
1126 case ISD::GET_ROUNDING:
1127 case ISD::MERGE_VALUES:
1128 case ISD::EH_RETURN:
1130 case ISD::EH_DWARF_CFA:
1134 // These operations lie about being legal: when they claim to be legal,
1135 // they should actually be expanded.
1136 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1137 if (Action == TargetLowering::Legal)
1138 Action = TargetLowering::Expand;
1139 break;
1142 case ISD::FRAMEADDR:
1143 case ISD::RETURNADDR:
1145 case ISD::SPONENTRY:
1146 // These operations lie about being legal: when they claim to be legal,
1147 // they should actually be custom-lowered.
1148 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1149 if (Action == TargetLowering::Legal)
1150 Action = TargetLowering::Custom;
1151 break;
1152 case ISD::CLEAR_CACHE:
1153 // This operation is typically going to be LibCall unless the target wants
1154 // something differrent.
1155 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1156 break;
1159 // READCYCLECOUNTER and READSTEADYCOUNTER return a i64, even if type
1160 // legalization might have expanded that to several smaller types.
1161 Action = TLI.getOperationAction(Node->getOpcode(), MVT::i64);
1162 break;
1163 case ISD::READ_REGISTER:
1165 // Named register is legal in the DAG, but blocked by register name
1166 // selection if not implemented by target (to chose the correct register)
1167 // They'll be converted to Copy(To/From)Reg.
1168 Action = TargetLowering::Legal;
1169 break;
1170 case ISD::UBSANTRAP:
1171 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1172 if (Action == TargetLowering::Expand) {
1173 // replace ISD::UBSANTRAP with ISD::TRAP
1174 SDValue NewVal;
1175 NewVal = DAG.getNode(ISD::TRAP, SDLoc(Node), Node->getVTList(),
1176 Node->getOperand(0));
1177 ReplaceNode(Node, NewVal.getNode());
1178 LegalizeOp(NewVal.getNode());
1179 return;
1180 }
1181 break;
1182 case ISD::DEBUGTRAP:
1183 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1184 if (Action == TargetLowering::Expand) {
1185 // replace ISD::DEBUGTRAP with ISD::TRAP
1186 SDValue NewVal;
1187 NewVal = DAG.getNode(ISD::TRAP, SDLoc(Node), Node->getVTList(),
1188 Node->getOperand(0));
1189 ReplaceNode(Node, NewVal.getNode());
1190 LegalizeOp(NewVal.getNode());
1191 return;
1192 }
1193 break;
1194 case ISD::SADDSAT:
1195 case ISD::UADDSAT:
1196 case ISD::SSUBSAT:
1197 case ISD::USUBSAT:
1198 case ISD::SSHLSAT:
1199 case ISD::USHLSAT:
1200 case ISD::SCMP:
1201 case ISD::UCMP:
1204 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1205 break;
1206 case ISD::SMULFIX:
1207 case ISD::SMULFIXSAT:
1208 case ISD::UMULFIX:
1209 case ISD::UMULFIXSAT:
1210 case ISD::SDIVFIX:
1211 case ISD::SDIVFIXSAT:
1212 case ISD::UDIVFIX:
1213 case ISD::UDIVFIXSAT: {
1214 unsigned Scale = Node->getConstantOperandVal(2);
1215 Action = TLI.getFixedPointOperationAction(Node->getOpcode(),
1216 Node->getValueType(0), Scale);
1217 break;
1218 }
1219 case ISD::MSCATTER:
1220 Action = TLI.getOperationAction(Node->getOpcode(),
1221 cast<MaskedScatterSDNode>(Node)->getValue().getValueType());
1222 break;
1223 case ISD::MSTORE:
1224 Action = TLI.getOperationAction(Node->getOpcode(),
1225 cast<MaskedStoreSDNode>(Node)->getValue().getValueType());
1226 break;
1227 case ISD::VP_SCATTER:
1228 Action = TLI.getOperationAction(
1229 Node->getOpcode(),
1230 cast<VPScatterSDNode>(Node)->getValue().getValueType());
1231 break;
1232 case ISD::VP_STORE:
1233 Action = TLI.getOperationAction(
1234 Node->getOpcode(),
1235 cast<VPStoreSDNode>(Node)->getValue().getValueType());
1236 break;
1237 case ISD::EXPERIMENTAL_VP_STRIDED_STORE:
1238 Action = TLI.getOperationAction(
1239 Node->getOpcode(),
1240 cast<VPStridedStoreSDNode>(Node)->getValue().getValueType());
1241 break;
1244 case ISD::VECREDUCE_ADD:
1245 case ISD::VECREDUCE_MUL:
1246 case ISD::VECREDUCE_AND:
1247 case ISD::VECREDUCE_OR:
1248 case ISD::VECREDUCE_XOR:
1257 case ISD::IS_FPCLASS:
1258 Action = TLI.getOperationAction(
1259 Node->getOpcode(), Node->getOperand(0).getValueType());
1260 break;
1263 case ISD::VP_REDUCE_FADD:
1264 case ISD::VP_REDUCE_FMUL:
1265 case ISD::VP_REDUCE_ADD:
1266 case ISD::VP_REDUCE_MUL:
1267 case ISD::VP_REDUCE_AND:
1268 case ISD::VP_REDUCE_OR:
1269 case ISD::VP_REDUCE_XOR:
1270 case ISD::VP_REDUCE_SMAX:
1271 case ISD::VP_REDUCE_SMIN:
1272 case ISD::VP_REDUCE_UMAX:
1273 case ISD::VP_REDUCE_UMIN:
1274 case ISD::VP_REDUCE_FMAX:
1275 case ISD::VP_REDUCE_FMIN:
1276 case ISD::VP_REDUCE_FMAXIMUM:
1277 case ISD::VP_REDUCE_FMINIMUM:
1278 case ISD::VP_REDUCE_SEQ_FADD:
1279 case ISD::VP_REDUCE_SEQ_FMUL:
1280 Action = TLI.getOperationAction(
1281 Node->getOpcode(), Node->getOperand(1).getValueType());
1282 break;
1283 case ISD::CTTZ_ELTS:
1285 case ISD::VP_CTTZ_ELTS:
1286 case ISD::VP_CTTZ_ELTS_ZERO_UNDEF:
1287 Action = TLI.getOperationAction(Node->getOpcode(),
1288 Node->getOperand(0).getValueType());
1289 break;
1291 Action = TLI.getOperationAction(
1292 Node->getOpcode(),
1293 cast<MaskedHistogramSDNode>(Node)->getIndex().getValueType());
1294 break;
1295 default:
1296 if (Node->getOpcode() >= ISD::BUILTIN_OP_END) {
1297 Action = TLI.getCustomOperationAction(*Node);
1298 } else {
1299 Action = TLI.getOperationAction(Node->getOpcode(), Node->getValueType(0));
1300 }
1301 break;
1302 }
1303
1304 if (SimpleFinishLegalizing) {
1305 SDNode *NewNode = Node;
1306 switch (Node->getOpcode()) {
1307 default: break;
1308 case ISD::SHL:
1309 case ISD::SRL:
1310 case ISD::SRA:
1311 case ISD::ROTL:
1312 case ISD::ROTR:
1313 case ISD::SSHLSAT:
1314 case ISD::USHLSAT: {
1315 // Legalizing shifts/rotates requires adjusting the shift amount
1316 // to the appropriate width.
1317 SDValue Op0 = Node->getOperand(0);
1318 SDValue Op1 = Node->getOperand(1);
1319 if (!Op1.getValueType().isVector()) {
1320 SDValue SAO = DAG.getShiftAmountOperand(Op0.getValueType(), Op1);
1321 // The getShiftAmountOperand() may create a new operand node or
1322 // return the existing one. If new operand is created we need
1323 // to update the parent node.
1324 // Do not try to legalize SAO here! It will be automatically legalized
1325 // in the next round.
1326 if (SAO != Op1)
1327 NewNode = DAG.UpdateNodeOperands(Node, Op0, SAO);
1328 }
1329 break;
1330 }
1331 case ISD::FSHL:
1332 case ISD::FSHR:
1333 case ISD::SRL_PARTS:
1334 case ISD::SRA_PARTS:
1335 case ISD::SHL_PARTS: {
1336 // Legalizing shifts/rotates requires adjusting the shift amount
1337 // to the appropriate width.
1338 SDValue Op0 = Node->getOperand(0);
1339 SDValue Op1 = Node->getOperand(1);
1340 SDValue Op2 = Node->getOperand(2);
1341 if (!Op2.getValueType().isVector()) {
1342 SDValue SAO = DAG.getShiftAmountOperand(Op0.getValueType(), Op2);
1343 // The getShiftAmountOperand() may create a new operand node or
1344 // return the existing one. If new operand is created we need
1345 // to update the parent node.
1346 if (SAO != Op2)
1347 NewNode = DAG.UpdateNodeOperands(Node, Op0, Op1, SAO);
1348 }
1349 break;
1350 }
1351 }
1352
1353 if (NewNode != Node) {
1354 ReplaceNode(Node, NewNode);
1355 Node = NewNode;
1356 }
1357 switch (Action) {
1358 case TargetLowering::Legal:
1359 LLVM_DEBUG(dbgs() << "Legal node: nothing to do\n");
1360 return;
1361 case TargetLowering::Custom:
1362 LLVM_DEBUG(dbgs() << "Trying custom legalization\n");
1363 // FIXME: The handling for custom lowering with multiple results is
1364 // a complete mess.
1365 if (SDValue Res = TLI.LowerOperation(SDValue(Node, 0), DAG)) {
1366 if (!(Res.getNode() != Node || Res.getResNo() != 0))
1367 return;
1368
1369 if (Node->getNumValues() == 1) {
1370 // Verify the new types match the original. Glue is waived because
1371 // ISD::ADDC can be legalized by replacing Glue with an integer type.
1372 assert((Res.getValueType() == Node->getValueType(0) ||
1373 Node->getValueType(0) == MVT::Glue) &&
1374 "Type mismatch for custom legalized operation");
1375 LLVM_DEBUG(dbgs() << "Successfully custom legalized node\n");
1376 // We can just directly replace this node with the lowered value.
1377 ReplaceNode(SDValue(Node, 0), Res);
1378 return;
1379 }
1380
1381 SmallVector<SDValue, 8> ResultVals;
1382 for (unsigned i = 0, e = Node->getNumValues(); i != e; ++i) {
1383 // Verify the new types match the original. Glue is waived because
1384 // ISD::ADDC can be legalized by replacing Glue with an integer type.
1385 assert((Res->getValueType(i) == Node->getValueType(i) ||
1386 Node->getValueType(i) == MVT::Glue) &&
1387 "Type mismatch for custom legalized operation");
1388 ResultVals.push_back(Res.getValue(i));
1389 }
1390 LLVM_DEBUG(dbgs() << "Successfully custom legalized node\n");
1391 ReplaceNode(Node, ResultVals.data());
1392 return;
1393 }
1394 LLVM_DEBUG(dbgs() << "Could not custom legalize node\n");
1395 [[fallthrough]];
1396 case TargetLowering::Expand:
1397 if (ExpandNode(Node))
1398 return;
1399 [[fallthrough]];
1400 case TargetLowering::LibCall:
1401 ConvertNodeToLibcall(Node);
1402 return;
1403 case TargetLowering::Promote:
1404 PromoteNode(Node);
1405 return;
1406 }
1407 }
1408
1409 switch (Node->getOpcode()) {
1410 default:
1411#ifndef NDEBUG
1412 dbgs() << "NODE: ";
1413 Node->dump( &DAG);
1414 dbgs() << "\n";
1415#endif
1416 llvm_unreachable("Do not know how to legalize this operator!");
1417
1418 case ISD::CALLSEQ_START:
1419 case ISD::CALLSEQ_END:
1420 break;
1421 case ISD::LOAD:
1422 return LegalizeLoadOps(Node);
1423 case ISD::STORE:
1424 return LegalizeStoreOps(Node);
1425 }
1426}
1427
1428SDValue SelectionDAGLegalize::ExpandExtractFromVectorThroughStack(SDValue Op) {
1429 SDValue Vec = Op.getOperand(0);
1430 SDValue Idx = Op.getOperand(1);
1431 SDLoc dl(Op);
1432
1433 // Before we generate a new store to a temporary stack slot, see if there is
1434 // already one that we can use. There often is because when we scalarize
1435 // vector operations (using SelectionDAG::UnrollVectorOp for example) a whole
1436 // series of EXTRACT_VECTOR_ELT nodes are generated, one for each element in
1437 // the vector. If all are expanded here, we don't want one store per vector
1438 // element.
1439
1440 // Caches for hasPredecessorHelper
1441 SmallPtrSet<const SDNode *, 32> Visited;
1443 Visited.insert(Op.getNode());
1444 Worklist.push_back(Idx.getNode());
1445 SDValue StackPtr, Ch;
1446 for (SDNode *User : Vec.getNode()->users()) {
1447 if (StoreSDNode *ST = dyn_cast<StoreSDNode>(User)) {
1448 if (ST->isIndexed() || ST->isTruncatingStore() ||
1449 ST->getValue() != Vec)
1450 continue;
1451
1452 // Make sure that nothing else could have stored into the destination of
1453 // this store.
1454 if (!ST->getChain().reachesChainWithoutSideEffects(DAG.getEntryNode()))
1455 continue;
1456
1457 // If the index is dependent on the store we will introduce a cycle when
1458 // creating the load (the load uses the index, and by replacing the chain
1459 // we will make the index dependent on the load). Also, the store might be
1460 // dependent on the extractelement and introduce a cycle when creating
1461 // the load.
1462 if (SDNode::hasPredecessorHelper(ST, Visited, Worklist) ||
1463 ST->hasPredecessor(Op.getNode()))
1464 continue;
1465
1466 StackPtr = ST->getBasePtr();
1467 Ch = SDValue(ST, 0);
1468 break;
1469 }
1470 }
1471
1472 EVT VecVT = Vec.getValueType();
1473
1474 if (!Ch.getNode()) {
1475 // Store the value to a temporary stack slot, then LOAD the returned part.
1476 StackPtr = DAG.CreateStackTemporary(VecVT);
1477 MachineMemOperand *StoreMMO = getStackAlignedMMO(
1478 StackPtr, DAG.getMachineFunction(), VecVT.isScalableVector());
1479 Ch = DAG.getStore(DAG.getEntryNode(), dl, Vec, StackPtr, StoreMMO);
1480 }
1481
1482 SDValue NewLoad;
1483 Align ElementAlignment =
1484 std::min(cast<StoreSDNode>(Ch)->getAlign(),
1486 Op.getValueType().getTypeForEVT(*DAG.getContext())));
1487
1488 if (Op.getValueType().isVector()) {
1489 StackPtr = TLI.getVectorSubVecPointer(DAG, StackPtr, VecVT,
1490 Op.getValueType(), Idx);
1491 NewLoad = DAG.getLoad(Op.getValueType(), dl, Ch, StackPtr,
1492 MachinePointerInfo(), ElementAlignment);
1493 } else {
1494 StackPtr = TLI.getVectorElementPointer(DAG, StackPtr, VecVT, Idx);
1495 NewLoad = DAG.getExtLoad(ISD::EXTLOAD, dl, Op.getValueType(), Ch, StackPtr,
1496 MachinePointerInfo(), VecVT.getVectorElementType(),
1497 ElementAlignment);
1498 }
1499
1500 // Replace the chain going out of the store, by the one out of the load.
1501 DAG.ReplaceAllUsesOfValueWith(Ch, SDValue(NewLoad.getNode(), 1));
1502
1503 // We introduced a cycle though, so update the loads operands, making sure
1504 // to use the original store's chain as an incoming chain.
1505 SmallVector<SDValue, 6> NewLoadOperands(NewLoad->ops());
1506 NewLoadOperands[0] = Ch;
1507 NewLoad =
1508 SDValue(DAG.UpdateNodeOperands(NewLoad.getNode(), NewLoadOperands), 0);
1509 return NewLoad;
1510}
1511
1512SDValue SelectionDAGLegalize::ExpandInsertToVectorThroughStack(SDValue Op) {
1513 assert(Op.getValueType().isVector() && "Non-vector insert subvector!");
1514
1515 SDValue Vec = Op.getOperand(0);
1516 SDValue Part = Op.getOperand(1);
1517 SDValue Idx = Op.getOperand(2);
1518 SDLoc dl(Op);
1519
1520 // Store the value to a temporary stack slot, then LOAD the returned part.
1521 EVT VecVT = Vec.getValueType();
1522 EVT PartVT = Part.getValueType();
1524 int FI = cast<FrameIndexSDNode>(StackPtr.getNode())->getIndex();
1525 MachinePointerInfo PtrInfo =
1527
1528 // First store the whole vector.
1529 Align BaseVecAlignment =
1531 SDValue Ch = DAG.getStore(DAG.getEntryNode(), dl, Vec, StackPtr, PtrInfo,
1532 BaseVecAlignment);
1533
1534 // Freeze the index so we don't poison the clamping code we're about to emit.
1535 Idx = DAG.getFreeze(Idx);
1536
1537 Type *PartTy = PartVT.getTypeForEVT(*DAG.getContext());
1538 Align PartAlignment = DAG.getDataLayout().getPrefTypeAlign(PartTy);
1539
1540 // Then store the inserted part.
1541 if (PartVT.isVector()) {
1542 SDValue SubStackPtr =
1543 TLI.getVectorSubVecPointer(DAG, StackPtr, VecVT, PartVT, Idx);
1544
1545 // Store the subvector.
1546 Ch = DAG.getStore(
1547 Ch, dl, Part, SubStackPtr,
1549 PartAlignment);
1550 } else {
1551 SDValue SubStackPtr =
1552 TLI.getVectorElementPointer(DAG, StackPtr, VecVT, Idx);
1553
1554 // Store the scalar value.
1555 Ch = DAG.getTruncStore(
1556 Ch, dl, Part, SubStackPtr,
1558 VecVT.getVectorElementType(), PartAlignment);
1559 }
1560
1561 assert(cast<StoreSDNode>(Ch)->getAlign() == PartAlignment &&
1562 "ElementAlignment does not match!");
1563
1564 // Finally, load the updated vector.
1565 return DAG.getLoad(Op.getValueType(), dl, Ch, StackPtr, PtrInfo,
1566 BaseVecAlignment);
1567}
1568
1569SDValue SelectionDAGLegalize::ExpandConcatVectors(SDNode *Node) {
1570 assert(Node->getOpcode() == ISD::CONCAT_VECTORS && "Unexpected opcode!");
1571 SDLoc DL(Node);
1573 unsigned NumOperands = Node->getNumOperands();
1574 MVT VectorIdxType = TLI.getVectorIdxTy(DAG.getDataLayout());
1575 EVT VectorValueType = Node->getOperand(0).getValueType();
1576 unsigned NumSubElem = VectorValueType.getVectorNumElements();
1577 EVT ElementValueType = TLI.getTypeToTransformTo(
1578 *DAG.getContext(), VectorValueType.getVectorElementType());
1579 for (unsigned I = 0; I < NumOperands; ++I) {
1580 SDValue SubOp = Node->getOperand(I);
1581 for (unsigned Idx = 0; Idx < NumSubElem; ++Idx) {
1582 Ops.push_back(DAG.getNode(ISD::EXTRACT_VECTOR_ELT, DL, ElementValueType,
1583 SubOp,
1584 DAG.getConstant(Idx, DL, VectorIdxType)));
1585 }
1586 }
1587 return DAG.getBuildVector(Node->getValueType(0), DL, Ops);
1588}
1589
1590SDValue SelectionDAGLegalize::ExpandVectorBuildThroughStack(SDNode* Node) {
1591 assert((Node->getOpcode() == ISD::BUILD_VECTOR ||
1592 Node->getOpcode() == ISD::CONCAT_VECTORS) &&
1593 "Unexpected opcode!");
1594
1595 // We can't handle this case efficiently. Allocate a sufficiently
1596 // aligned object on the stack, store each operand into it, then load
1597 // the result as a vector.
1598 // Create the stack frame object.
1599 EVT VT = Node->getValueType(0);
1600 EVT MemVT = isa<BuildVectorSDNode>(Node) ? VT.getVectorElementType()
1601 : Node->getOperand(0).getValueType();
1602 SDLoc dl(Node);
1603 SDValue FIPtr = DAG.CreateStackTemporary(VT);
1604 int FI = cast<FrameIndexSDNode>(FIPtr.getNode())->getIndex();
1605 MachinePointerInfo PtrInfo =
1607
1608 // Emit a store of each element to the stack slot.
1610 unsigned TypeByteSize = MemVT.getSizeInBits() / 8;
1611 assert(TypeByteSize > 0 && "Vector element type too small for stack store!");
1612
1613 // If the destination vector element type of a BUILD_VECTOR is narrower than
1614 // the source element type, only store the bits necessary.
1615 bool Truncate = isa<BuildVectorSDNode>(Node) &&
1616 MemVT.bitsLT(Node->getOperand(0).getValueType());
1617
1618 // Store (in the right endianness) the elements to memory.
1619 for (unsigned i = 0, e = Node->getNumOperands(); i != e; ++i) {
1620 // Ignore undef elements.
1621 if (Node->getOperand(i).isUndef()) continue;
1622
1623 unsigned Offset = TypeByteSize*i;
1624
1625 SDValue Idx =
1627
1628 if (Truncate)
1629 Stores.push_back(DAG.getTruncStore(DAG.getEntryNode(), dl,
1630 Node->getOperand(i), Idx,
1631 PtrInfo.getWithOffset(Offset), MemVT));
1632 else
1633 Stores.push_back(DAG.getStore(DAG.getEntryNode(), dl, Node->getOperand(i),
1634 Idx, PtrInfo.getWithOffset(Offset)));
1635 }
1636
1637 SDValue StoreChain;
1638 if (!Stores.empty()) // Not all undef elements?
1639 StoreChain = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Stores);
1640 else
1641 StoreChain = DAG.getEntryNode();
1642
1643 // Result is a load from the stack slot.
1644 return DAG.getLoad(VT, dl, StoreChain, FIPtr, PtrInfo);
1645}
1646
1647/// Bitcast a floating-point value to an integer value. Only bitcast the part
1648/// containing the sign bit if the target has no integer value capable of
1649/// holding all bits of the floating-point value.
1650void SelectionDAGLegalize::getSignAsIntValue(FloatSignAsInt &State,
1651 const SDLoc &DL,
1652 SDValue Value) const {
1653 EVT FloatVT = Value.getValueType();
1654 unsigned NumBits = FloatVT.getScalarSizeInBits();
1655 State.FloatVT = FloatVT;
1656 EVT IVT = EVT::getIntegerVT(*DAG.getContext(), NumBits);
1657 // Convert to an integer of the same size.
1658 if (TLI.isTypeLegal(IVT)) {
1659 State.IntValue = DAG.getNode(ISD::BITCAST, DL, IVT, Value);
1660 State.SignMask = APInt::getSignMask(NumBits);
1661 State.SignBit = NumBits - 1;
1662 return;
1663 }
1664
1665 auto &DataLayout = DAG.getDataLayout();
1666 // Store the float to memory, then load the sign part out as an integer.
1667 MVT LoadTy = TLI.getRegisterType(MVT::i8);
1668 // First create a temporary that is aligned for both the load and store.
1669 SDValue StackPtr = DAG.CreateStackTemporary(FloatVT, LoadTy);
1670 int FI = cast<FrameIndexSDNode>(StackPtr.getNode())->getIndex();
1671 // Then store the float to it.
1672 State.FloatPtr = StackPtr;
1673 MachineFunction &MF = DAG.getMachineFunction();
1674 State.FloatPointerInfo = MachinePointerInfo::getFixedStack(MF, FI);
1675 State.Chain = DAG.getStore(DAG.getEntryNode(), DL, Value, State.FloatPtr,
1676 State.FloatPointerInfo);
1677
1678 SDValue IntPtr;
1679 if (DataLayout.isBigEndian()) {
1680 assert(FloatVT.isByteSized() && "Unsupported floating point type!");
1681 // Load out a legal integer with the same sign bit as the float.
1682 IntPtr = StackPtr;
1683 State.IntPointerInfo = State.FloatPointerInfo;
1684 } else {
1685 // Advance the pointer so that the loaded byte will contain the sign bit.
1686 unsigned ByteOffset = (NumBits / 8) - 1;
1687 IntPtr =
1688 DAG.getMemBasePlusOffset(StackPtr, TypeSize::getFixed(ByteOffset), DL);
1689 State.IntPointerInfo = MachinePointerInfo::getFixedStack(MF, FI,
1690 ByteOffset);
1691 }
1692
1693 State.IntPtr = IntPtr;
1694 State.IntValue = DAG.getExtLoad(ISD::EXTLOAD, DL, LoadTy, State.Chain, IntPtr,
1695 State.IntPointerInfo, MVT::i8);
1696 State.SignMask = APInt::getOneBitSet(LoadTy.getScalarSizeInBits(), 7);
1697 State.SignBit = 7;
1698}
1699
1700/// Replace the integer value produced by getSignAsIntValue() with a new value
1701/// and cast the result back to a floating-point type.
1702SDValue SelectionDAGLegalize::modifySignAsInt(const FloatSignAsInt &State,
1703 const SDLoc &DL,
1704 SDValue NewIntValue) const {
1705 if (!State.Chain)
1706 return DAG.getNode(ISD::BITCAST, DL, State.FloatVT, NewIntValue);
1707
1708 // Override the part containing the sign bit in the value stored on the stack.
1709 SDValue Chain = DAG.getTruncStore(State.Chain, DL, NewIntValue, State.IntPtr,
1710 State.IntPointerInfo, MVT::i8);
1711 return DAG.getLoad(State.FloatVT, DL, Chain, State.FloatPtr,
1712 State.FloatPointerInfo);
1713}
1714
1715SDValue SelectionDAGLegalize::ExpandFCOPYSIGN(SDNode *Node) const {
1716 SDLoc DL(Node);
1717 SDValue Mag = Node->getOperand(0);
1718 SDValue Sign = Node->getOperand(1);
1719
1720 // Get sign bit into an integer value.
1721 FloatSignAsInt SignAsInt;
1722 getSignAsIntValue(SignAsInt, DL, Sign);
1723
1724 EVT IntVT = SignAsInt.IntValue.getValueType();
1725 SDValue SignMask = DAG.getConstant(SignAsInt.SignMask, DL, IntVT);
1726 SDValue SignBit = DAG.getNode(ISD::AND, DL, IntVT, SignAsInt.IntValue,
1727 SignMask);
1728
1729 // If FABS is legal transform
1730 // FCOPYSIGN(x, y) => SignBit(y) ? -FABS(x) : FABS(x)
1731 EVT FloatVT = Mag.getValueType();
1732 if (TLI.isOperationLegalOrCustom(ISD::FABS, FloatVT) &&
1733 TLI.isOperationLegalOrCustom(ISD::FNEG, FloatVT)) {
1734 SDValue AbsValue = DAG.getNode(ISD::FABS, DL, FloatVT, Mag);
1735 SDValue NegValue = DAG.getNode(ISD::FNEG, DL, FloatVT, AbsValue);
1736 SDValue Cond = DAG.getSetCC(DL, getSetCCResultType(IntVT), SignBit,
1737 DAG.getConstant(0, DL, IntVT), ISD::SETNE);
1738 return DAG.getSelect(DL, FloatVT, Cond, NegValue, AbsValue);
1739 }
1740
1741 // Transform Mag value to integer, and clear the sign bit.
1742 FloatSignAsInt MagAsInt;
1743 getSignAsIntValue(MagAsInt, DL, Mag);
1744 EVT MagVT = MagAsInt.IntValue.getValueType();
1745 SDValue ClearSignMask = DAG.getConstant(~MagAsInt.SignMask, DL, MagVT);
1746 SDValue ClearedSign = DAG.getNode(ISD::AND, DL, MagVT, MagAsInt.IntValue,
1747 ClearSignMask);
1748
1749 // Get the signbit at the right position for MagAsInt.
1750 int ShiftAmount = SignAsInt.SignBit - MagAsInt.SignBit;
1751 EVT ShiftVT = IntVT;
1752 if (SignBit.getScalarValueSizeInBits() <
1753 ClearedSign.getScalarValueSizeInBits()) {
1754 SignBit = DAG.getNode(ISD::ZERO_EXTEND, DL, MagVT, SignBit);
1755 ShiftVT = MagVT;
1756 }
1757 if (ShiftAmount > 0) {
1758 SDValue ShiftCnst = DAG.getConstant(ShiftAmount, DL, ShiftVT);
1759 SignBit = DAG.getNode(ISD::SRL, DL, ShiftVT, SignBit, ShiftCnst);
1760 } else if (ShiftAmount < 0) {
1761 SDValue ShiftCnst = DAG.getConstant(-ShiftAmount, DL, ShiftVT);
1762 SignBit = DAG.getNode(ISD::SHL, DL, ShiftVT, SignBit, ShiftCnst);
1763 }
1764 if (SignBit.getScalarValueSizeInBits() >
1765 ClearedSign.getScalarValueSizeInBits()) {
1766 SignBit = DAG.getNode(ISD::TRUNCATE, DL, MagVT, SignBit);
1767 }
1768
1769 // Store the part with the modified sign and convert back to float.
1770 SDValue CopiedSign = DAG.getNode(ISD::OR, DL, MagVT, ClearedSign, SignBit,
1772
1773 return modifySignAsInt(MagAsInt, DL, CopiedSign);
1774}
1775
1776SDValue SelectionDAGLegalize::ExpandFNEG(SDNode *Node) const {
1777 // Get the sign bit as an integer.
1778 SDLoc DL(Node);
1779 FloatSignAsInt SignAsInt;
1780 getSignAsIntValue(SignAsInt, DL, Node->getOperand(0));
1781 EVT IntVT = SignAsInt.IntValue.getValueType();
1782
1783 // Flip the sign.
1784 SDValue SignMask = DAG.getConstant(SignAsInt.SignMask, DL, IntVT);
1785 SDValue SignFlip =
1786 DAG.getNode(ISD::XOR, DL, IntVT, SignAsInt.IntValue, SignMask);
1787
1788 // Convert back to float.
1789 return modifySignAsInt(SignAsInt, DL, SignFlip);
1790}
1791
1792SDValue SelectionDAGLegalize::ExpandFABS(SDNode *Node) const {
1793 SDLoc DL(Node);
1794 SDValue Value = Node->getOperand(0);
1795
1796 // Transform FABS(x) => FCOPYSIGN(x, 0.0) if FCOPYSIGN is legal.
1797 EVT FloatVT = Value.getValueType();
1798 if (TLI.isOperationLegalOrCustom(ISD::FCOPYSIGN, FloatVT)) {
1799 SDValue Zero = DAG.getConstantFP(0.0, DL, FloatVT);
1800 return DAG.getNode(ISD::FCOPYSIGN, DL, FloatVT, Value, Zero);
1801 }
1802
1803 // Transform value to integer, clear the sign bit and transform back.
1804 FloatSignAsInt ValueAsInt;
1805 getSignAsIntValue(ValueAsInt, DL, Value);
1806 EVT IntVT = ValueAsInt.IntValue.getValueType();
1807 SDValue ClearSignMask = DAG.getConstant(~ValueAsInt.SignMask, DL, IntVT);
1808 SDValue ClearedSign = DAG.getNode(ISD::AND, DL, IntVT, ValueAsInt.IntValue,
1809 ClearSignMask);
1810 return modifySignAsInt(ValueAsInt, DL, ClearedSign);
1811}
1812
1813void SelectionDAGLegalize::ExpandDYNAMIC_STACKALLOC(SDNode* Node,
1814 SmallVectorImpl<SDValue> &Results) {
1816 assert(SPReg && "Target cannot require DYNAMIC_STACKALLOC expansion and"
1817 " not tell us which reg is the stack pointer!");
1818 SDLoc dl(Node);
1819 EVT VT = Node->getValueType(0);
1820 SDValue Tmp1 = SDValue(Node, 0);
1821 SDValue Tmp2 = SDValue(Node, 1);
1822 SDValue Tmp3 = Node->getOperand(2);
1823 SDValue Chain = Tmp1.getOperand(0);
1824
1825 // Chain the dynamic stack allocation so that it doesn't modify the stack
1826 // pointer when other instructions are using the stack.
1827 Chain = DAG.getCALLSEQ_START(Chain, 0, 0, dl);
1828
1829 SDValue Size = Tmp2.getOperand(1);
1830 SDValue SP = DAG.getCopyFromReg(Chain, dl, SPReg, VT);
1831 Chain = SP.getValue(1);
1832 Align Alignment = cast<ConstantSDNode>(Tmp3)->getAlignValue();
1833 const TargetFrameLowering *TFL = DAG.getSubtarget().getFrameLowering();
1834 unsigned Opc =
1837
1838 Align StackAlign = TFL->getStackAlign();
1839 Tmp1 = DAG.getNode(Opc, dl, VT, SP, Size); // Value
1840 if (Alignment > StackAlign)
1841 Tmp1 = DAG.getNode(ISD::AND, dl, VT, Tmp1,
1842 DAG.getSignedConstant(-Alignment.value(), dl, VT));
1843 Chain = DAG.getCopyToReg(Chain, dl, SPReg, Tmp1); // Output chain
1844
1845 Tmp2 = DAG.getCALLSEQ_END(Chain, 0, 0, SDValue(), dl);
1846
1847 Results.push_back(Tmp1);
1848 Results.push_back(Tmp2);
1849}
1850
1851/// Emit a store/load combination to the stack. This stores
1852/// SrcOp to a stack slot of type SlotVT, truncating it if needed. It then does
1853/// a load from the stack slot to DestVT, extending it if needed.
1854/// The resultant code need not be legal.
1855SDValue SelectionDAGLegalize::EmitStackConvert(SDValue SrcOp, EVT SlotVT,
1856 EVT DestVT, const SDLoc &dl) {
1857 return EmitStackConvert(SrcOp, SlotVT, DestVT, dl, DAG.getEntryNode());
1858}
1859
1860SDValue SelectionDAGLegalize::EmitStackConvert(SDValue SrcOp, EVT SlotVT,
1861 EVT DestVT, const SDLoc &dl,
1862 SDValue Chain) {
1863 EVT SrcVT = SrcOp.getValueType();
1864 Type *DestType = DestVT.getTypeForEVT(*DAG.getContext());
1865 Align DestAlign = DAG.getDataLayout().getPrefTypeAlign(DestType);
1866
1867 // Don't convert with stack if the load/store is expensive.
1868 if ((SrcVT.bitsGT(SlotVT) && !TLI.isTruncStoreLegalOrCustom(
1869 SrcOp.getValueType(), SlotVT, DestAlign,
1871 (SlotVT.bitsLT(DestVT) &&
1872 !TLI.isLoadLegalOrCustom(DestVT, SlotVT, DestAlign,
1874 ISD::EXTLOAD, false)))
1875 return SDValue();
1876
1877 // Create the stack frame object.
1878 Align SrcAlign = DAG.getDataLayout().getPrefTypeAlign(
1879 SrcOp.getValueType().getTypeForEVT(*DAG.getContext()));
1880 SDValue FIPtr = DAG.CreateStackTemporary(SlotVT.getStoreSize(), SrcAlign);
1881
1882 FrameIndexSDNode *StackPtrFI = cast<FrameIndexSDNode>(FIPtr);
1883 int SPFI = StackPtrFI->getIndex();
1884 MachinePointerInfo PtrInfo =
1886
1887 // Emit a store to the stack slot. Use a truncstore if the input value is
1888 // later than DestVT.
1889 SDValue Store;
1890
1891 if (SrcVT.bitsGT(SlotVT))
1892 Store = DAG.getTruncStore(Chain, dl, SrcOp, FIPtr, PtrInfo,
1893 SlotVT, SrcAlign);
1894 else {
1895 assert(SrcVT.bitsEq(SlotVT) && "Invalid store");
1896 Store = DAG.getStore(Chain, dl, SrcOp, FIPtr, PtrInfo, SrcAlign);
1897 }
1898
1899 // Result is a load from the stack slot.
1900 if (SlotVT.bitsEq(DestVT))
1901 return DAG.getLoad(DestVT, dl, Store, FIPtr, PtrInfo, DestAlign);
1902
1903 assert(SlotVT.bitsLT(DestVT) && "Unknown extension!");
1904 return DAG.getExtLoad(ISD::EXTLOAD, dl, DestVT, Store, FIPtr, PtrInfo, SlotVT,
1905 DestAlign);
1906}
1907
1908SDValue SelectionDAGLegalize::ExpandSCALAR_TO_VECTOR(SDNode *Node) {
1909 SDLoc dl(Node);
1910 // Create a vector sized/aligned stack slot, store the value to element #0,
1911 // then load the whole vector back out.
1912 SDValue StackPtr = DAG.CreateStackTemporary(Node->getValueType(0));
1913
1914 FrameIndexSDNode *StackPtrFI = cast<FrameIndexSDNode>(StackPtr);
1915 int SPFI = StackPtrFI->getIndex();
1916
1917 SDValue Ch = DAG.getTruncStore(
1918 DAG.getEntryNode(), dl, Node->getOperand(0), StackPtr,
1920 Node->getValueType(0).getVectorElementType());
1921 return DAG.getLoad(
1922 Node->getValueType(0), dl, Ch, StackPtr,
1924}
1925
1926static bool
1928 const TargetLowering &TLI, SDValue &Res) {
1929 unsigned NumElems = Node->getNumOperands();
1930 SDLoc dl(Node);
1931 EVT VT = Node->getValueType(0);
1932
1933 // Try to group the scalars into pairs, shuffle the pairs together, then
1934 // shuffle the pairs of pairs together, etc. until the vector has
1935 // been built. This will work only if all of the necessary shuffle masks
1936 // are legal.
1937
1938 // We do this in two phases; first to check the legality of the shuffles,
1939 // and next, assuming that all shuffles are legal, to create the new nodes.
1940 for (int Phase = 0; Phase < 2; ++Phase) {
1942 NewIntermedVals;
1943 for (unsigned i = 0; i < NumElems; ++i) {
1944 SDValue V = Node->getOperand(i);
1945 if (V.isUndef())
1946 continue;
1947
1948 SDValue Vec;
1949 if (Phase)
1950 Vec = DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, VT, V);
1951 IntermedVals.push_back(std::make_pair(Vec, SmallVector<int, 16>(1, i)));
1952 }
1953
1954 while (IntermedVals.size() > 2) {
1955 NewIntermedVals.clear();
1956 for (unsigned i = 0, e = (IntermedVals.size() & ~1u); i < e; i += 2) {
1957 // This vector and the next vector are shuffled together (simply to
1958 // append the one to the other).
1959 SmallVector<int, 16> ShuffleVec(NumElems, -1);
1960
1961 SmallVector<int, 16> FinalIndices;
1962 FinalIndices.reserve(IntermedVals[i].second.size() +
1963 IntermedVals[i+1].second.size());
1964
1965 int k = 0;
1966 for (unsigned j = 0, f = IntermedVals[i].second.size(); j != f;
1967 ++j, ++k) {
1968 ShuffleVec[k] = j;
1969 FinalIndices.push_back(IntermedVals[i].second[j]);
1970 }
1971 for (unsigned j = 0, f = IntermedVals[i+1].second.size(); j != f;
1972 ++j, ++k) {
1973 ShuffleVec[k] = NumElems + j;
1974 FinalIndices.push_back(IntermedVals[i+1].second[j]);
1975 }
1976
1977 SDValue Shuffle;
1978 if (Phase)
1979 Shuffle = DAG.getVectorShuffle(VT, dl, IntermedVals[i].first,
1980 IntermedVals[i+1].first,
1981 ShuffleVec);
1982 else if (!TLI.isShuffleMaskLegal(ShuffleVec, VT))
1983 return false;
1984 NewIntermedVals.push_back(
1985 std::make_pair(Shuffle, std::move(FinalIndices)));
1986 }
1987
1988 // If we had an odd number of defined values, then append the last
1989 // element to the array of new vectors.
1990 if ((IntermedVals.size() & 1) != 0)
1991 NewIntermedVals.push_back(IntermedVals.back());
1992
1993 IntermedVals.swap(NewIntermedVals);
1994 }
1995
1996 assert(IntermedVals.size() <= 2 && IntermedVals.size() > 0 &&
1997 "Invalid number of intermediate vectors");
1998 SDValue Vec1 = IntermedVals[0].first;
1999 SDValue Vec2;
2000 if (IntermedVals.size() > 1)
2001 Vec2 = IntermedVals[1].first;
2002 else if (Phase)
2003 Vec2 = DAG.getPOISON(VT);
2004
2005 SmallVector<int, 16> ShuffleVec(NumElems, -1);
2006 for (unsigned i = 0, e = IntermedVals[0].second.size(); i != e; ++i)
2007 ShuffleVec[IntermedVals[0].second[i]] = i;
2008 for (unsigned i = 0, e = IntermedVals[1].second.size(); i != e; ++i)
2009 ShuffleVec[IntermedVals[1].second[i]] = NumElems + i;
2010
2011 if (Phase)
2012 Res = DAG.getVectorShuffle(VT, dl, Vec1, Vec2, ShuffleVec);
2013 else if (!TLI.isShuffleMaskLegal(ShuffleVec, VT))
2014 return false;
2015 }
2016
2017 return true;
2018}
2019
2020/// Expand a BUILD_VECTOR node on targets that don't
2021/// support the operation, but do support the resultant vector type.
2022SDValue SelectionDAGLegalize::ExpandBUILD_VECTOR(SDNode *Node) {
2023 unsigned NumElems = Node->getNumOperands();
2024 SDValue Value1, Value2;
2025 SDLoc dl(Node);
2026 EVT VT = Node->getValueType(0);
2027 EVT OpVT = Node->getOperand(0).getValueType();
2028 EVT EltVT = VT.getVectorElementType();
2029
2030 // If the only non-undef value is the low element, turn this into a
2031 // SCALAR_TO_VECTOR node. If this is { X, X, X, X }, determine X.
2032 bool isOnlyLowElement = true;
2033 bool MoreThanTwoValues = false;
2034 bool isConstant = true;
2035 for (unsigned i = 0; i < NumElems; ++i) {
2036 SDValue V = Node->getOperand(i);
2037 if (V.isUndef())
2038 continue;
2039 if (i > 0)
2040 isOnlyLowElement = false;
2042 isConstant = false;
2043
2044 if (!Value1.getNode()) {
2045 Value1 = V;
2046 } else if (!Value2.getNode()) {
2047 if (V != Value1)
2048 Value2 = V;
2049 } else if (V != Value1 && V != Value2) {
2050 MoreThanTwoValues = true;
2051 }
2052 }
2053
2054 if (!Value1.getNode())
2055 return DAG.getUNDEF(VT);
2056
2057 if (isOnlyLowElement)
2058 return DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, VT, Node->getOperand(0));
2059
2060 // If all elements are constants, create a load from the constant pool.
2061 if (isConstant) {
2063 for (unsigned i = 0, e = NumElems; i != e; ++i) {
2064 if (ConstantFPSDNode *V =
2065 dyn_cast<ConstantFPSDNode>(Node->getOperand(i))) {
2066 CV.push_back(const_cast<ConstantFP *>(V->getConstantFPValue()));
2067 } else if (ConstantSDNode *V =
2068 dyn_cast<ConstantSDNode>(Node->getOperand(i))) {
2069 if (OpVT==EltVT)
2070 CV.push_back(const_cast<ConstantInt *>(V->getConstantIntValue()));
2071 else {
2072 // If OpVT and EltVT don't match, EltVT is not legal and the
2073 // element values have been promoted/truncated earlier. Undo this;
2074 // we don't want a v16i8 to become a v16i32 for example.
2075 const ConstantInt *CI = V->getConstantIntValue();
2076 CV.push_back(ConstantInt::get(EltVT.getTypeForEVT(*DAG.getContext()),
2077 CI->getZExtValue(), /*IsSigned=*/false,
2078 /*ImplicitTrunc=*/true));
2079 }
2080 } else {
2081 assert(Node->getOperand(i).isUndef());
2082 Type *OpNTy = EltVT.getTypeForEVT(*DAG.getContext());
2083 CV.push_back(UndefValue::get(OpNTy));
2084 }
2085 }
2086 Constant *CP = ConstantVector::get(CV);
2087 SDValue CPIdx =
2088 DAG.getConstantPool(CP, TLI.getPointerTy(DAG.getDataLayout()));
2089 Align Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlign();
2090 return DAG.getLoad(
2091 VT, dl, DAG.getEntryNode(), CPIdx,
2093 Alignment);
2094 }
2095
2096 SmallSet<SDValue, 16> DefinedValues;
2097 for (unsigned i = 0; i < NumElems; ++i) {
2098 if (Node->getOperand(i).isUndef())
2099 continue;
2100 DefinedValues.insert(Node->getOperand(i));
2101 }
2102
2103 if (TLI.shouldExpandBuildVectorWithShuffles(VT, DefinedValues.size())) {
2104 if (!MoreThanTwoValues) {
2105 SmallVector<int, 8> ShuffleVec(NumElems, -1);
2106 for (unsigned i = 0; i < NumElems; ++i) {
2107 SDValue V = Node->getOperand(i);
2108 if (V.isUndef())
2109 continue;
2110 ShuffleVec[i] = V == Value1 ? 0 : NumElems;
2111 }
2112 if (TLI.isShuffleMaskLegal(ShuffleVec, Node->getValueType(0))) {
2113 // Get the splatted value into the low element of a vector register.
2114 SDValue Vec1 = DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, VT, Value1);
2115 SDValue Vec2;
2116 if (Value2.getNode())
2117 Vec2 = DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, VT, Value2);
2118 else
2119 Vec2 = DAG.getPOISON(VT);
2120
2121 // Return shuffle(LowValVec, undef, <0,0,0,0>)
2122 return DAG.getVectorShuffle(VT, dl, Vec1, Vec2, ShuffleVec);
2123 }
2124 } else {
2125 SDValue Res;
2126 if (ExpandBVWithShuffles(Node, DAG, TLI, Res))
2127 return Res;
2128 }
2129 }
2130
2131 // Otherwise, we can't handle this case efficiently.
2132 return ExpandVectorBuildThroughStack(Node);
2133}
2134
2135SDValue SelectionDAGLegalize::ExpandSPLAT_VECTOR(SDNode *Node) {
2136 SDLoc DL(Node);
2137 EVT VT = Node->getValueType(0);
2138 SDValue SplatVal = Node->getOperand(0);
2139
2140 return DAG.getSplatBuildVector(VT, DL, SplatVal);
2141}
2142
2143// Expand a node into a call to a libcall, returning the value as the first
2144// result and the chain as the second. If the result value does not fit into a
2145// register, return the lo part and set the hi part to the by-reg argument in
2146// the first. If it does fit into a single register, return the result and
2147// leave the Hi part unset.
2148std::pair<SDValue, SDValue>
2149SelectionDAGLegalize::ExpandLibCall(RTLIB::Libcall LC, SDNode *Node,
2150 TargetLowering::ArgListTy &&Args,
2151 bool IsSigned, EVT RetVT) {
2152 EVT CodePtrTy = TLI.getPointerTy(DAG.getDataLayout());
2154 RTLIB::LibcallImpl LCImpl = DAG.getLibcalls().getLibcallImpl(LC);
2155 if (LCImpl != RTLIB::Unsupported)
2156 Callee = DAG.getExternalSymbol(LCImpl, CodePtrTy);
2157 else {
2158 Callee = DAG.getPOISON(CodePtrTy);
2159 DAG.getContext()->emitError(Twine("no libcall available for ") +
2160 Node->getOperationName(&DAG));
2161 }
2162
2163 Type *RetTy = RetVT.getTypeForEVT(*DAG.getContext());
2164
2165 // By default, the input chain to this libcall is the entry node of the
2166 // function. If the libcall is going to be emitted as a tail call then
2167 // TLI.isUsedByReturnOnly will change it to the right chain if the return
2168 // node which is being folded has a non-entry input chain.
2169 SDValue InChain = DAG.getEntryNode();
2170
2171 // isTailCall may be true since the callee does not reference caller stack
2172 // frame. Check if it's in the right position and that the return types match.
2173 SDValue TCChain = InChain;
2174 const Function &F = DAG.getMachineFunction().getFunction();
2175 bool isTailCall =
2176 TLI.isInTailCallPosition(DAG, Node, TCChain) &&
2177 (RetTy == F.getReturnType() || F.getReturnType()->isVoidTy());
2178 if (isTailCall)
2179 InChain = TCChain;
2180
2181 TargetLowering::CallLoweringInfo CLI(DAG);
2182 bool signExtend = TLI.shouldSignExtendTypeInLibCall(RetTy, IsSigned);
2183 CLI.setDebugLoc(SDLoc(Node))
2184 .setChain(InChain)
2185 .setLibCallee(DAG.getLibcalls().getLibcallImplCallingConv(LCImpl), RetTy,
2186 Callee, std::move(Args))
2187 .setTailCall(isTailCall)
2188 .setSExtResult(signExtend)
2189 .setZExtResult(!signExtend)
2190 .setIsPostTypeLegalization(true);
2191
2192 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2193
2194 if (!CallInfo.second.getNode()) {
2195 LLVM_DEBUG(dbgs() << "Created tailcall: "; DAG.getRoot().dump(&DAG));
2196 // It's a tailcall, return the chain (which is the DAG root).
2197 return {DAG.getRoot(), DAG.getRoot()};
2198 }
2199
2200 LLVM_DEBUG(dbgs() << "Created libcall: "; CallInfo.first.dump(&DAG));
2201 return CallInfo;
2202}
2203
2204std::pair<SDValue, SDValue> SelectionDAGLegalize::ExpandLibCall(RTLIB::Libcall LC, SDNode *Node,
2205 bool isSigned) {
2206 TargetLowering::ArgListTy Args;
2207 for (const SDValue &Op : Node->op_values()) {
2208 EVT ArgVT = Op.getValueType();
2209 Type *ArgTy = ArgVT.getTypeForEVT(*DAG.getContext());
2210 TargetLowering::ArgListEntry Entry(Op, ArgTy);
2211 Entry.IsSExt = TLI.shouldSignExtendTypeInLibCall(ArgTy, isSigned);
2212 Entry.IsZExt = !Entry.IsSExt;
2213 Args.push_back(Entry);
2214 }
2215
2216 return ExpandLibCall(LC, Node, std::move(Args), isSigned,
2217 Node->getValueType(0));
2218}
2219
2220void SelectionDAGLegalize::ExpandFPLibCall(SDNode* Node,
2221 RTLIB::Libcall LC,
2222 SmallVectorImpl<SDValue> &Results) {
2223 if (LC == RTLIB::UNKNOWN_LIBCALL)
2224 llvm_unreachable("Can't create an unknown libcall!");
2225
2226 if (Node->isStrictFPOpcode()) {
2227 EVT RetVT = Node->getValueType(0);
2229 TargetLowering::MakeLibCallOptions CallOptions;
2230 CallOptions.IsPostTypeLegalization = true;
2231 // FIXME: This doesn't support tail calls.
2232 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(DAG, LC, RetVT,
2233 Ops, CallOptions,
2234 SDLoc(Node),
2235 Node->getOperand(0));
2236 Results.push_back(Tmp.first);
2237 Results.push_back(Tmp.second);
2238 } else {
2239 bool IsSignedArgument = Node->getOpcode() == ISD::FLDEXP;
2240 SDValue Tmp = ExpandLibCall(LC, Node, IsSignedArgument).first;
2241 Results.push_back(Tmp);
2242 }
2243}
2244
2245/// Expand the node to a libcall based on the result type.
2246void SelectionDAGLegalize::ExpandFPLibCall(SDNode* Node,
2247 RTLIB::Libcall Call_F32,
2248 RTLIB::Libcall Call_F64,
2249 RTLIB::Libcall Call_F80,
2250 RTLIB::Libcall Call_F128,
2251 RTLIB::Libcall Call_PPCF128,
2252 SmallVectorImpl<SDValue> &Results) {
2253 RTLIB::Libcall LC = RTLIB::getFPLibCall(Node->getSimpleValueType(0),
2254 Call_F32, Call_F64, Call_F80,
2255 Call_F128, Call_PPCF128);
2256 ExpandFPLibCall(Node, LC, Results);
2257}
2258
2259void SelectionDAGLegalize::ExpandFastFPLibCall(
2260 SDNode *Node, bool IsFast,
2261 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F32,
2262 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F64,
2263 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F80,
2264 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_F128,
2265 std::pair<RTLIB::Libcall, RTLIB::Libcall> Call_PPCF128,
2266 SmallVectorImpl<SDValue> &Results) {
2267
2268 EVT VT = Node->getSimpleValueType(0);
2269
2270 RTLIB::Libcall LC;
2271
2272 // FIXME: Probably should define fast to respect nan/inf and only be
2273 // approximate functions.
2274
2275 if (IsFast) {
2276 LC = RTLIB::getFPLibCall(VT, Call_F32.first, Call_F64.first, Call_F80.first,
2277 Call_F128.first, Call_PPCF128.first);
2278 }
2279
2280 if (!IsFast || DAG.getLibcalls().getLibcallImpl(LC) == RTLIB::Unsupported) {
2281 // Fall back if we don't have a fast implementation.
2282 LC = RTLIB::getFPLibCall(VT, Call_F32.second, Call_F64.second,
2283 Call_F80.second, Call_F128.second,
2284 Call_PPCF128.second);
2285 }
2286
2287 ExpandFPLibCall(Node, LC, Results);
2288}
2289
2290SDValue SelectionDAGLegalize::ExpandIntLibCall(SDNode* Node, bool isSigned,
2291 RTLIB::Libcall Call_I8,
2292 RTLIB::Libcall Call_I16,
2293 RTLIB::Libcall Call_I32,
2294 RTLIB::Libcall Call_I64,
2295 RTLIB::Libcall Call_I128) {
2296 RTLIB::Libcall LC;
2297 switch (Node->getSimpleValueType(0).SimpleTy) {
2298 default: llvm_unreachable("Unexpected request for libcall!");
2299 case MVT::i8: LC = Call_I8; break;
2300 case MVT::i16: LC = Call_I16; break;
2301 case MVT::i32: LC = Call_I32; break;
2302 case MVT::i64: LC = Call_I64; break;
2303 case MVT::i128: LC = Call_I128; break;
2304 }
2305 return ExpandLibCall(LC, Node, isSigned).first;
2306}
2307
2308/// Expand the node to a libcall based on first argument type (for instance
2309/// lround and its variant).
2310void SelectionDAGLegalize::ExpandArgFPLibCall(SDNode* Node,
2311 RTLIB::Libcall Call_F32,
2312 RTLIB::Libcall Call_F64,
2313 RTLIB::Libcall Call_F80,
2314 RTLIB::Libcall Call_F128,
2315 RTLIB::Libcall Call_PPCF128,
2316 SmallVectorImpl<SDValue> &Results) {
2317 EVT InVT = Node->getOperand(Node->isStrictFPOpcode() ? 1 : 0).getValueType();
2318 RTLIB::Libcall LC = RTLIB::getFPLibCall(InVT.getSimpleVT(),
2319 Call_F32, Call_F64, Call_F80,
2320 Call_F128, Call_PPCF128);
2321 ExpandFPLibCall(Node, LC, Results);
2322}
2323
2324SDValue SelectionDAGLegalize::ExpandBitCountingLibCall(
2325 SDNode *Node, RTLIB::Libcall CallI32, RTLIB::Libcall CallI64,
2326 RTLIB::Libcall CallI128) {
2327 RTLIB::Libcall LC;
2328 switch (Node->getSimpleValueType(0).SimpleTy) {
2329 default:
2330 llvm_unreachable("Unexpected request for libcall!");
2331 case MVT::i32:
2332 LC = CallI32;
2333 break;
2334 case MVT::i64:
2335 LC = CallI64;
2336 break;
2337 case MVT::i128:
2338 LC = CallI128;
2339 break;
2340 }
2341
2342 // Bit-counting libcalls have one unsigned argument and return `int`.
2343 // Note that `int` may be illegal on this target; ExpandLibCall will
2344 // take care of promoting it to a legal type.
2345 SDValue Op = Node->getOperand(0);
2346 EVT IntVT =
2348
2349 EVT ArgVT = Op.getValueType();
2350 Type *ArgTy = ArgVT.getTypeForEVT(*DAG.getContext());
2351 TargetLowering::ArgListEntry Arg(Op, ArgTy);
2352 Arg.IsSExt = TLI.shouldSignExtendTypeInLibCall(ArgTy, /*IsSigned=*/false);
2353 Arg.IsZExt = !Arg.IsSExt;
2354
2355 SDValue Res = ExpandLibCall(LC, Node, TargetLowering::ArgListTy{Arg},
2356 /*IsSigned=*/true, IntVT)
2357 .first;
2358
2359 // If ExpandLibCall created a tail call, the result was already
2360 // of the correct type. Otherwise, we need to sign extend it.
2361 if (Res.getValueType() != MVT::Other)
2362 Res = DAG.getSExtOrTrunc(Res, SDLoc(Node), Node->getValueType(0));
2363 return Res;
2364}
2365
2366/// Issue libcalls to __{u}divmod to compute div / rem pairs.
2367void
2368SelectionDAGLegalize::ExpandDivRemLibCall(SDNode *Node,
2369 SmallVectorImpl<SDValue> &Results) {
2370 unsigned Opcode = Node->getOpcode();
2371 bool isSigned = Opcode == ISD::SDIVREM;
2372
2373 RTLIB::Libcall LC;
2374 switch (Node->getSimpleValueType(0).SimpleTy) {
2375 default: llvm_unreachable("Unexpected request for libcall!");
2376 case MVT::i8: LC= isSigned ? RTLIB::SDIVREM_I8 : RTLIB::UDIVREM_I8; break;
2377 case MVT::i16: LC= isSigned ? RTLIB::SDIVREM_I16 : RTLIB::UDIVREM_I16; break;
2378 case MVT::i32: LC= isSigned ? RTLIB::SDIVREM_I32 : RTLIB::UDIVREM_I32; break;
2379 case MVT::i64: LC= isSigned ? RTLIB::SDIVREM_I64 : RTLIB::UDIVREM_I64; break;
2380 case MVT::i128: LC= isSigned ? RTLIB::SDIVREM_I128:RTLIB::UDIVREM_I128; break;
2381 }
2382
2383 // The input chain to this libcall is the entry node of the function.
2384 // Legalizing the call will automatically add the previous call to the
2385 // dependence.
2386 SDValue InChain = DAG.getEntryNode();
2387
2388 EVT RetVT = Node->getValueType(0);
2389 Type *RetTy = RetVT.getTypeForEVT(*DAG.getContext());
2390
2391 TargetLowering::ArgListTy Args;
2392 for (const SDValue &Op : Node->op_values()) {
2393 EVT ArgVT = Op.getValueType();
2394 Type *ArgTy = ArgVT.getTypeForEVT(*DAG.getContext());
2395 TargetLowering::ArgListEntry Entry(Op, ArgTy);
2396 Entry.IsSExt = isSigned;
2397 Entry.IsZExt = !isSigned;
2398 Args.push_back(Entry);
2399 }
2400
2401 // Also pass the return address of the remainder.
2402 SDValue FIPtr = DAG.CreateStackTemporary(RetVT);
2403 TargetLowering::ArgListEntry Entry(
2404 FIPtr, PointerType::getUnqual(RetTy->getContext()));
2405 Entry.IsSExt = isSigned;
2406 Entry.IsZExt = !isSigned;
2407 Args.push_back(Entry);
2408
2409 RTLIB::LibcallImpl LibcallImpl = DAG.getLibcalls().getLibcallImpl(LC);
2410 if (LibcallImpl == RTLIB::Unsupported) {
2411 DAG.getContext()->emitError(Twine("no libcall available for ") +
2412 Node->getOperationName(&DAG));
2413 SDValue Poison = DAG.getPOISON(RetVT);
2414 Results.push_back(Poison);
2415 Results.push_back(Poison);
2416 return;
2417 }
2418
2419 SDValue Callee =
2420 DAG.getExternalSymbol(LibcallImpl, TLI.getPointerTy(DAG.getDataLayout()));
2421
2422 SDLoc dl(Node);
2423 TargetLowering::CallLoweringInfo CLI(DAG);
2424 CLI.setDebugLoc(dl)
2425 .setChain(InChain)
2426 .setLibCallee(DAG.getLibcalls().getLibcallImplCallingConv(LibcallImpl),
2427 RetTy, Callee, std::move(Args))
2428 .setSExtResult(isSigned)
2429 .setZExtResult(!isSigned);
2430
2431 std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2432
2433 // Remainder is loaded back from the stack frame.
2434 int FI = cast<FrameIndexSDNode>(FIPtr)->getIndex();
2435 MachinePointerInfo PtrInfo =
2437
2438 SDValue Rem = DAG.getLoad(RetVT, dl, CallInfo.second, FIPtr, PtrInfo);
2439 Results.push_back(CallInfo.first);
2440 Results.push_back(Rem);
2441}
2442
2443/// Return true if sincos or __sincos_stret libcall is available.
2445 const LibcallLoweringInfo &Libcalls) {
2446 MVT::SimpleValueType VT = Node->getSimpleValueType(0).SimpleTy;
2447 return Libcalls.getLibcallImpl(RTLIB::getSINCOS(VT)) != RTLIB::Unsupported ||
2448 Libcalls.getLibcallImpl(RTLIB::getSINCOS_STRET(VT)) !=
2449 RTLIB::Unsupported;
2450}
2451
2452/// Only issue sincos libcall if both sin and cos are needed.
2453static bool useSinCos(SDNode *Node) {
2454 unsigned OtherOpcode = Node->getOpcode() == ISD::FSIN
2455 ? ISD::FCOS : ISD::FSIN;
2456
2457 SDValue Op0 = Node->getOperand(0);
2458 for (const SDNode *User : Op0.getNode()->users()) {
2459 if (User == Node)
2460 continue;
2461 // The other user might have been turned into sincos already.
2462 if (User->getOpcode() == OtherOpcode || User->getOpcode() == ISD::FSINCOS)
2463 return true;
2464 }
2465 return false;
2466}
2467
2468SDValue SelectionDAGLegalize::ExpandSincosStretLibCall(SDNode *Node) const {
2469 // For iOS, we want to call an alternative entry point: __sincos_stret,
2470 // which returns the values in two S / D registers.
2471 SDLoc dl(Node);
2472 SDValue Arg = Node->getOperand(0);
2473 EVT ArgVT = Arg.getValueType();
2474 RTLIB::Libcall LC = RTLIB::getSINCOS_STRET(ArgVT);
2475 RTLIB::LibcallImpl SincosStret = DAG.getLibcalls().getLibcallImpl(LC);
2476 if (SincosStret == RTLIB::Unsupported)
2477 return SDValue();
2478
2479 /// There are 3 different ABI cases to handle:
2480 /// - Direct return of separate fields in registers
2481 /// - Single return as vector elements
2482 /// - sret struct
2483
2484 const RTLIB::RuntimeLibcallsInfo &CallsInfo = TLI.getRuntimeLibcallsInfo();
2485
2486 const DataLayout &DL = DAG.getDataLayout();
2487
2488 auto [FuncTy, FuncAttrs] = CallsInfo.getFunctionTy(
2489 *DAG.getContext(), TM.getTargetTriple(), DL, SincosStret);
2490
2491 Type *SincosStretRetTy = FuncTy->getReturnType();
2492 CallingConv::ID CallConv = CallsInfo.getLibcallImplCallingConv(SincosStret);
2493
2494 SDValue Callee =
2495 DAG.getExternalSymbol(SincosStret, TLI.getProgramPointerTy(DL));
2496
2497 TargetLowering::ArgListTy Args;
2498 SDValue SRet;
2499
2500 int FrameIdx;
2501 if (FuncTy->getParamType(0)->isPointerTy()) {
2502 // Uses sret
2503 MachineFrameInfo &MFI = DAG.getMachineFunction().getFrameInfo();
2504
2505 AttributeSet PtrAttrs = FuncAttrs.getParamAttrs(0);
2506 Type *StructTy = PtrAttrs.getStructRetType();
2507 const uint64_t ByteSize = DL.getTypeAllocSize(StructTy);
2508 const Align StackAlign = DL.getPrefTypeAlign(StructTy);
2509
2510 FrameIdx = MFI.CreateStackObject(ByteSize, StackAlign, false);
2511 SRet = DAG.getFrameIndex(FrameIdx, TLI.getFrameIndexTy(DL));
2512
2513 TargetLowering::ArgListEntry Entry(SRet, FuncTy->getParamType(0));
2514 Entry.IsSRet = true;
2515 Entry.IndirectType = StructTy;
2516 Entry.Alignment = StackAlign;
2517
2518 Args.push_back(Entry);
2519 Args.emplace_back(Arg, FuncTy->getParamType(1));
2520 } else {
2521 Args.emplace_back(Arg, FuncTy->getParamType(0));
2522 }
2523
2524 TargetLowering::CallLoweringInfo CLI(DAG);
2525 CLI.setDebugLoc(dl)
2526 .setChain(DAG.getEntryNode())
2527 .setLibCallee(CallConv, SincosStretRetTy, Callee, std::move(Args))
2528 .setIsPostTypeLegalization();
2529
2530 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
2531
2532 if (SRet) {
2533 MachinePointerInfo PtrInfo =
2535 SDValue LoadSin = DAG.getLoad(ArgVT, dl, CallResult.second, SRet, PtrInfo);
2536
2537 TypeSize StoreSize = ArgVT.getStoreSize();
2538
2539 // Address of cos field.
2540 SDValue Add = DAG.getObjectPtrOffset(dl, SRet, StoreSize);
2541 SDValue LoadCos = DAG.getLoad(ArgVT, dl, LoadSin.getValue(1), Add,
2542 PtrInfo.getWithOffset(StoreSize));
2543
2544 SDVTList Tys = DAG.getVTList(ArgVT, ArgVT);
2545 return DAG.getNode(ISD::MERGE_VALUES, dl, Tys, LoadSin.getValue(0),
2546 LoadCos.getValue(0));
2547 }
2548
2549 if (!CallResult.first.getValueType().isVector())
2550 return CallResult.first;
2551
2552 SDValue SinVal =
2553 DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, ArgVT, CallResult.first,
2554 DAG.getVectorIdxConstant(0, dl));
2555 SDValue CosVal =
2556 DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, ArgVT, CallResult.first,
2557 DAG.getVectorIdxConstant(1, dl));
2558 SDVTList Tys = DAG.getVTList(ArgVT, ArgVT);
2559 return DAG.getNode(ISD::MERGE_VALUES, dl, Tys, SinVal, CosVal);
2560}
2561
2562SDValue SelectionDAGLegalize::expandLdexp(SDNode *Node) const {
2563 SDLoc dl(Node);
2564 EVT VT = Node->getValueType(0);
2565 SDValue X = Node->getOperand(0);
2566 SDValue N = Node->getOperand(1);
2567 EVT ExpVT = N.getValueType();
2568 EVT AsIntVT = VT.changeTypeToInteger();
2569 if (AsIntVT == EVT()) // TODO: How to handle f80?
2570 return SDValue();
2571
2572 if (Node->getOpcode() == ISD::STRICT_FLDEXP) // TODO
2573 return SDValue();
2574
2575 SDNodeFlags NSW;
2576 NSW.setNoSignedWrap(true);
2577 SDNodeFlags NUW_NSW;
2578 NUW_NSW.setNoUnsignedWrap(true);
2579 NUW_NSW.setNoSignedWrap(true);
2580
2581 EVT SetCCVT =
2582 TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), ExpVT);
2583 const fltSemantics &FltSem = VT.getFltSemantics();
2584
2585 const APFloat::ExponentType MaxExpVal = APFloat::semanticsMaxExponent(FltSem);
2586 const APFloat::ExponentType MinExpVal = APFloat::semanticsMinExponent(FltSem);
2587 const int Precision = APFloat::semanticsPrecision(FltSem);
2588
2589 const SDValue MaxExp = DAG.getSignedConstant(MaxExpVal, dl, ExpVT);
2590 const SDValue MinExp = DAG.getSignedConstant(MinExpVal, dl, ExpVT);
2591
2592 const SDValue DoubleMaxExp = DAG.getSignedConstant(2 * MaxExpVal, dl, ExpVT);
2593
2594 const APFloat One(FltSem, "1.0");
2595 APFloat ScaleUpK = scalbn(One, MaxExpVal, APFloat::rmNearestTiesToEven);
2596
2597 // Offset by precision to avoid denormal range.
2598 APFloat ScaleDownK =
2599 scalbn(One, MinExpVal + Precision, APFloat::rmNearestTiesToEven);
2600
2601 // TODO: Should really introduce control flow and use a block for the >
2602 // MaxExp, < MinExp cases
2603
2604 // First, handle exponents Exp > MaxExp and scale down.
2605 SDValue NGtMaxExp = DAG.getSetCC(dl, SetCCVT, N, MaxExp, ISD::SETGT);
2606
2607 SDValue DecN0 = DAG.getNode(ISD::SUB, dl, ExpVT, N, MaxExp, NSW);
2608 SDValue ClampMaxVal = DAG.getConstant(3 * MaxExpVal, dl, ExpVT);
2609 SDValue ClampN_Big = DAG.getNode(ISD::SMIN, dl, ExpVT, N, ClampMaxVal);
2610 SDValue DecN1 =
2611 DAG.getNode(ISD::SUB, dl, ExpVT, ClampN_Big, DoubleMaxExp, NSW);
2612
2613 SDValue ScaleUpTwice =
2614 DAG.getSetCC(dl, SetCCVT, N, DoubleMaxExp, ISD::SETUGT);
2615
2616 const SDValue ScaleUpVal = DAG.getConstantFP(ScaleUpK, dl, VT);
2617 SDValue ScaleUp0 = DAG.getNode(ISD::FMUL, dl, VT, X, ScaleUpVal);
2618 SDValue ScaleUp1 = DAG.getNode(ISD::FMUL, dl, VT, ScaleUp0, ScaleUpVal);
2619
2620 SDValue SelectN_Big =
2621 DAG.getNode(ISD::SELECT, dl, ExpVT, ScaleUpTwice, DecN1, DecN0);
2622 SDValue SelectX_Big =
2623 DAG.getNode(ISD::SELECT, dl, VT, ScaleUpTwice, ScaleUp1, ScaleUp0);
2624
2625 // Now handle exponents Exp < MinExp
2626 SDValue NLtMinExp = DAG.getSetCC(dl, SetCCVT, N, MinExp, ISD::SETLT);
2627
2628 SDValue Increment0 = DAG.getConstant(-(MinExpVal + Precision), dl, ExpVT);
2629 SDValue Increment1 = DAG.getConstant(-2 * (MinExpVal + Precision), dl, ExpVT);
2630
2631 SDValue IncN0 = DAG.getNode(ISD::ADD, dl, ExpVT, N, Increment0, NUW_NSW);
2632
2633 SDValue ClampMinVal =
2634 DAG.getSignedConstant(3 * MinExpVal + 2 * Precision, dl, ExpVT);
2635 SDValue ClampN_Small = DAG.getNode(ISD::SMAX, dl, ExpVT, N, ClampMinVal);
2636 SDValue IncN1 =
2637 DAG.getNode(ISD::ADD, dl, ExpVT, ClampN_Small, Increment1, NSW);
2638
2639 const SDValue ScaleDownVal = DAG.getConstantFP(ScaleDownK, dl, VT);
2640 SDValue ScaleDown0 = DAG.getNode(ISD::FMUL, dl, VT, X, ScaleDownVal);
2641 SDValue ScaleDown1 = DAG.getNode(ISD::FMUL, dl, VT, ScaleDown0, ScaleDownVal);
2642
2643 SDValue ScaleDownTwice = DAG.getSetCC(
2644 dl, SetCCVT, N,
2645 DAG.getSignedConstant(2 * MinExpVal + Precision, dl, ExpVT), ISD::SETULT);
2646
2647 SDValue SelectN_Small =
2648 DAG.getNode(ISD::SELECT, dl, ExpVT, ScaleDownTwice, IncN1, IncN0);
2649 SDValue SelectX_Small =
2650 DAG.getNode(ISD::SELECT, dl, VT, ScaleDownTwice, ScaleDown1, ScaleDown0);
2651
2652 // Now combine the two out of range exponent handling cases with the base
2653 // case.
2654 SDValue NewX = DAG.getNode(
2655 ISD::SELECT, dl, VT, NGtMaxExp, SelectX_Big,
2656 DAG.getNode(ISD::SELECT, dl, VT, NLtMinExp, SelectX_Small, X));
2657
2658 SDValue NewN = DAG.getNode(
2659 ISD::SELECT, dl, ExpVT, NGtMaxExp, SelectN_Big,
2660 DAG.getNode(ISD::SELECT, dl, ExpVT, NLtMinExp, SelectN_Small, N));
2661
2662 SDValue BiasedN = DAG.getNode(ISD::ADD, dl, ExpVT, NewN, MaxExp, NSW);
2663
2664 SDValue ExponentShiftAmt =
2665 DAG.getShiftAmountConstant(Precision - 1, ExpVT, dl);
2666 SDValue CastExpToValTy = DAG.getZExtOrTrunc(BiasedN, dl, AsIntVT);
2667
2668 SDValue AsInt = DAG.getNode(ISD::SHL, dl, AsIntVT, CastExpToValTy,
2669 ExponentShiftAmt, NUW_NSW);
2670 SDValue AsFP = DAG.getNode(ISD::BITCAST, dl, VT, AsInt);
2671 return DAG.getNode(ISD::FMUL, dl, VT, NewX, AsFP);
2672}
2673
2674SDValue SelectionDAGLegalize::expandFrexp(SDNode *Node) const {
2675 SDLoc dl(Node);
2676 SDValue Val = Node->getOperand(0);
2677 EVT VT = Val.getValueType();
2678 EVT ExpVT = Node->getValueType(1);
2679 EVT AsIntVT = VT.changeTypeToInteger();
2680 if (AsIntVT == EVT()) // TODO: How to handle f80?
2681 return SDValue();
2682
2683 const fltSemantics &FltSem = VT.getFltSemantics();
2684 const APFloat::ExponentType MinExpVal = APFloat::semanticsMinExponent(FltSem);
2685 const unsigned Precision = APFloat::semanticsPrecision(FltSem);
2686 const unsigned BitSize = VT.getScalarSizeInBits();
2687
2688 // TODO: Could introduce control flow and skip over the denormal handling.
2689
2690 // scale_up = fmul value, scalbn(1.0, precision + 1)
2691 // extracted_exp = (bitcast value to uint) >> precision - 1
2692 // biased_exp = extracted_exp + min_exp
2693 // extracted_fract = (bitcast value to uint) & (fract_mask | sign_mask)
2694 //
2695 // is_denormal = val < smallest_normalized
2696 // computed_fract = is_denormal ? scale_up : extracted_fract
2697 // computed_exp = is_denormal ? biased_exp + (-precision - 1) : biased_exp
2698 //
2699 // result_0 = (!isfinite(val) || iszero(val)) ? val : computed_fract
2700 // result_1 = (!isfinite(val) || iszero(val)) ? 0 : computed_exp
2701
2702 SDValue NegSmallestNormalizedInt = DAG.getConstant(
2703 APFloat::getSmallestNormalized(FltSem, true).bitcastToAPInt(), dl,
2704 AsIntVT);
2705
2706 SDValue SmallestNormalizedInt = DAG.getConstant(
2707 APFloat::getSmallestNormalized(FltSem, false).bitcastToAPInt(), dl,
2708 AsIntVT);
2709
2710 // Masks out the exponent bits.
2711 SDValue ExpMask =
2712 DAG.getConstant(APFloat::getInf(FltSem).bitcastToAPInt(), dl, AsIntVT);
2713
2714 // Mask out the exponent part of the value.
2715 //
2716 // e.g, for f32 FractSignMaskVal = 0x807fffff
2717 APInt FractSignMaskVal = APInt::getBitsSet(BitSize, 0, Precision - 1);
2718 FractSignMaskVal.setBit(BitSize - 1); // Set the sign bit
2719
2720 APInt SignMaskVal = APInt::getSignedMaxValue(BitSize);
2721 SDValue SignMask = DAG.getConstant(SignMaskVal, dl, AsIntVT);
2722
2723 SDValue FractSignMask = DAG.getConstant(FractSignMaskVal, dl, AsIntVT);
2724
2725 const APFloat One(FltSem, "1.0");
2726 // Scale a possible denormal input.
2727 // e.g., for f64, 0x1p+54
2728 APFloat ScaleUpKVal =
2729 scalbn(One, Precision + 1, APFloat::rmNearestTiesToEven);
2730
2731 SDValue ScaleUpK = DAG.getConstantFP(ScaleUpKVal, dl, VT);
2732 SDValue ScaleUp = DAG.getNode(ISD::FMUL, dl, VT, Val, ScaleUpK);
2733
2734 EVT SetCCVT =
2735 TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), VT);
2736
2737 SDValue AsInt = DAG.getNode(ISD::BITCAST, dl, AsIntVT, Val);
2738
2739 SDValue Abs = DAG.getNode(ISD::AND, dl, AsIntVT, AsInt, SignMask);
2740
2741 SDValue AddNegSmallestNormal =
2742 DAG.getNode(ISD::ADD, dl, AsIntVT, Abs, NegSmallestNormalizedInt);
2743 SDValue DenormOrZero = DAG.getSetCC(dl, SetCCVT, AddNegSmallestNormal,
2744 NegSmallestNormalizedInt, ISD::SETULE);
2745
2746 SDValue IsDenormal =
2747 DAG.getSetCC(dl, SetCCVT, Abs, SmallestNormalizedInt, ISD::SETULT);
2748
2749 SDValue MinExp = DAG.getSignedConstant(MinExpVal, dl, ExpVT);
2750 SDValue Zero = DAG.getConstant(0, dl, ExpVT);
2751
2752 SDValue ScaledAsInt = DAG.getNode(ISD::BITCAST, dl, AsIntVT, ScaleUp);
2753 SDValue ScaledSelect =
2754 DAG.getNode(ISD::SELECT, dl, AsIntVT, IsDenormal, ScaledAsInt, AsInt);
2755
2756 SDValue ExpMaskScaled =
2757 DAG.getNode(ISD::AND, dl, AsIntVT, ScaledAsInt, ExpMask);
2758
2759 SDValue ScaledValue =
2760 DAG.getNode(ISD::SELECT, dl, AsIntVT, IsDenormal, ExpMaskScaled, Abs);
2761
2762 // Extract the exponent bits.
2763 SDValue ExponentShiftAmt =
2764 DAG.getShiftAmountConstant(Precision - 1, AsIntVT, dl);
2765 SDValue ShiftedExp =
2766 DAG.getNode(ISD::SRL, dl, AsIntVT, ScaledValue, ExponentShiftAmt);
2767 SDValue Exp = DAG.getSExtOrTrunc(ShiftedExp, dl, ExpVT);
2768
2769 SDValue NormalBiasedExp = DAG.getNode(ISD::ADD, dl, ExpVT, Exp, MinExp);
2770 SDValue DenormalOffset = DAG.getConstant(-Precision - 1, dl, ExpVT);
2771 SDValue DenormalExpBias =
2772 DAG.getNode(ISD::SELECT, dl, ExpVT, IsDenormal, DenormalOffset, Zero);
2773
2774 SDValue MaskedFractAsInt =
2775 DAG.getNode(ISD::AND, dl, AsIntVT, ScaledSelect, FractSignMask);
2776 const APFloat Half(FltSem, "0.5");
2777 SDValue FPHalf = DAG.getConstant(Half.bitcastToAPInt(), dl, AsIntVT);
2778 SDValue Or = DAG.getNode(ISD::OR, dl, AsIntVT, MaskedFractAsInt, FPHalf);
2779 SDValue MaskedFract = DAG.getNode(ISD::BITCAST, dl, VT, Or);
2780
2781 SDValue ComputedExp =
2782 DAG.getNode(ISD::ADD, dl, ExpVT, NormalBiasedExp, DenormalExpBias);
2783
2784 SDValue Result0 =
2785 DAG.getNode(ISD::SELECT, dl, VT, DenormOrZero, Val, MaskedFract);
2786
2787 SDValue Result1 =
2788 DAG.getNode(ISD::SELECT, dl, ExpVT, DenormOrZero, Zero, ComputedExp);
2789
2790 return DAG.getMergeValues({Result0, Result1}, dl);
2791}
2792
2793SDValue SelectionDAGLegalize::expandModf(SDNode *Node) const {
2794 SDLoc dl(Node);
2795 SDValue Val = Node->getOperand(0);
2796 EVT VT = Val.getValueType();
2797 SDNodeFlags Flags = Node->getFlags();
2798
2799 SDValue IntPart = DAG.getNode(ISD::FTRUNC, dl, VT, Val, Flags);
2800 SDValue FracPart = DAG.getNode(ISD::FSUB, dl, VT, Val, IntPart, Flags);
2801
2802 SDValue FracToUse;
2803 if (Flags.hasNoInfs()) {
2804 FracToUse = FracPart;
2805 } else {
2806 SDValue Abs = DAG.getNode(ISD::FABS, dl, VT, Val, Flags);
2807 SDValue Inf =
2809 EVT SetCCVT =
2810 TLI.getSetCCResultType(DAG.getDataLayout(), *DAG.getContext(), VT);
2811 SDValue IsInf = DAG.getSetCC(dl, SetCCVT, Abs, Inf, ISD::SETOEQ);
2812 SDValue Zero = DAG.getConstantFP(0.0, dl, VT);
2813 FracToUse = DAG.getSelect(dl, VT, IsInf, Zero, FracPart);
2814 }
2815
2816 SDValue ResultFrac =
2817 DAG.getNode(ISD::FCOPYSIGN, dl, VT, FracToUse, Val, Flags);
2818 return DAG.getMergeValues({ResultFrac, IntPart}, dl);
2819}
2820
2821/// This function is responsible for legalizing a
2822/// INT_TO_FP operation of the specified operand when the target requests that
2823/// we expand it. At this point, we know that the result and operand types are
2824/// legal for the target.
2825SDValue SelectionDAGLegalize::ExpandLegalINT_TO_FP(SDNode *Node,
2826 SDValue &Chain) {
2827 bool isSigned = (Node->getOpcode() == ISD::STRICT_SINT_TO_FP ||
2828 Node->getOpcode() == ISD::SINT_TO_FP);
2829 EVT DestVT = Node->getValueType(0);
2830 SDLoc dl(Node);
2831 unsigned OpNo = Node->isStrictFPOpcode() ? 1 : 0;
2832 SDValue Op0 = Node->getOperand(OpNo);
2833 EVT SrcVT = Op0.getValueType();
2834
2835 // TODO: Should any fast-math-flags be set for the created nodes?
2836 LLVM_DEBUG(dbgs() << "Legalizing INT_TO_FP\n");
2837 if (SrcVT == MVT::i32 && TLI.isTypeLegal(MVT::f64) &&
2838 (DestVT.bitsLE(MVT::f64) ||
2839 TLI.isOperationLegal(Node->isStrictFPOpcode() ? ISD::STRICT_FP_EXTEND
2841 DestVT))) {
2842 LLVM_DEBUG(dbgs() << "32-bit [signed|unsigned] integer to float/double "
2843 "expansion\n");
2844
2845 // Get the stack frame index of a 8 byte buffer.
2846 SDValue StackSlot = DAG.CreateStackTemporary(MVT::f64);
2847
2848 SDValue Lo = Op0;
2849 // if signed map to unsigned space
2850 if (isSigned) {
2851 // Invert sign bit (signed to unsigned mapping).
2852 Lo = DAG.getNode(ISD::XOR, dl, MVT::i32, Lo,
2853 DAG.getConstant(0x80000000u, dl, MVT::i32));
2854 }
2855 // Initial hi portion of constructed double.
2856 SDValue Hi = DAG.getConstant(0x43300000u, dl, MVT::i32);
2857
2858 // If this a big endian target, swap the lo and high data.
2859 if (DAG.getDataLayout().isBigEndian())
2860 std::swap(Lo, Hi);
2861
2862 SDValue MemChain = DAG.getEntryNode();
2863
2864 // Store the lo of the constructed double.
2865 SDValue Store1 = DAG.getStore(MemChain, dl, Lo, StackSlot,
2866 MachinePointerInfo());
2867 // Store the hi of the constructed double.
2868 SDValue HiPtr =
2869 DAG.getMemBasePlusOffset(StackSlot, TypeSize::getFixed(4), dl);
2870 SDValue Store2 =
2871 DAG.getStore(MemChain, dl, Hi, HiPtr, MachinePointerInfo());
2872 MemChain = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Store1, Store2);
2873
2874 // load the constructed double
2875 SDValue Load =
2876 DAG.getLoad(MVT::f64, dl, MemChain, StackSlot, MachinePointerInfo());
2877 // FP constant to bias correct the final result
2878 SDValue Bias = DAG.getConstantFP(
2879 isSigned ? llvm::bit_cast<double>(0x4330000080000000ULL)
2880 : llvm::bit_cast<double>(0x4330000000000000ULL),
2881 dl, MVT::f64);
2882 // Subtract the bias and get the final result.
2883 SDValue Sub;
2885 if (Node->isStrictFPOpcode()) {
2886 Sub = DAG.getNode(ISD::STRICT_FSUB, dl, {MVT::f64, MVT::Other},
2887 {Node->getOperand(0), Load, Bias});
2888 Chain = Sub.getValue(1);
2889 if (DestVT != Sub.getValueType()) {
2890 std::pair<SDValue, SDValue> ResultPair;
2891 ResultPair =
2892 DAG.getStrictFPExtendOrRound(Sub, Chain, dl, DestVT);
2893 Result = ResultPair.first;
2894 Chain = ResultPair.second;
2895 }
2896 else
2897 Result = Sub;
2898 } else {
2899 Sub = DAG.getNode(ISD::FSUB, dl, MVT::f64, Load, Bias);
2900 Result = DAG.getFPExtendOrRound(Sub, dl, DestVT);
2901 }
2902 return Result;
2903 }
2904
2905 if (isSigned)
2906 return SDValue();
2907
2908 // TODO: Generalize this for use with other types.
2909 if (((SrcVT == MVT::i32 || SrcVT == MVT::i64) && DestVT == MVT::f32) ||
2910 (SrcVT == MVT::i64 && DestVT == MVT::f64)) {
2911 LLVM_DEBUG(dbgs() << "Converting unsigned i32/i64 to f32/f64\n");
2912 // For unsigned conversions, convert them to signed conversions using the
2913 // algorithm from the x86_64 __floatundisf in compiler_rt. That method
2914 // should be valid for i32->f32 as well.
2915
2916 // More generally this transform should be valid if there are 3 more bits
2917 // in the integer type than the significand. Rounding uses the first bit
2918 // after the width of the significand and the OR of all bits after that. So
2919 // we need to be able to OR the shifted out bit into one of the bits that
2920 // participate in the OR.
2921
2922 // TODO: This really should be implemented using a branch rather than a
2923 // select. We happen to get lucky and machinesink does the right
2924 // thing most of the time. This would be a good candidate for a
2925 // pseudo-op, or, even better, for whole-function isel.
2926 EVT SetCCVT = getSetCCResultType(SrcVT);
2927
2928 SDValue SignBitTest = DAG.getSetCC(
2929 dl, SetCCVT, Op0, DAG.getConstant(0, dl, SrcVT), ISD::SETLT);
2930
2931 SDValue ShiftConst = DAG.getShiftAmountConstant(1, SrcVT, dl);
2932 SDValue Shr = DAG.getNode(ISD::SRL, dl, SrcVT, Op0, ShiftConst);
2933 SDValue AndConst = DAG.getConstant(1, dl, SrcVT);
2934 SDValue And = DAG.getNode(ISD::AND, dl, SrcVT, Op0, AndConst);
2935 SDValue Or = DAG.getNode(ISD::OR, dl, SrcVT, And, Shr);
2936
2937 SDValue Slow, Fast;
2938 if (Node->isStrictFPOpcode()) {
2939 // In strict mode, we must avoid spurious exceptions, and therefore
2940 // must make sure to only emit a single STRICT_SINT_TO_FP.
2941 SDValue InCvt = DAG.getSelect(dl, SrcVT, SignBitTest, Or, Op0);
2942 // The STRICT_SINT_TO_FP inherits the exception mode from the
2943 // incoming STRICT_UINT_TO_FP node; the STRICT_FADD node can
2944 // never raise any exception.
2945 SDNodeFlags Flags;
2946 Flags.setNoFPExcept(Node->getFlags().hasNoFPExcept());
2947 Fast = DAG.getNode(ISD::STRICT_SINT_TO_FP, dl, {DestVT, MVT::Other},
2948 {Node->getOperand(0), InCvt}, Flags);
2949 Flags.setNoFPExcept(true);
2950 Slow = DAG.getNode(ISD::STRICT_FADD, dl, {DestVT, MVT::Other},
2951 {Fast.getValue(1), Fast, Fast}, Flags);
2952 Chain = Slow.getValue(1);
2953 } else {
2954 SDValue SignCvt = DAG.getNode(ISD::SINT_TO_FP, dl, DestVT, Or);
2955 Slow = DAG.getNode(ISD::FADD, dl, DestVT, SignCvt, SignCvt);
2956 Fast = DAG.getNode(ISD::SINT_TO_FP, dl, DestVT, Op0);
2957 }
2958
2959 return DAG.getSelect(dl, DestVT, SignBitTest, Slow, Fast);
2960 }
2961
2962 // Don't expand it if there isn't cheap fadd.
2963 if (!TLI.isOperationLegalOrCustom(
2964 Node->isStrictFPOpcode() ? ISD::STRICT_FADD : ISD::FADD, DestVT))
2965 return SDValue();
2966
2967 // The following optimization is valid only if every value in SrcVT (when
2968 // treated as signed) is representable in DestVT. Check that the mantissa
2969 // size of DestVT is >= than the number of bits in SrcVT -1.
2970 assert(APFloat::semanticsPrecision(DestVT.getFltSemantics()) >=
2971 SrcVT.getSizeInBits() - 1 &&
2972 "Cannot perform lossless SINT_TO_FP!");
2973
2974 SDValue Tmp1;
2975 if (Node->isStrictFPOpcode()) {
2976 Tmp1 = DAG.getNode(ISD::STRICT_SINT_TO_FP, dl, { DestVT, MVT::Other },
2977 { Node->getOperand(0), Op0 });
2978 } else
2979 Tmp1 = DAG.getNode(ISD::SINT_TO_FP, dl, DestVT, Op0);
2980
2981 SDValue SignSet = DAG.getSetCC(dl, getSetCCResultType(SrcVT), Op0,
2982 DAG.getConstant(0, dl, SrcVT), ISD::SETLT);
2983 SDValue Zero = DAG.getIntPtrConstant(0, dl),
2984 Four = DAG.getIntPtrConstant(4, dl);
2985 SDValue CstOffset = DAG.getSelect(dl, Zero.getValueType(),
2986 SignSet, Four, Zero);
2987
2988 // If the sign bit of the integer is set, the large number will be treated
2989 // as a negative number. To counteract this, the dynamic code adds an
2990 // offset depending on the data type.
2991 uint64_t FF;
2992 switch (SrcVT.getSimpleVT().SimpleTy) {
2993 default:
2994 return SDValue();
2995 case MVT::i8 : FF = 0x43800000ULL; break; // 2^8 (as a float)
2996 case MVT::i16: FF = 0x47800000ULL; break; // 2^16 (as a float)
2997 case MVT::i32: FF = 0x4F800000ULL; break; // 2^32 (as a float)
2998 case MVT::i64: FF = 0x5F800000ULL; break; // 2^64 (as a float)
2999 }
3000 if (DAG.getDataLayout().isLittleEndian())
3001 FF <<= 32;
3002 Constant *FudgeFactor = ConstantInt::get(
3003 Type::getInt64Ty(*DAG.getContext()), FF);
3004
3005 SDValue CPIdx =
3006 DAG.getConstantPool(FudgeFactor, TLI.getPointerTy(DAG.getDataLayout()));
3007 Align Alignment = cast<ConstantPoolSDNode>(CPIdx)->getAlign();
3008 CPIdx = DAG.getNode(ISD::ADD, dl, CPIdx.getValueType(), CPIdx, CstOffset);
3009 Alignment = commonAlignment(Alignment, 4);
3010 SDValue FudgeInReg;
3011 if (DestVT == MVT::f32)
3012 FudgeInReg = DAG.getLoad(
3013 MVT::f32, dl, DAG.getEntryNode(), CPIdx,
3015 Alignment);
3016 else {
3017 SDValue Load = DAG.getExtLoad(
3018 ISD::EXTLOAD, dl, DestVT, DAG.getEntryNode(), CPIdx,
3020 Alignment);
3021 HandleSDNode Handle(Load);
3022 LegalizeOp(Load.getNode());
3023 FudgeInReg = Handle.getValue();
3024 }
3025
3026 if (Node->isStrictFPOpcode()) {
3027 SDValue Result = DAG.getNode(ISD::STRICT_FADD, dl, { DestVT, MVT::Other },
3028 { Tmp1.getValue(1), Tmp1, FudgeInReg });
3029 Chain = Result.getValue(1);
3030 return Result;
3031 }
3032
3033 return DAG.getNode(ISD::FADD, dl, DestVT, Tmp1, FudgeInReg);
3034}
3035
3036/// This function is responsible for legalizing a
3037/// *INT_TO_FP operation of the specified operand when the target requests that
3038/// we promote it. At this point, we know that the result and operand types are
3039/// legal for the target, and that there is a legal UINT_TO_FP or SINT_TO_FP
3040/// operation that takes a larger input.
3041void SelectionDAGLegalize::PromoteLegalINT_TO_FP(
3042 SDNode *N, const SDLoc &dl, SmallVectorImpl<SDValue> &Results) {
3043 bool IsStrict = N->isStrictFPOpcode();
3044 bool IsSigned = N->getOpcode() == ISD::SINT_TO_FP ||
3045 N->getOpcode() == ISD::STRICT_SINT_TO_FP;
3046 EVT DestVT = N->getValueType(0);
3047 SDValue LegalOp = N->getOperand(IsStrict ? 1 : 0);
3048 unsigned UIntOp = IsStrict ? ISD::STRICT_UINT_TO_FP : ISD::UINT_TO_FP;
3049 unsigned SIntOp = IsStrict ? ISD::STRICT_SINT_TO_FP : ISD::SINT_TO_FP;
3050
3051 // First step, figure out the appropriate *INT_TO_FP operation to use.
3052 EVT NewInTy = LegalOp.getValueType();
3053
3054 unsigned OpToUse = 0;
3055
3056 // Scan for the appropriate larger type to use.
3057 while (true) {
3058 NewInTy = (MVT::SimpleValueType)(NewInTy.getSimpleVT().SimpleTy+1);
3059 assert(NewInTy.isInteger() && "Ran out of possibilities!");
3060
3061 // If the target supports SINT_TO_FP of this type, use it.
3062 if (TLI.isOperationLegalOrCustom(SIntOp, NewInTy)) {
3063 OpToUse = SIntOp;
3064 break;
3065 }
3066 if (IsSigned)
3067 continue;
3068
3069 // If the target supports UINT_TO_FP of this type, use it.
3070 if (TLI.isOperationLegalOrCustom(UIntOp, NewInTy)) {
3071 OpToUse = UIntOp;
3072 break;
3073 }
3074
3075 // Otherwise, try a larger type.
3076 }
3077
3078 // Okay, we found the operation and type to use. Zero extend our input to the
3079 // desired type then run the operation on it.
3080 if (IsStrict) {
3081 SDValue Res =
3082 DAG.getNode(OpToUse, dl, {DestVT, MVT::Other},
3083 {N->getOperand(0),
3084 DAG.getNode(IsSigned ? ISD::SIGN_EXTEND : ISD::ZERO_EXTEND,
3085 dl, NewInTy, LegalOp)});
3086 Results.push_back(Res);
3087 Results.push_back(Res.getValue(1));
3088 return;
3089 }
3090
3091 Results.push_back(
3092 DAG.getNode(OpToUse, dl, DestVT,
3093 DAG.getNode(IsSigned ? ISD::SIGN_EXTEND : ISD::ZERO_EXTEND,
3094 dl, NewInTy, LegalOp)));
3095}
3096
3097/// This function is responsible for legalizing a
3098/// FP_TO_*INT operation of the specified operand when the target requests that
3099/// we promote it. At this point, we know that the result and operand types are
3100/// legal for the target, and that there is a legal FP_TO_UINT or FP_TO_SINT
3101/// operation that returns a larger result.
3102void SelectionDAGLegalize::PromoteLegalFP_TO_INT(SDNode *N, const SDLoc &dl,
3103 SmallVectorImpl<SDValue> &Results) {
3104 bool IsStrict = N->isStrictFPOpcode();
3105 bool IsSigned = N->getOpcode() == ISD::FP_TO_SINT ||
3106 N->getOpcode() == ISD::STRICT_FP_TO_SINT;
3107 EVT DestVT = N->getValueType(0);
3108 SDValue LegalOp = N->getOperand(IsStrict ? 1 : 0);
3109 // First step, figure out the appropriate FP_TO*INT operation to use.
3110 EVT NewOutTy = DestVT;
3111
3112 unsigned OpToUse = 0;
3113
3114 // Scan for the appropriate larger type to use.
3115 while (true) {
3116 NewOutTy = (MVT::SimpleValueType)(NewOutTy.getSimpleVT().SimpleTy+1);
3117 assert(NewOutTy.isInteger() && "Ran out of possibilities!");
3118
3119 // A larger signed type can hold all unsigned values of the requested type,
3120 // so using FP_TO_SINT is valid
3121 OpToUse = IsStrict ? ISD::STRICT_FP_TO_SINT : ISD::FP_TO_SINT;
3122 if (TLI.isOperationLegalOrCustom(OpToUse, NewOutTy))
3123 break;
3124
3125 // However, if the value may be < 0.0, we *must* use some FP_TO_SINT.
3126 OpToUse = IsStrict ? ISD::STRICT_FP_TO_UINT : ISD::FP_TO_UINT;
3127 if (!IsSigned && TLI.isOperationLegalOrCustom(OpToUse, NewOutTy))
3128 break;
3129
3130 // Otherwise, try a larger type.
3131 }
3132
3133 // Okay, we found the operation and type to use.
3135 if (IsStrict) {
3136 SDVTList VTs = DAG.getVTList(NewOutTy, MVT::Other);
3137 Operation = DAG.getNode(OpToUse, dl, VTs, N->getOperand(0), LegalOp);
3138 } else
3139 Operation = DAG.getNode(OpToUse, dl, NewOutTy, LegalOp);
3140
3141 // Truncate the result of the extended FP_TO_*INT operation to the desired
3142 // size.
3143 SDValue Trunc = DAG.getNode(ISD::TRUNCATE, dl, DestVT, Operation);
3144 Results.push_back(Trunc);
3145 if (IsStrict)
3146 Results.push_back(Operation.getValue(1));
3147}
3148
3149/// Promote FP_TO_*INT_SAT operation to a larger result type. At this point
3150/// the result and operand types are legal and there must be a legal
3151/// FP_TO_*INT_SAT operation for a larger result type.
3152SDValue SelectionDAGLegalize::PromoteLegalFP_TO_INT_SAT(SDNode *Node,
3153 const SDLoc &dl) {
3154 unsigned Opcode = Node->getOpcode();
3155
3156 // Scan for the appropriate larger type to use.
3157 EVT NewOutTy = Node->getValueType(0);
3158 while (true) {
3159 NewOutTy = (MVT::SimpleValueType)(NewOutTy.getSimpleVT().SimpleTy + 1);
3160 assert(NewOutTy.isInteger() && "Ran out of possibilities!");
3161
3162 if (TLI.isOperationLegalOrCustom(Opcode, NewOutTy))
3163 break;
3164 }
3165
3166 // Saturation width is determined by second operand, so we don't have to
3167 // perform any fixup and can directly truncate the result.
3168 SDValue Result = DAG.getNode(Opcode, dl, NewOutTy, Node->getOperand(0),
3169 Node->getOperand(1));
3170 return DAG.getNode(ISD::TRUNCATE, dl, Node->getValueType(0), Result);
3171}
3172
3173/// Open code the operations for PARITY of the specified operation.
3174SDValue SelectionDAGLegalize::ExpandPARITY(SDValue Op, const SDLoc &dl) {
3175 EVT VT = Op.getValueType();
3176 EVT ShVT = TLI.getShiftAmountTy(VT, DAG.getDataLayout());
3177 unsigned Sz = VT.getScalarSizeInBits();
3178
3179 // If CTPOP is legal, use it. Otherwise use shifts and xor.
3182 Result = DAG.getNode(ISD::CTPOP, dl, VT, Op);
3183 } else {
3184 Result = Op;
3185 for (unsigned i = Log2_32_Ceil(Sz); i != 0;) {
3186 SDValue Shift = DAG.getNode(ISD::SRL, dl, VT, Result,
3187 DAG.getConstant(1ULL << (--i), dl, ShVT));
3188 Result = DAG.getNode(ISD::XOR, dl, VT, Result, Shift);
3189 }
3190 }
3191
3192 return DAG.getNode(ISD::AND, dl, VT, Result, DAG.getConstant(1, dl, VT));
3193}
3194
3195SDValue SelectionDAGLegalize::PromoteReduction(SDNode *Node) {
3196 bool IsVPOpcode = ISD::isVPOpcode(Node->getOpcode());
3197 MVT VecVT = IsVPOpcode ? Node->getOperand(1).getSimpleValueType()
3198 : Node->getOperand(0).getSimpleValueType();
3199 MVT NewVecVT = TLI.getTypeToPromoteTo(Node->getOpcode(), VecVT);
3200 MVT ScalarVT = Node->getSimpleValueType(0);
3201 MVT NewScalarVT = NewVecVT.getVectorElementType();
3202
3203 SDLoc DL(Node);
3204 SmallVector<SDValue, 4> Operands(Node->getNumOperands());
3205
3206 // FIXME: Support integer.
3207 assert(Node->getOperand(0).getValueType().isFloatingPoint() &&
3208 "Only FP promotion is supported");
3209
3210 for (unsigned j = 0; j != Node->getNumOperands(); ++j)
3211 if (Node->getOperand(j).getValueType().isVector() &&
3212 !(IsVPOpcode &&
3213 ISD::getVPMaskIdx(Node->getOpcode()) == j)) { // Skip mask operand.
3214 // promote the vector operand.
3215 // FIXME: Support integer.
3216 assert(Node->getOperand(j).getValueType().isFloatingPoint() &&
3217 "Only FP promotion is supported");
3218 Operands[j] =
3219 DAG.getNode(ISD::FP_EXTEND, DL, NewVecVT, Node->getOperand(j));
3220 } else if (Node->getOperand(j).getValueType().isFloatingPoint()) {
3221 // promote the initial value.
3222 Operands[j] =
3223 DAG.getNode(ISD::FP_EXTEND, DL, NewScalarVT, Node->getOperand(j));
3224 } else {
3225 Operands[j] = Node->getOperand(j); // Skip VL operand.
3226 }
3227
3228 SDValue Res = DAG.getNode(Node->getOpcode(), DL, NewScalarVT, Operands,
3229 Node->getFlags());
3230
3231 assert(ScalarVT.isFloatingPoint() && "Only FP promotion is supported");
3232 return DAG.getNode(ISD::FP_ROUND, DL, ScalarVT, Res,
3233 DAG.getIntPtrConstant(0, DL, /*isTarget=*/true));
3234}
3235
3236bool SelectionDAGLegalize::ExpandNode(SDNode *Node) {
3237 LLVM_DEBUG(dbgs() << "Trying to expand node\n");
3239 SDLoc dl(Node);
3240 SDValue Tmp1, Tmp2, Tmp3, Tmp4;
3241 bool NeedInvert;
3242 switch (Node->getOpcode()) {
3243 case ISD::ABS:
3244 if ((Tmp1 = TLI.expandABS(Node, DAG)))
3245 Results.push_back(Tmp1);
3246 break;
3247 case ISD::ABDS:
3248 case ISD::ABDU:
3249 if ((Tmp1 = TLI.expandABD(Node, DAG)))
3250 Results.push_back(Tmp1);
3251 break;
3252 case ISD::AVGCEILS:
3253 case ISD::AVGCEILU:
3254 case ISD::AVGFLOORS:
3255 case ISD::AVGFLOORU:
3256 if ((Tmp1 = TLI.expandAVG(Node, DAG)))
3257 Results.push_back(Tmp1);
3258 break;
3259 case ISD::CTPOP:
3260 if ((Tmp1 = TLI.expandCTPOP(Node, DAG)))
3261 Results.push_back(Tmp1);
3262 break;
3263 case ISD::CTLZ:
3265 if ((Tmp1 = TLI.expandCTLZ(Node, DAG)))
3266 Results.push_back(Tmp1);
3267 break;
3268 case ISD::CTLS:
3269 if ((Tmp1 = TLI.expandCTLS(Node, DAG)))
3270 Results.push_back(Tmp1);
3271 break;
3272 case ISD::CTTZ:
3274 if ((Tmp1 = TLI.expandCTTZ(Node, DAG)))
3275 Results.push_back(Tmp1);
3276 break;
3277 case ISD::BITREVERSE:
3278 if ((Tmp1 = TLI.expandBITREVERSE(Node, DAG)))
3279 Results.push_back(Tmp1);
3280 break;
3281 case ISD::BSWAP:
3282 if ((Tmp1 = TLI.expandBSWAP(Node, DAG)))
3283 Results.push_back(Tmp1);
3284 break;
3285 case ISD::PARITY:
3286 Results.push_back(ExpandPARITY(Node->getOperand(0), dl));
3287 break;
3288 case ISD::FRAMEADDR:
3289 case ISD::RETURNADDR:
3291 Results.push_back(DAG.getConstant(0, dl, Node->getValueType(0)));
3292 break;
3293 case ISD::EH_DWARF_CFA: {
3294 SDValue CfaArg = DAG.getSExtOrTrunc(Node->getOperand(0), dl,
3295 TLI.getPointerTy(DAG.getDataLayout()));
3296 SDValue Offset = DAG.getNode(ISD::ADD, dl,
3297 CfaArg.getValueType(),
3299 CfaArg.getValueType()),
3300 CfaArg);
3301 SDValue FA = DAG.getNode(
3303 DAG.getConstant(0, dl, TLI.getPointerTy(DAG.getDataLayout())));
3304 Results.push_back(DAG.getNode(ISD::ADD, dl, FA.getValueType(),
3305 FA, Offset));
3306 break;
3307 }
3308 case ISD::GET_ROUNDING:
3309 Results.push_back(DAG.getConstant(1, dl, Node->getValueType(0)));
3310 Results.push_back(Node->getOperand(0));
3311 break;
3312 case ISD::EH_RETURN:
3313 case ISD::EH_LABEL:
3314 case ISD::PREFETCH:
3315 case ISD::VAEND:
3317 // If the target didn't expand these, there's nothing to do, so just
3318 // preserve the chain and be done.
3319 Results.push_back(Node->getOperand(0));
3320 break;
3323 // If the target didn't expand this, just return 'zero' and preserve the
3324 // chain.
3325 Results.append(Node->getNumValues() - 1,
3326 DAG.getConstant(0, dl, Node->getValueType(0)));
3327 Results.push_back(Node->getOperand(0));
3328 break;
3330 // If the target didn't expand this, just return 'zero' and preserve the
3331 // chain.
3332 Results.push_back(DAG.getConstant(0, dl, MVT::i32));
3333 Results.push_back(Node->getOperand(0));
3334 break;
3335 case ISD::ATOMIC_LOAD: {
3336 // There is no libcall for atomic load; fake it with ATOMIC_CMP_SWAP.
3337 SDValue Zero = DAG.getConstant(0, dl, Node->getValueType(0));
3338 SDVTList VTs = DAG.getVTList(Node->getValueType(0), MVT::Other);
3339 SDValue Swap = DAG.getAtomicCmpSwap(
3340 ISD::ATOMIC_CMP_SWAP, dl, cast<AtomicSDNode>(Node)->getMemoryVT(), VTs,
3341 Node->getOperand(0), Node->getOperand(1), Zero, Zero,
3342 cast<AtomicSDNode>(Node)->getMemOperand());
3343 Results.push_back(Swap.getValue(0));
3344 Results.push_back(Swap.getValue(1));
3345 break;
3346 }
3347 case ISD::ATOMIC_STORE: {
3348 // There is no libcall for atomic store; fake it with ATOMIC_SWAP.
3349 SDValue Swap = DAG.getAtomic(
3350 ISD::ATOMIC_SWAP, dl, cast<AtomicSDNode>(Node)->getMemoryVT(),
3351 Node->getOperand(0), Node->getOperand(2), Node->getOperand(1),
3352 cast<AtomicSDNode>(Node)->getMemOperand());
3353 Results.push_back(Swap.getValue(1));
3354 break;
3355 }
3357 // Expanding an ATOMIC_CMP_SWAP_WITH_SUCCESS produces an ATOMIC_CMP_SWAP and
3358 // splits out the success value as a comparison. Expanding the resulting
3359 // ATOMIC_CMP_SWAP will produce a libcall.
3360 SDVTList VTs = DAG.getVTList(Node->getValueType(0), MVT::Other);
3361 SDValue Res = DAG.getAtomicCmpSwap(
3362 ISD::ATOMIC_CMP_SWAP, dl, cast<AtomicSDNode>(Node)->getMemoryVT(), VTs,
3363 Node->getOperand(0), Node->getOperand(1), Node->getOperand(2),
3364 Node->getOperand(3), cast<MemSDNode>(Node)->getMemOperand());
3365
3366 SDValue ExtRes = Res;
3367 SDValue LHS = Res;
3368 SDValue RHS = Node->getOperand(1);
3369
3370 EVT AtomicType = cast<AtomicSDNode>(Node)->getMemoryVT();
3371 EVT OuterType = Node->getValueType(0);
3372 switch (TLI.getExtendForAtomicOps()) {
3373 case ISD::SIGN_EXTEND:
3374 LHS = DAG.getNode(ISD::AssertSext, dl, OuterType, Res,
3375 DAG.getValueType(AtomicType));
3376 RHS = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, OuterType,
3377 Node->getOperand(2), DAG.getValueType(AtomicType));
3378 ExtRes = LHS;
3379 break;
3380 case ISD::ZERO_EXTEND:
3381 LHS = DAG.getNode(ISD::AssertZext, dl, OuterType, Res,
3382 DAG.getValueType(AtomicType));
3383 RHS = DAG.getZeroExtendInReg(Node->getOperand(2), dl, AtomicType);
3384 ExtRes = LHS;
3385 break;
3386 case ISD::ANY_EXTEND:
3387 LHS = DAG.getZeroExtendInReg(Res, dl, AtomicType);
3388 RHS = DAG.getZeroExtendInReg(Node->getOperand(2), dl, AtomicType);
3389 break;
3390 default:
3391 llvm_unreachable("Invalid atomic op extension");
3392 }
3393
3395 DAG.getSetCC(dl, Node->getValueType(1), LHS, RHS, ISD::SETEQ);
3396
3397 Results.push_back(ExtRes.getValue(0));
3398 Results.push_back(Success);
3399 Results.push_back(Res.getValue(1));
3400 break;
3401 }
3402 case ISD::ATOMIC_LOAD_SUB: {
3403 SDLoc DL(Node);
3404 EVT VT = Node->getValueType(0);
3405 SDValue RHS = Node->getOperand(2);
3406 AtomicSDNode *AN = cast<AtomicSDNode>(Node);
3407 if (RHS->getOpcode() == ISD::SIGN_EXTEND_INREG &&
3408 cast<VTSDNode>(RHS->getOperand(1))->getVT() == AN->getMemoryVT())
3409 RHS = RHS->getOperand(0);
3410 SDValue NewRHS =
3411 DAG.getNode(ISD::SUB, DL, VT, DAG.getConstant(0, DL, VT), RHS);
3413 Node->getOperand(0), Node->getOperand(1),
3414 NewRHS, AN->getMemOperand());
3415 Results.push_back(Res);
3416 Results.push_back(Res.getValue(1));
3417 break;
3418 }
3420 ExpandDYNAMIC_STACKALLOC(Node, Results);
3421 break;
3422 case ISD::MERGE_VALUES:
3423 for (unsigned i = 0; i < Node->getNumValues(); i++)
3424 Results.push_back(Node->getOperand(i));
3425 break;
3426 case ISD::POISON:
3427 case ISD::UNDEF: {
3428 EVT VT = Node->getValueType(0);
3429 if (VT.isInteger())
3430 Results.push_back(DAG.getConstant(0, dl, VT));
3431 else {
3432 assert(VT.isFloatingPoint() && "Unknown value type!");
3433 Results.push_back(DAG.getConstantFP(0, dl, VT));
3434 }
3435 break;
3436 }
3438 // When strict mode is enforced we can't do expansion because it
3439 // does not honor the "strict" properties. Only libcall is allowed.
3440 if (TLI.isStrictFPEnabled())
3441 break;
3442 // We might as well mutate to FP_ROUND when FP_ROUND operation is legal
3443 // since this operation is more efficient than stack operation.
3444 if (TLI.getStrictFPOperationAction(Node->getOpcode(),
3445 Node->getValueType(0))
3446 == TargetLowering::Legal)
3447 break;
3448 // We fall back to use stack operation when the FP_ROUND operation
3449 // isn't available.
3450 if ((Tmp1 = EmitStackConvert(Node->getOperand(1), Node->getValueType(0),
3451 Node->getValueType(0), dl,
3452 Node->getOperand(0)))) {
3453 ReplaceNode(Node, Tmp1.getNode());
3454 LLVM_DEBUG(dbgs() << "Successfully expanded STRICT_FP_ROUND node\n");
3455 return true;
3456 }
3457 break;
3458 case ISD::FP_ROUND: {
3459 if ((Tmp1 = TLI.expandFP_ROUND(Node, DAG))) {
3460 Results.push_back(Tmp1);
3461 break;
3462 }
3463
3464 [[fallthrough]];
3465 }
3466 case ISD::BITCAST:
3467 if ((Tmp1 = EmitStackConvert(Node->getOperand(0), Node->getValueType(0),
3468 Node->getValueType(0), dl)))
3469 Results.push_back(Tmp1);
3470 break;
3472 // When strict mode is enforced we can't do expansion because it
3473 // does not honor the "strict" properties. Only libcall is allowed.
3474 if (TLI.isStrictFPEnabled())
3475 break;
3476 // We might as well mutate to FP_EXTEND when FP_EXTEND operation is legal
3477 // since this operation is more efficient than stack operation.
3478 if (TLI.getStrictFPOperationAction(Node->getOpcode(),
3479 Node->getValueType(0))
3480 == TargetLowering::Legal)
3481 break;
3482 // We fall back to use stack operation when the FP_EXTEND operation
3483 // isn't available.
3484 if ((Tmp1 = EmitStackConvert(
3485 Node->getOperand(1), Node->getOperand(1).getValueType(),
3486 Node->getValueType(0), dl, Node->getOperand(0)))) {
3487 ReplaceNode(Node, Tmp1.getNode());
3488 LLVM_DEBUG(dbgs() << "Successfully expanded STRICT_FP_EXTEND node\n");
3489 return true;
3490 }
3491 break;
3492 case ISD::FP_EXTEND: {
3493 SDValue Op = Node->getOperand(0);
3494 EVT SrcVT = Op.getValueType();
3495 EVT DstVT = Node->getValueType(0);
3496 if (SrcVT.getScalarType() == MVT::bf16) {
3497 Results.push_back(DAG.getNode(ISD::BF16_TO_FP, SDLoc(Node), DstVT, Op));
3498 break;
3499 }
3500
3501 if ((Tmp1 = EmitStackConvert(Op, SrcVT, DstVT, dl)))
3502 Results.push_back(Tmp1);
3503 break;
3504 }
3505 case ISD::BF16_TO_FP: {
3506 // Always expand bf16 to f32 casts, they lower to ext + shift.
3507 //
3508 // Note that the operand of this code can be bf16 or an integer type in case
3509 // bf16 is not supported on the target and was softened.
3510 SDValue Op = Node->getOperand(0);
3511 if (Op.getValueType() == MVT::bf16) {
3512 Op = DAG.getNode(ISD::ANY_EXTEND, dl, MVT::i32,
3513 DAG.getNode(ISD::BITCAST, dl, MVT::i16, Op));
3514 } else {
3515 Op = DAG.getAnyExtOrTrunc(Op, dl, MVT::i32);
3516 }
3517 Op = DAG.getNode(ISD::SHL, dl, MVT::i32, Op,
3518 DAG.getShiftAmountConstant(16, MVT::i32, dl));
3519 Op = DAG.getNode(ISD::BITCAST, dl, MVT::f32, Op);
3520 // Add fp_extend in case the output is bigger than f32.
3521 if (Node->getValueType(0) != MVT::f32)
3522 Op = DAG.getNode(ISD::FP_EXTEND, dl, Node->getValueType(0), Op);
3523 Results.push_back(Op);
3524 break;
3525 }
3526 case ISD::FP_TO_BF16: {
3527 SDValue Op = Node->getOperand(0);
3528 if (Op.getValueType() != MVT::f32)
3529 Op = DAG.getNode(ISD::FP_ROUND, dl, MVT::f32, Op,
3530 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true));
3531 // Certain SNaNs will turn into infinities if we do a simple shift right.
3532 if (!DAG.isKnownNeverSNaN(Op)) {
3533 Op = DAG.getNode(ISD::FCANONICALIZE, dl, MVT::f32, Op, Node->getFlags());
3534 }
3535 Op = DAG.getNode(ISD::SRL, dl, MVT::i32,
3536 DAG.getNode(ISD::BITCAST, dl, MVT::i32, Op),
3537 DAG.getShiftAmountConstant(16, MVT::i32, dl));
3538 // The result of this node can be bf16 or an integer type in case bf16 is
3539 // not supported on the target and was softened to i16 for storage.
3540 if (Node->getValueType(0) == MVT::bf16) {
3541 Op = DAG.getNode(ISD::BITCAST, dl, MVT::bf16,
3542 DAG.getNode(ISD::TRUNCATE, dl, MVT::i16, Op));
3543 } else {
3544 Op = DAG.getAnyExtOrTrunc(Op, dl, Node->getValueType(0));
3545 }
3546 Results.push_back(Op);
3547 break;
3548 }
3550 // Expand conversion from arbitrary FP format stored in an integer to a
3551 // native IEEE float type using integer bit manipulation.
3552 //
3553 // TODO: currently only conversions from FP4, FP6 and FP8 formats from OCP
3554 // specification are expanded. Remaining arbitrary FP types: Float8E4M3,
3555 // Float8E3M4, Float8E5M2FNUZ, Float8E4M3FNUZ, Float8E4M3B11FNUZ,
3556 // Float8E8M0FNU.
3557 EVT DstVT = Node->getValueType(0);
3558
3559 SDValue IntVal = Node->getOperand(0);
3560 const uint64_t SemEnum = Node->getConstantOperandVal(1);
3561 const auto Sem = static_cast<APFloatBase::Semantics>(SemEnum);
3562
3563 // Supported source formats.
3564 switch (Sem) {
3570 break;
3571 default:
3572 DAG.getContext()->emitError("CONVERT_FROM_ARBITRARY_FP: not implemented "
3573 "source format (semantics enum " +
3574 Twine(SemEnum) + ")");
3575 Results.push_back(DAG.getPOISON(DstVT));
3576 break;
3577 }
3578 if (!Results.empty())
3579 break;
3580
3581 const fltSemantics &SrcSem = APFloatBase::EnumToSemantics(Sem);
3582
3583 const unsigned SrcBits = APFloat::getSizeInBits(SrcSem);
3584 const unsigned SrcPrecision = APFloat::semanticsPrecision(SrcSem);
3585 const unsigned SrcMant = SrcPrecision - 1;
3586 const unsigned SrcExp = SrcBits - SrcMant - 1;
3587 const int SrcBias = 1 - APFloat::semanticsMinExponent(SrcSem);
3588
3589 const fltNonfiniteBehavior NFBehavior = SrcSem.nonFiniteBehavior;
3590
3591 // Destination format parameters.
3592 const fltSemantics &DstSem = DstVT.getFltSemantics();
3593
3594 const unsigned DstBits = APFloat::getSizeInBits(DstSem);
3595 const unsigned DstMant = APFloat::semanticsPrecision(DstSem) - 1;
3596 const unsigned DstExpBits = DstBits - DstMant - 1;
3597 const int DstMinExp = APFloat::semanticsMinExponent(DstSem);
3598 const int DstBias = 1 - DstMinExp;
3599 const uint64_t DstExpAllOnes = (1ULL << DstExpBits) - 1;
3600
3601 // Work in an integer type matching the destination float width.
3602 // Use zero-extend to preserve the raw bit-pattern.
3603 EVT IntVT = EVT::getIntegerVT(*DAG.getContext(), DstBits);
3604 SDValue Src = DAG.getZExtOrTrunc(IntVal, dl, IntVT);
3605
3606 EVT SetCCVT = getSetCCResultType(IntVT);
3607
3608 SDValue Zero = DAG.getConstant(0, dl, IntVT);
3609 SDValue One = DAG.getConstant(1, dl, IntVT);
3610
3611 // Extract bit fields.
3612 const uint64_t MantMask = (SrcMant > 0) ? ((1ULL << SrcMant) - 1) : 0;
3613 const uint64_t ExpMask = (1ULL << SrcExp) - 1;
3614
3615 SDValue MantField = DAG.getNode(ISD::AND, dl, IntVT, Src,
3616 DAG.getConstant(MantMask, dl, IntVT));
3617
3618 SDValue ExpField =
3619 DAG.getNode(ISD::AND, dl, IntVT,
3620 DAG.getNode(ISD::SRL, dl, IntVT, Src,
3621 DAG.getShiftAmountConstant(SrcMant, IntVT, dl)),
3622 DAG.getConstant(ExpMask, dl, IntVT));
3623
3624 SDValue SignBit =
3625 DAG.getNode(ISD::SRL, dl, IntVT, Src,
3626 DAG.getShiftAmountConstant(SrcBits - 1, IntVT, dl));
3627
3628 // Precompute sign shifted to MSB of destination.
3629 SDValue SignShifted =
3630 DAG.getNode(ISD::SHL, dl, IntVT, SignBit,
3631 DAG.getShiftAmountConstant(DstBits - 1, IntVT, dl));
3632
3633 // Classify the input value based on compile-time format properties.
3634 SDValue ExpAllOnes = DAG.getConstant(ExpMask, dl, IntVT);
3635 SDValue IsExpAllOnes =
3636 DAG.getSetCC(dl, SetCCVT, ExpField, ExpAllOnes, ISD::SETEQ);
3637 SDValue IsExpZero = DAG.getSetCC(dl, SetCCVT, ExpField, Zero, ISD::SETEQ);
3638 SDValue IsMantZero = DAG.getSetCC(dl, SetCCVT, MantField, Zero, ISD::SETEQ);
3639 SDValue IsMantNonZero =
3640 DAG.getSetCC(dl, SetCCVT, MantField, Zero, ISD::SETNE);
3641
3642 // NaN detection.
3643 SDValue IsNaN;
3644 if (NFBehavior == fltNonfiniteBehavior::FiniteOnly) {
3645 // FiniteOnly formats (E2M1FN, E3M2FN, E2M3FN) never produce NaN.
3646 IsNaN = DAG.getBoolConstant(false, dl, SetCCVT, IntVT);
3647 } else if (NFBehavior == fltNonfiniteBehavior::IEEE754) {
3648 // E5M2 produces NaN when exp == all-ones AND mantissa != 0.
3649 IsNaN = DAG.getNode(ISD::AND, dl, SetCCVT, IsExpAllOnes, IsMantNonZero);
3650 } else {
3651 // NanOnly + AllOnes (E4M3FN): NaN when all exp and mantissa bits are 1.
3652 assert(SrcSem.nanEncoding == fltNanEncoding::AllOnes);
3653 SDValue MantAllOnes = DAG.getConstant(MantMask, dl, IntVT);
3654 SDValue IsMantAllOnes =
3655 DAG.getSetCC(dl, SetCCVT, MantField, MantAllOnes, ISD::SETEQ);
3656 IsNaN = DAG.getNode(ISD::AND, dl, SetCCVT, IsExpAllOnes, IsMantAllOnes);
3657 }
3658
3659 // Inf detection.
3660 SDValue IsInf;
3661 if (NFBehavior == fltNonfiniteBehavior::IEEE754) {
3662 // E5M2: Inf when exp == all-ones AND mantissa == 0.
3663 IsInf = DAG.getNode(ISD::AND, dl, SetCCVT, IsExpAllOnes, IsMantZero);
3664 } else {
3665 // NanOnly and FiniteOnly formats have no Inf representation.
3666 IsInf = DAG.getBoolConstant(false, dl, SetCCVT, IntVT);
3667 }
3668
3669 // Zero detection.
3670 SDValue IsZero = DAG.getNode(ISD::AND, dl, SetCCVT, IsExpZero, IsMantZero);
3671
3672 // Denorm detection: exp == 0 AND mant != 0.
3673 SDValue IsDenorm =
3674 DAG.getNode(ISD::AND, dl, SetCCVT, IsExpZero, IsMantNonZero);
3675
3676 // Normal value conversion.
3677 // dst_exp = exp_field + (DstBias - SrcBias)
3678 // dst_mant = mant << (DstMant - SrcMant)
3679 const int BiasAdjust = DstBias - SrcBias;
3680 SDValue NormDstExp = DAG.getNode(
3681 ISD::ADD, dl, IntVT, ExpField,
3682 DAG.getConstant(APInt(DstBits, BiasAdjust, true), dl, IntVT));
3683
3684 SDValue NormDstMant;
3685 if (DstMant > SrcMant) {
3686 SDValue NormDstMantShift =
3687 DAG.getShiftAmountConstant(DstMant - SrcMant, IntVT, dl);
3688 NormDstMant =
3689 DAG.getNode(ISD::SHL, dl, IntVT, MantField, NormDstMantShift);
3690 } else {
3691 NormDstMant = MantField;
3692 }
3693
3694 // Assemble normal result.
3695 SDValue DstMantShift = DAG.getShiftAmountConstant(DstMant, IntVT, dl);
3696 SDValue NormExpShifted =
3697 DAG.getNode(ISD::SHL, dl, IntVT, NormDstExp, DstMantShift);
3698 SDValue NormResult = DAG.getNode(
3699 ISD::OR, dl, IntVT,
3700 DAG.getNode(ISD::OR, dl, IntVT, SignShifted, NormExpShifted),
3701 NormDstMant);
3702
3703 // Denormal value conversion.
3704 // For a denormal source (exp_field == 0, mant != 0), normalize by finding
3705 // the MSB position of mant using CTLZ, then compute the correct
3706 // exponent and mantissa for the destination format.
3707 SDValue DenormResult;
3708 {
3709 const unsigned IntVTBits = DstBits;
3710 SDValue LeadingZeros =
3711 DAG.getNode(ISD::CTLZ_ZERO_UNDEF, dl, IntVT, MantField);
3712
3713 // dst_exp_denorm = (IntVTBits + DstBias - SrcBias - SrcMant) -
3714 // LeadingZeros
3715 const int DenormExpConst =
3716 (int)IntVTBits + DstBias - SrcBias - (int)SrcMant;
3717 SDValue DenormDstExp = DAG.getNode(
3718 ISD::SUB, dl, IntVT,
3719 DAG.getConstant(APInt(DstBits, DenormExpConst, true), dl, IntVT),
3720 LeadingZeros);
3721
3722 // MSB position of the mantissa (0-indexed from LSB).
3723 SDValue MantMSB =
3724 DAG.getNode(ISD::SUB, dl, IntVT,
3725 DAG.getConstant(IntVTBits - 1, dl, IntVT), LeadingZeros);
3726
3727 // leading_one = 1 << MantMSB
3728 SDValue LeadingOne = DAG.getNode(ISD::SHL, dl, IntVT, One, MantMSB);
3729
3730 // frac = mant XOR leading_one (strip the implicit 1)
3731 SDValue Frac = DAG.getNode(ISD::XOR, dl, IntVT, MantField, LeadingOne);
3732
3733 // shift_amount = DstMant - MantMSB
3734 // = DstMant - (IntVTBits - 1 - LeadingZeros)
3735 // = LeadingZeros - (IntVTBits - 1 - DstMant)
3736 const unsigned ShiftSub = IntVTBits - 1 - DstMant; // always >= 0
3737 SDValue ShiftAmount = DAG.getNode(ISD::SUB, dl, IntVT, LeadingZeros,
3738 DAG.getConstant(ShiftSub, dl, IntVT));
3739
3740 SDValue DenormDstMant =
3741 DAG.getNode(ISD::SHL, dl, IntVT, Frac, ShiftAmount);
3742
3743 // Assemble denorm as sign | (denorm_dst_exp << DstMant) | denorm_dst_mant
3744 SDValue DenormExpShifted =
3745 DAG.getNode(ISD::SHL, dl, IntVT, DenormDstExp, DstMantShift);
3746 DenormResult = DAG.getNode(
3747 ISD::OR, dl, IntVT,
3748 DAG.getNode(ISD::OR, dl, IntVT, SignShifted, DenormExpShifted),
3749 DenormDstMant);
3750 }
3751
3752 // Select between normal and denorm paths.
3753 SDValue FiniteResult =
3754 DAG.getSelect(dl, IntVT, IsDenorm, DenormResult, NormResult);
3755
3756 // Build special-value results.
3757 // NaN -> canonical quiet NaN: sign=0, exp=all-ones, qNaN bit set.
3758 // Encoding: (DstExpAllOnes << DstMant) | (1 << (DstMant - 1))
3759 const uint64_t QNaNBit = (DstMant > 0) ? (1ULL << (DstMant - 1)) : 0;
3760 SDValue NaNResult =
3761 DAG.getConstant((DstExpAllOnes << DstMant) | QNaNBit, dl, IntVT);
3762
3763 // Inf -> destination Inf.
3764 // sign | (DstExpAllOnes << DstMant)
3765 SDValue InfResult =
3766 DAG.getNode(ISD::OR, dl, IntVT, SignShifted,
3767 DAG.getConstant(DstExpAllOnes << DstMant, dl, IntVT));
3768
3769 // Zero -> signed zero.
3770 // Sign bit only.
3771 SDValue ZeroResult = SignShifted;
3772
3773 // Final selection goes in order: NaN takes priority, then Inf, then Zero.
3774 SDValue Result = FiniteResult;
3775 Result = DAG.getSelect(dl, IntVT, IsZero, ZeroResult, Result);
3776 Result = DAG.getSelect(dl, IntVT, IsInf, InfResult, Result);
3777 Result = DAG.getSelect(dl, IntVT, IsNaN, NaNResult, Result);
3778
3779 // Bitcast integer result to destination float type.
3780 Result = DAG.getNode(ISD::BITCAST, dl, DstVT, Result);
3781
3782 Results.push_back(Result);
3783 break;
3784 }
3785 case ISD::FCANONICALIZE: {
3786 // This implements llvm.canonicalize.f* by multiplication with 1.0, as
3787 // suggested in
3788 // https://llvm.org/docs/LangRef.html#llvm-canonicalize-intrinsic.
3789 // It uses strict_fp operations even outside a strict_fp context in order
3790 // to guarantee that the canonicalization is not optimized away by later
3791 // passes. The result chain introduced by that is intentionally ignored
3792 // since no ordering requirement is intended here.
3793
3794 // Create strict multiplication by 1.0.
3795 SDValue Operand = Node->getOperand(0);
3796 EVT VT = Operand.getValueType();
3797 SDValue One = DAG.getConstantFP(1.0, dl, VT);
3798 SDValue Chain = DAG.getEntryNode();
3799 // Propagate existing flags on canonicalize, and additionally set
3800 // NoFPExcept.
3801 SDNodeFlags CanonicalizeFlags = Node->getFlags();
3802 CanonicalizeFlags.setNoFPExcept(true);
3803 SDValue Mul = DAG.getNode(ISD::STRICT_FMUL, dl, {VT, MVT::Other},
3804 {Chain, Operand, One}, CanonicalizeFlags);
3805
3806 Results.push_back(Mul);
3807 break;
3808 }
3810 EVT ExtraVT = cast<VTSDNode>(Node->getOperand(1))->getVT();
3811 EVT VT = Node->getValueType(0);
3812
3813 // An in-register sign-extend of a boolean is a negation:
3814 // 'true' (1) sign-extended is -1.
3815 // 'false' (0) sign-extended is 0.
3816 // However, we must mask the high bits of the source operand because the
3817 // SIGN_EXTEND_INREG does not guarantee that the high bits are already zero.
3818
3819 // TODO: Do this for vectors too?
3820 if (ExtraVT.isScalarInteger() && ExtraVT.getSizeInBits() == 1) {
3821 SDValue One = DAG.getConstant(1, dl, VT);
3822 SDValue And = DAG.getNode(ISD::AND, dl, VT, Node->getOperand(0), One);
3823 SDValue Zero = DAG.getConstant(0, dl, VT);
3824 SDValue Neg = DAG.getNode(ISD::SUB, dl, VT, Zero, And);
3825 Results.push_back(Neg);
3826 break;
3827 }
3828
3829 // NOTE: we could fall back on load/store here too for targets without
3830 // SRA. However, it is doubtful that any exist.
3831 unsigned BitsDiff = VT.getScalarSizeInBits() -
3832 ExtraVT.getScalarSizeInBits();
3833 SDValue ShiftCst = DAG.getShiftAmountConstant(BitsDiff, VT, dl);
3834 Tmp1 = DAG.getNode(ISD::SHL, dl, VT, Node->getOperand(0), ShiftCst);
3835 Tmp1 = DAG.getNode(ISD::SRA, dl, VT, Tmp1, ShiftCst);
3836 Results.push_back(Tmp1);
3837 break;
3838 }
3839 case ISD::UINT_TO_FP:
3841 if (TLI.expandUINT_TO_FP(Node, Tmp1, Tmp2, DAG)) {
3842 Results.push_back(Tmp1);
3843 if (Node->isStrictFPOpcode())
3844 Results.push_back(Tmp2);
3845 break;
3846 }
3847 [[fallthrough]];
3848 case ISD::SINT_TO_FP:
3850 if ((Tmp1 = ExpandLegalINT_TO_FP(Node, Tmp2))) {
3851 Results.push_back(Tmp1);
3852 if (Node->isStrictFPOpcode())
3853 Results.push_back(Tmp2);
3854 }
3855 break;
3856 case ISD::FP_TO_SINT:
3857 if (TLI.expandFP_TO_SINT(Node, Tmp1, DAG))
3858 Results.push_back(Tmp1);
3859 break;
3861 if (TLI.expandFP_TO_SINT(Node, Tmp1, DAG)) {
3862 ReplaceNode(Node, Tmp1.getNode());
3863 LLVM_DEBUG(dbgs() << "Successfully expanded STRICT_FP_TO_SINT node\n");
3864 return true;
3865 }
3866 break;
3867 case ISD::FP_TO_UINT:
3868 if (TLI.expandFP_TO_UINT(Node, Tmp1, Tmp2, DAG))
3869 Results.push_back(Tmp1);
3870 break;
3872 if (TLI.expandFP_TO_UINT(Node, Tmp1, Tmp2, DAG)) {
3873 // Relink the chain.
3874 DAG.ReplaceAllUsesOfValueWith(SDValue(Node,1), Tmp2);
3875 // Replace the new UINT result.
3876 ReplaceNodeWithValue(SDValue(Node, 0), Tmp1);
3877 LLVM_DEBUG(dbgs() << "Successfully expanded STRICT_FP_TO_UINT node\n");
3878 return true;
3879 }
3880 break;
3883 Results.push_back(TLI.expandFP_TO_INT_SAT(Node, DAG));
3884 break;
3885 case ISD::LROUND:
3886 case ISD::LLROUND: {
3887 SDValue Arg = Node->getOperand(0);
3888 EVT ArgVT = Arg.getValueType();
3889 EVT ResVT = Node->getValueType(0);
3890 SDLoc dl(Node);
3891 SDValue RoundNode = DAG.getNode(ISD::FROUND, dl, ArgVT, Arg);
3892 Results.push_back(DAG.getNode(ISD::FP_TO_SINT, dl, ResVT, RoundNode));
3893 break;
3894 }
3895 case ISD::VAARG:
3896 Results.push_back(DAG.expandVAArg(Node));
3897 Results.push_back(Results[0].getValue(1));
3898 break;
3899 case ISD::VACOPY:
3900 Results.push_back(DAG.expandVACopy(Node));
3901 break;
3903 if (Node->getOperand(0).getValueType().getVectorElementCount().isScalar())
3904 // This must be an access of the only element. Return it.
3905 Tmp1 = DAG.getNode(ISD::BITCAST, dl, Node->getValueType(0),
3906 Node->getOperand(0));
3907 else
3908 Tmp1 = ExpandExtractFromVectorThroughStack(SDValue(Node, 0));
3909 Results.push_back(Tmp1);
3910 break;
3912 Results.push_back(ExpandExtractFromVectorThroughStack(SDValue(Node, 0)));
3913 break;
3915 Results.push_back(ExpandInsertToVectorThroughStack(SDValue(Node, 0)));
3916 break;
3918 if (EVT VectorValueType = Node->getOperand(0).getValueType();
3919 VectorValueType.isScalableVector() ||
3920 TLI.isOperationExpand(ISD::EXTRACT_VECTOR_ELT, VectorValueType))
3921 Results.push_back(ExpandVectorBuildThroughStack(Node));
3922 else
3923 Results.push_back(ExpandConcatVectors(Node));
3924 break;
3926 Results.push_back(ExpandSCALAR_TO_VECTOR(Node));
3927 break;
3929 Results.push_back(ExpandINSERT_VECTOR_ELT(SDValue(Node, 0)));
3930 break;
3931 case ISD::VECTOR_SHUFFLE: {
3932 SmallVector<int, 32> NewMask;
3933 ArrayRef<int> Mask = cast<ShuffleVectorSDNode>(Node)->getMask();
3934
3935 EVT VT = Node->getValueType(0);
3936 EVT EltVT = VT.getVectorElementType();
3937 SDValue Op0 = Node->getOperand(0);
3938 SDValue Op1 = Node->getOperand(1);
3939 if (!TLI.isTypeLegal(EltVT)) {
3940 EVT NewEltVT = TLI.getTypeToTransformTo(*DAG.getContext(), EltVT);
3941
3942 // BUILD_VECTOR operands are allowed to be wider than the element type.
3943 // But if NewEltVT is smaller that EltVT the BUILD_VECTOR does not accept
3944 // it.
3945 if (NewEltVT.bitsLT(EltVT)) {
3946 // Convert shuffle node.
3947 // If original node was v4i64 and the new EltVT is i32,
3948 // cast operands to v8i32 and re-build the mask.
3949
3950 // Calculate new VT, the size of the new VT should be equal to original.
3951 EVT NewVT =
3952 EVT::getVectorVT(*DAG.getContext(), NewEltVT,
3953 VT.getSizeInBits() / NewEltVT.getSizeInBits());
3954 assert(NewVT.bitsEq(VT));
3955
3956 // cast operands to new VT
3957 Op0 = DAG.getNode(ISD::BITCAST, dl, NewVT, Op0);
3958 Op1 = DAG.getNode(ISD::BITCAST, dl, NewVT, Op1);
3959
3960 // Convert the shuffle mask
3961 unsigned int factor =
3963
3964 // EltVT gets smaller
3965 assert(factor > 0);
3966
3967 for (unsigned i = 0; i < VT.getVectorNumElements(); ++i) {
3968 if (Mask[i] < 0) {
3969 for (unsigned fi = 0; fi < factor; ++fi)
3970 NewMask.push_back(Mask[i]);
3971 }
3972 else {
3973 for (unsigned fi = 0; fi < factor; ++fi)
3974 NewMask.push_back(Mask[i]*factor+fi);
3975 }
3976 }
3977 Mask = NewMask;
3978 VT = NewVT;
3979 }
3980 EltVT = NewEltVT;
3981 }
3982 unsigned NumElems = VT.getVectorNumElements();
3984 for (unsigned i = 0; i != NumElems; ++i) {
3985 if (Mask[i] < 0) {
3986 Ops.push_back(DAG.getUNDEF(EltVT));
3987 continue;
3988 }
3989 unsigned Idx = Mask[i];
3990 if (Idx < NumElems)
3991 Ops.push_back(DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, EltVT, Op0,
3992 DAG.getVectorIdxConstant(Idx, dl)));
3993 else
3994 Ops.push_back(
3995 DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, EltVT, Op1,
3996 DAG.getVectorIdxConstant(Idx - NumElems, dl)));
3997 }
3998
3999 Tmp1 = DAG.getBuildVector(VT, dl, Ops);
4000 // We may have changed the BUILD_VECTOR type. Cast it back to the Node type.
4001 Tmp1 = DAG.getNode(ISD::BITCAST, dl, Node->getValueType(0), Tmp1);
4002 Results.push_back(Tmp1);
4003 break;
4004 }
4007 Results.push_back(TLI.expandVectorSplice(Node, DAG));
4008 break;
4009 }
4011 unsigned Factor = Node->getNumOperands();
4012 if (Factor <= 2 || !isPowerOf2_32(Factor))
4013 break;
4015 EVT VecVT = Node->getValueType(0);
4016 SmallVector<EVT> HalfVTs(Factor / 2, VecVT);
4017 // Deinterleave at Factor/2 so each result contains two factors interleaved:
4018 // a0b0 c0d0 a1b1 c1d1 -> [a0c0 b0d0] [a1c1 b1d1]
4019 SDValue L = DAG.getNode(ISD::VECTOR_DEINTERLEAVE, dl, HalfVTs,
4020 ArrayRef(Ops).take_front(Factor / 2));
4021 SDValue R = DAG.getNode(ISD::VECTOR_DEINTERLEAVE, dl, HalfVTs,
4022 ArrayRef(Ops).take_back(Factor / 2));
4023 Results.resize(Factor);
4024 // Deinterleave the 2 factors out:
4025 // [a0c0 a1c1] [b0d0 b1d1] -> a0a1 b0b1 c0c1 d0d1
4026 for (unsigned I = 0; I < Factor / 2; I++) {
4028 DAG.getNode(ISD::VECTOR_DEINTERLEAVE, dl, {VecVT, VecVT},
4029 {L.getValue(I), R.getValue(I)});
4030 Results[I] = Deinterleave.getValue(0);
4031 Results[I + Factor / 2] = Deinterleave.getValue(1);
4032 }
4033 break;
4034 }
4036 unsigned Factor = Node->getNumOperands();
4037 if (Factor <= 2 || !isPowerOf2_32(Factor))
4038 break;
4039 EVT VecVT = Node->getValueType(0);
4040 SmallVector<EVT> HalfVTs(Factor / 2, VecVT);
4041 SmallVector<SDValue, 8> LOps, ROps;
4042 // Interleave so we have 2 factors per result:
4043 // a0a1 b0b1 c0c1 d0d1 -> [a0c0 b0d0] [a1c1 b1d1]
4044 for (unsigned I = 0; I < Factor / 2; I++) {
4045 SDValue Interleave =
4046 DAG.getNode(ISD::VECTOR_INTERLEAVE, dl, {VecVT, VecVT},
4047 {Node->getOperand(I), Node->getOperand(I + Factor / 2)});
4048 LOps.push_back(Interleave.getValue(0));
4049 ROps.push_back(Interleave.getValue(1));
4050 }
4051 // Interleave at Factor/2:
4052 // [a0c0 b0d0] [a1c1 b1d1] -> a0b0 c0d0 a1b1 c1d1
4053 SDValue L = DAG.getNode(ISD::VECTOR_INTERLEAVE, dl, HalfVTs, LOps);
4054 SDValue R = DAG.getNode(ISD::VECTOR_INTERLEAVE, dl, HalfVTs, ROps);
4055 for (unsigned I = 0; I < Factor / 2; I++)
4056 Results.push_back(L.getValue(I));
4057 for (unsigned I = 0; I < Factor / 2; I++)
4058 Results.push_back(R.getValue(I));
4059 break;
4060 }
4061 case ISD::EXTRACT_ELEMENT: {
4062 EVT OpTy = Node->getOperand(0).getValueType();
4063 if (Node->getConstantOperandVal(1)) {
4064 // 1 -> Hi
4065 Tmp1 = DAG.getNode(
4066 ISD::SRL, dl, OpTy, Node->getOperand(0),
4067 DAG.getShiftAmountConstant(OpTy.getSizeInBits() / 2, OpTy, dl));
4068 Tmp1 = DAG.getNode(ISD::TRUNCATE, dl, Node->getValueType(0), Tmp1);
4069 } else {
4070 // 0 -> Lo
4071 Tmp1 = DAG.getNode(ISD::TRUNCATE, dl, Node->getValueType(0),
4072 Node->getOperand(0));
4073 }
4074 Results.push_back(Tmp1);
4075 break;
4076 }
4077 case ISD::STACKADDRESS:
4078 case ISD::STACKSAVE:
4079 // Expand to CopyFromReg if the target set
4080 // StackPointerRegisterToSaveRestore.
4082 Results.push_back(DAG.getCopyFromReg(Node->getOperand(0), dl, SP,
4083 Node->getValueType(0)));
4084 Results.push_back(Results[0].getValue(1));
4085 } else {
4086 Results.push_back(DAG.getUNDEF(Node->getValueType(0)));
4087 Results.push_back(Node->getOperand(0));
4088
4089 StringRef IntrinsicName = Node->getOpcode() == ISD::STACKADDRESS
4090 ? "llvm.stackaddress"
4091 : "llvm.stacksave";
4092 DAG.getContext()->diagnose(DiagnosticInfoLegalizationFailure(
4093 Twine(IntrinsicName) + " is not supported on this target.",
4095 }
4096 break;
4097 case ISD::STACKRESTORE:
4098 // Expand to CopyToReg if the target set
4099 // StackPointerRegisterToSaveRestore.
4101 Results.push_back(DAG.getCopyToReg(Node->getOperand(0), dl, SP,
4102 Node->getOperand(1)));
4103 } else {
4104 Results.push_back(Node->getOperand(0));
4105 }
4106 break;
4108 Results.push_back(DAG.getConstant(0, dl, Node->getValueType(0)));
4109 Results.push_back(Results[0].getValue(0));
4110 break;
4111 case ISD::FCOPYSIGN:
4112 Results.push_back(ExpandFCOPYSIGN(Node));
4113 break;
4114 case ISD::FNEG:
4115 Results.push_back(ExpandFNEG(Node));
4116 break;
4117 case ISD::FABS:
4118 Results.push_back(ExpandFABS(Node));
4119 break;
4120 case ISD::IS_FPCLASS: {
4121 auto Test = static_cast<FPClassTest>(Node->getConstantOperandVal(1));
4122 if (SDValue Expanded =
4123 TLI.expandIS_FPCLASS(Node->getValueType(0), Node->getOperand(0),
4124 Test, Node->getFlags(), SDLoc(Node), DAG))
4125 Results.push_back(Expanded);
4126 break;
4127 }
4128 case ISD::SMIN:
4129 case ISD::SMAX:
4130 case ISD::UMIN:
4131 case ISD::UMAX: {
4132 // Expand Y = MAX(A, B) -> Y = (A > B) ? A : B
4133 ISD::CondCode Pred;
4134 switch (Node->getOpcode()) {
4135 default: llvm_unreachable("How did we get here?");
4136 case ISD::SMAX: Pred = ISD::SETGT; break;
4137 case ISD::SMIN: Pred = ISD::SETLT; break;
4138 case ISD::UMAX: Pred = ISD::SETUGT; break;
4139 case ISD::UMIN: Pred = ISD::SETULT; break;
4140 }
4141 Tmp1 = Node->getOperand(0);
4142 Tmp2 = Node->getOperand(1);
4143 Tmp1 = DAG.getSelectCC(dl, Tmp1, Tmp2, Tmp1, Tmp2, Pred);
4144 Results.push_back(Tmp1);
4145 break;
4146 }
4147 case ISD::FMINNUM:
4148 case ISD::FMAXNUM: {
4149 if (SDValue Expanded = TLI.expandFMINNUM_FMAXNUM(Node, DAG))
4150 Results.push_back(Expanded);
4151 break;
4152 }
4153 case ISD::FMINIMUM:
4154 case ISD::FMAXIMUM: {
4155 if (SDValue Expanded = TLI.expandFMINIMUM_FMAXIMUM(Node, DAG))
4156 Results.push_back(Expanded);
4157 break;
4158 }
4159 case ISD::FMINIMUMNUM:
4160 case ISD::FMAXIMUMNUM: {
4161 Results.push_back(TLI.expandFMINIMUMNUM_FMAXIMUMNUM(Node, DAG));
4162 break;
4163 }
4164 case ISD::FSIN:
4165 case ISD::FCOS: {
4166 EVT VT = Node->getValueType(0);
4167 // Turn fsin / fcos into ISD::FSINCOS node if there are a pair of fsin /
4168 // fcos which share the same operand and both are used.
4169 if ((TLI.isOperationLegal(ISD::FSINCOS, VT) ||
4170 isSinCosLibcallAvailable(Node, DAG.getLibcalls())) &&
4171 useSinCos(Node)) {
4172 SDVTList VTs = DAG.getVTList(VT, VT);
4173 Tmp1 = DAG.getNode(ISD::FSINCOS, dl, VTs, Node->getOperand(0));
4174 if (Node->getOpcode() == ISD::FCOS)
4175 Tmp1 = Tmp1.getValue(1);
4176 Results.push_back(Tmp1);
4177 }
4178 break;
4179 }
4180 case ISD::FLDEXP:
4181 case ISD::STRICT_FLDEXP: {
4182 EVT VT = Node->getValueType(0);
4183 RTLIB::Libcall LC = RTLIB::getLDEXP(VT);
4184 // Use the LibCall instead, it is very likely faster
4185 // FIXME: Use separate LibCall action.
4186 if (DAG.getLibcalls().getLibcallImpl(LC) != RTLIB::Unsupported)
4187 break;
4188
4189 if (SDValue Expanded = expandLdexp(Node)) {
4190 Results.push_back(Expanded);
4191 if (Node->getOpcode() == ISD::STRICT_FLDEXP)
4192 Results.push_back(Expanded.getValue(1));
4193 }
4194
4195 break;
4196 }
4197 case ISD::FFREXP: {
4198 RTLIB::Libcall LC = RTLIB::getFREXP(Node->getValueType(0));
4199 // Use the LibCall instead, it is very likely faster
4200 // FIXME: Use separate LibCall action.
4201 if (DAG.getLibcalls().getLibcallImpl(LC) != RTLIB::Unsupported)
4202 break;
4203
4204 if (SDValue Expanded = expandFrexp(Node)) {
4205 Results.push_back(Expanded);
4206 Results.push_back(Expanded.getValue(1));
4207 }
4208 break;
4209 }
4210 case ISD::FMODF: {
4211 RTLIB::Libcall LC = RTLIB::getMODF(Node->getValueType(0));
4212 // Use the LibCall instead, it is very likely faster
4213 // FIXME: Use separate LibCall action.
4214 if (DAG.getLibcalls().getLibcallImpl(LC) != RTLIB::Unsupported)
4215 break;
4216
4217 if (SDValue Expanded = expandModf(Node)) {
4218 Results.push_back(Expanded);
4219 Results.push_back(Expanded.getValue(1));
4220 }
4221 break;
4222 }
4223 case ISD::FSINCOS: {
4224 if (isSinCosLibcallAvailable(Node, DAG.getLibcalls()))
4225 break;
4226 EVT VT = Node->getValueType(0);
4227 SDValue Op = Node->getOperand(0);
4228 SDNodeFlags Flags = Node->getFlags();
4229 Tmp1 = DAG.getNode(ISD::FSIN, dl, VT, Op, Flags);
4230 Tmp2 = DAG.getNode(ISD::FCOS, dl, VT, Op, Flags);
4231 Results.append({Tmp1, Tmp2});
4232 break;
4233 }
4234 case ISD::FMAD:
4235 llvm_unreachable("Illegal fmad should never be formed");
4236
4237 case ISD::FP16_TO_FP:
4238 if (Node->getValueType(0) != MVT::f32) {
4239 // We can extend to types bigger than f32 in two steps without changing
4240 // the result. Since "f16 -> f32" is much more commonly available, give
4241 // CodeGen the option of emitting that before resorting to a libcall.
4242 SDValue Res =
4243 DAG.getNode(ISD::FP16_TO_FP, dl, MVT::f32, Node->getOperand(0));
4244 Results.push_back(
4245 DAG.getNode(ISD::FP_EXTEND, dl, Node->getValueType(0), Res));
4246 }
4247 break;
4250 if (Node->getValueType(0) != MVT::f32) {
4251 // We can extend to types bigger than f32 in two steps without changing
4252 // the result. Since "f16 -> f32" is much more commonly available, give
4253 // CodeGen the option of emitting that before resorting to a libcall.
4254 SDValue Res = DAG.getNode(Node->getOpcode(), dl, {MVT::f32, MVT::Other},
4255 {Node->getOperand(0), Node->getOperand(1)});
4256 Res = DAG.getNode(ISD::STRICT_FP_EXTEND, dl,
4257 {Node->getValueType(0), MVT::Other},
4258 {Res.getValue(1), Res});
4259 Results.push_back(Res);
4260 Results.push_back(Res.getValue(1));
4261 }
4262 break;
4263 case ISD::FP_TO_FP16:
4264 LLVM_DEBUG(dbgs() << "Legalizing FP_TO_FP16\n");
4265 if (Node->getFlags().hasApproximateFuncs() && !TLI.useSoftFloat()) {
4266 SDValue Op = Node->getOperand(0);
4267 MVT SVT = Op.getSimpleValueType();
4268 if ((SVT == MVT::f64 || SVT == MVT::f80) &&
4270 // Under fastmath, we can expand this node into a fround followed by
4271 // a float-half conversion.
4272 SDValue FloatVal =
4273 DAG.getNode(ISD::FP_ROUND, dl, MVT::f32, Op,
4274 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true));
4275 Results.push_back(
4276 DAG.getNode(ISD::FP_TO_FP16, dl, Node->getValueType(0), FloatVal));
4277 }
4278 }
4279 break;
4280 case ISD::ConstantFP: {
4281 ConstantFPSDNode *CFP = cast<ConstantFPSDNode>(Node);
4282 // Check to see if this FP immediate is already legal.
4283 // If this is a legal constant, turn it into a TargetConstantFP node.
4284 if (!TLI.isFPImmLegal(CFP->getValueAPF(), Node->getValueType(0),
4285 DAG.shouldOptForSize()))
4286 Results.push_back(ExpandConstantFP(CFP, true));
4287 break;
4288 }
4289 case ISD::Constant: {
4290 ConstantSDNode *CP = cast<ConstantSDNode>(Node);
4291 Results.push_back(ExpandConstant(CP));
4292 break;
4293 }
4294 case ISD::FSUB: {
4295 EVT VT = Node->getValueType(0);
4296 if (TLI.isOperationLegalOrCustom(ISD::FADD, VT) &&
4298 const SDNodeFlags Flags = Node->getFlags();
4299 Tmp1 = DAG.getNode(ISD::FNEG, dl, VT, Node->getOperand(1));
4300 Tmp1 = DAG.getNode(ISD::FADD, dl, VT, Node->getOperand(0), Tmp1, Flags);
4301 Results.push_back(Tmp1);
4302 }
4303 break;
4304 }
4305 case ISD::SUB: {
4306 EVT VT = Node->getValueType(0);
4309 "Don't know how to expand this subtraction!");
4310 Tmp1 = DAG.getNOT(dl, Node->getOperand(1), VT);
4311 Tmp1 = DAG.getNode(ISD::ADD, dl, VT, Tmp1, DAG.getConstant(1, dl, VT));
4312 Results.push_back(DAG.getNode(ISD::ADD, dl, VT, Node->getOperand(0), Tmp1));
4313 break;
4314 }
4315 case ISD::UREM:
4316 case ISD::SREM:
4317 if (TLI.expandREM(Node, Tmp1, DAG))
4318 Results.push_back(Tmp1);
4319 break;
4320 case ISD::UDIV:
4321 case ISD::SDIV: {
4322 bool isSigned = Node->getOpcode() == ISD::SDIV;
4323 unsigned DivRemOpc = isSigned ? ISD::SDIVREM : ISD::UDIVREM;
4324 EVT VT = Node->getValueType(0);
4325 if (TLI.isOperationLegalOrCustom(DivRemOpc, VT)) {
4326 SDVTList VTs = DAG.getVTList(VT, VT);
4327 Tmp1 = DAG.getNode(DivRemOpc, dl, VTs, Node->getOperand(0),
4328 Node->getOperand(1));
4329 Results.push_back(Tmp1);
4330 }
4331 break;
4332 }
4333 case ISD::MULHU:
4334 case ISD::MULHS: {
4335 unsigned ExpandOpcode =
4336 Node->getOpcode() == ISD::MULHU ? ISD::UMUL_LOHI : ISD::SMUL_LOHI;
4337 EVT VT = Node->getValueType(0);
4338 SDVTList VTs = DAG.getVTList(VT, VT);
4339
4340 Tmp1 = DAG.getNode(ExpandOpcode, dl, VTs, Node->getOperand(0),
4341 Node->getOperand(1));
4342 Results.push_back(Tmp1.getValue(1));
4343 break;
4344 }
4345 case ISD::UMUL_LOHI:
4346 case ISD::SMUL_LOHI: {
4347 SDValue LHS = Node->getOperand(0);
4348 SDValue RHS = Node->getOperand(1);
4349 EVT VT = LHS.getValueType();
4350 unsigned MULHOpcode =
4351 Node->getOpcode() == ISD::UMUL_LOHI ? ISD::MULHU : ISD::MULHS;
4352
4353 if (TLI.isOperationLegalOrCustom(MULHOpcode, VT)) {
4354 Results.push_back(DAG.getNode(ISD::MUL, dl, VT, LHS, RHS));
4355 Results.push_back(DAG.getNode(MULHOpcode, dl, VT, LHS, RHS));
4356 break;
4357 }
4358
4360 EVT HalfType = VT.getHalfSizedIntegerVT(*DAG.getContext());
4361 assert(TLI.isTypeLegal(HalfType));
4362 if (TLI.expandMUL_LOHI(Node->getOpcode(), VT, dl, LHS, RHS, Halves,
4363 HalfType, DAG,
4364 TargetLowering::MulExpansionKind::Always)) {
4365 for (unsigned i = 0; i < 2; ++i) {
4366 SDValue Lo = DAG.getNode(ISD::ZERO_EXTEND, dl, VT, Halves[2 * i]);
4367 SDValue Hi = DAG.getNode(ISD::ANY_EXTEND, dl, VT, Halves[2 * i + 1]);
4368 SDValue Shift =
4369 DAG.getShiftAmountConstant(HalfType.getScalarSizeInBits(), VT, dl);
4370 Hi = DAG.getNode(ISD::SHL, dl, VT, Hi, Shift);
4371 Results.push_back(DAG.getNode(ISD::OR, dl, VT, Lo, Hi));
4372 }
4373 break;
4374 }
4375 break;
4376 }
4377 case ISD::MUL: {
4378 EVT VT = Node->getValueType(0);
4379 SDVTList VTs = DAG.getVTList(VT, VT);
4380 // See if multiply or divide can be lowered using two-result operations.
4381 // We just need the low half of the multiply; try both the signed
4382 // and unsigned forms. If the target supports both SMUL_LOHI and
4383 // UMUL_LOHI, form a preference by checking which forms of plain
4384 // MULH it supports.
4385 bool HasSMUL_LOHI = TLI.isOperationLegalOrCustom(ISD::SMUL_LOHI, VT);
4386 bool HasUMUL_LOHI = TLI.isOperationLegalOrCustom(ISD::UMUL_LOHI, VT);
4387 bool HasMULHS = TLI.isOperationLegalOrCustom(ISD::MULHS, VT);
4388 bool HasMULHU = TLI.isOperationLegalOrCustom(ISD::MULHU, VT);
4389 unsigned OpToUse = 0;
4390 if (HasSMUL_LOHI && !HasMULHS) {
4391 OpToUse = ISD::SMUL_LOHI;
4392 } else if (HasUMUL_LOHI && !HasMULHU) {
4393 OpToUse = ISD::UMUL_LOHI;
4394 } else if (HasSMUL_LOHI) {
4395 OpToUse = ISD::SMUL_LOHI;
4396 } else if (HasUMUL_LOHI) {
4397 OpToUse = ISD::UMUL_LOHI;
4398 }
4399 if (OpToUse) {
4400 Results.push_back(DAG.getNode(OpToUse, dl, VTs, Node->getOperand(0),
4401 Node->getOperand(1)));
4402 break;
4403 }
4404
4405 SDValue Lo, Hi;
4406 EVT HalfType = VT.getHalfSizedIntegerVT(*DAG.getContext());
4411 TLI.expandMUL(Node, Lo, Hi, HalfType, DAG,
4412 TargetLowering::MulExpansionKind::OnlyLegalOrCustom)) {
4413 Lo = DAG.getNode(ISD::ZERO_EXTEND, dl, VT, Lo);
4414 Hi = DAG.getNode(ISD::ANY_EXTEND, dl, VT, Hi);
4415 SDValue Shift =
4416 DAG.getShiftAmountConstant(HalfType.getSizeInBits(), VT, dl);
4417 Hi = DAG.getNode(ISD::SHL, dl, VT, Hi, Shift);
4418 Results.push_back(DAG.getNode(ISD::OR, dl, VT, Lo, Hi));
4419 }
4420 break;
4421 }
4422 case ISD::FSHL:
4423 case ISD::FSHR:
4424 if (SDValue Expanded = TLI.expandFunnelShift(Node, DAG))
4425 Results.push_back(Expanded);
4426 break;
4427 case ISD::ROTL:
4428 case ISD::ROTR:
4429 if (SDValue Expanded = TLI.expandROT(Node, true /*AllowVectorOps*/, DAG))
4430 Results.push_back(Expanded);
4431 break;
4432 case ISD::CLMUL:
4433 case ISD::CLMULR:
4434 case ISD::CLMULH:
4435 if (SDValue Expanded = TLI.expandCLMUL(Node, DAG))
4436 Results.push_back(Expanded);
4437 break;
4438 case ISD::SADDSAT:
4439 case ISD::UADDSAT:
4440 case ISD::SSUBSAT:
4441 case ISD::USUBSAT:
4442 Results.push_back(TLI.expandAddSubSat(Node, DAG));
4443 break;
4444 case ISD::SCMP:
4445 case ISD::UCMP:
4446 Results.push_back(TLI.expandCMP(Node, DAG));
4447 break;
4448 case ISD::SSHLSAT:
4449 case ISD::USHLSAT:
4450 Results.push_back(TLI.expandShlSat(Node, DAG));
4451 break;
4452 case ISD::SMULFIX:
4453 case ISD::SMULFIXSAT:
4454 case ISD::UMULFIX:
4455 case ISD::UMULFIXSAT:
4456 Results.push_back(TLI.expandFixedPointMul(Node, DAG));
4457 break;
4458 case ISD::SDIVFIX:
4459 case ISD::SDIVFIXSAT:
4460 case ISD::UDIVFIX:
4461 case ISD::UDIVFIXSAT:
4462 if (SDValue V = TLI.expandFixedPointDiv(Node->getOpcode(), SDLoc(Node),
4463 Node->getOperand(0),
4464 Node->getOperand(1),
4465 Node->getConstantOperandVal(2),
4466 DAG)) {
4467 Results.push_back(V);
4468 break;
4469 }
4470 // FIXME: We might want to retry here with a wider type if we fail, if that
4471 // type is legal.
4472 // FIXME: Technically, so long as we only have sdivfixes where BW+Scale is
4473 // <= 128 (which is the case for all of the default Embedded-C types),
4474 // we will only get here with types and scales that we could always expand
4475 // if we were allowed to generate libcalls to division functions of illegal
4476 // type. But we cannot do that.
4477 llvm_unreachable("Cannot expand DIVFIX!");
4478 case ISD::UADDO_CARRY:
4479 case ISD::USUBO_CARRY: {
4480 SDValue LHS = Node->getOperand(0);
4481 SDValue RHS = Node->getOperand(1);
4482 SDValue Carry = Node->getOperand(2);
4483
4484 bool IsAdd = Node->getOpcode() == ISD::UADDO_CARRY;
4485
4486 // Initial add of the 2 operands.
4487 unsigned Op = IsAdd ? ISD::ADD : ISD::SUB;
4488 EVT VT = LHS.getValueType();
4489 SDValue Sum = DAG.getNode(Op, dl, VT, LHS, RHS);
4490
4491 // Initial check for overflow.
4492 EVT CarryType = Node->getValueType(1);
4493 EVT SetCCType = getSetCCResultType(Node->getValueType(0));
4494 ISD::CondCode CC = IsAdd ? ISD::SETULT : ISD::SETUGT;
4495 SDValue Overflow = DAG.getSetCC(dl, SetCCType, Sum, LHS, CC);
4496
4497 // Add of the sum and the carry.
4498 SDValue One = DAG.getConstant(1, dl, VT);
4499 SDValue CarryExt =
4500 DAG.getNode(ISD::AND, dl, VT, DAG.getZExtOrTrunc(Carry, dl, VT), One);
4501 SDValue Sum2 = DAG.getNode(Op, dl, VT, Sum, CarryExt);
4502
4503 // Second check for overflow. If we are adding, we can only overflow if the
4504 // initial sum is all 1s ang the carry is set, resulting in a new sum of 0.
4505 // If we are subtracting, we can only overflow if the initial sum is 0 and
4506 // the carry is set, resulting in a new sum of all 1s.
4507 SDValue Zero = DAG.getConstant(0, dl, VT);
4508 SDValue Overflow2 =
4509 IsAdd ? DAG.getSetCC(dl, SetCCType, Sum2, Zero, ISD::SETEQ)
4510 : DAG.getSetCC(dl, SetCCType, Sum, Zero, ISD::SETEQ);
4511 Overflow2 = DAG.getNode(ISD::AND, dl, SetCCType, Overflow2,
4512 DAG.getZExtOrTrunc(Carry, dl, SetCCType));
4513
4514 SDValue ResultCarry =
4515 DAG.getNode(ISD::OR, dl, SetCCType, Overflow, Overflow2);
4516
4517 Results.push_back(Sum2);
4518 Results.push_back(DAG.getBoolExtOrTrunc(ResultCarry, dl, CarryType, VT));
4519 break;
4520 }
4521 case ISD::SADDO:
4522 case ISD::SSUBO: {
4523 SDValue Result, Overflow;
4524 TLI.expandSADDSUBO(Node, Result, Overflow, DAG);
4525 Results.push_back(Result);
4526 Results.push_back(Overflow);
4527 break;
4528 }
4529 case ISD::UADDO:
4530 case ISD::USUBO: {
4531 SDValue Result, Overflow;
4532 TLI.expandUADDSUBO(Node, Result, Overflow, DAG);
4533 Results.push_back(Result);
4534 Results.push_back(Overflow);
4535 break;
4536 }
4537 case ISD::UMULO:
4538 case ISD::SMULO: {
4539 SDValue Result, Overflow;
4540 if (TLI.expandMULO(Node, Result, Overflow, DAG)) {
4541 Results.push_back(Result);
4542 Results.push_back(Overflow);
4543 }
4544 break;
4545 }
4546 case ISD::BUILD_PAIR: {
4547 EVT PairTy = Node->getValueType(0);
4548 Tmp1 = DAG.getNode(ISD::ZERO_EXTEND, dl, PairTy, Node->getOperand(0));
4549 Tmp2 = DAG.getNode(ISD::ANY_EXTEND, dl, PairTy, Node->getOperand(1));
4550 Tmp2 = DAG.getNode(
4551 ISD::SHL, dl, PairTy, Tmp2,
4552 DAG.getShiftAmountConstant(PairTy.getSizeInBits() / 2, PairTy, dl));
4553 Results.push_back(DAG.getNode(ISD::OR, dl, PairTy, Tmp1, Tmp2));
4554 break;
4555 }
4556 case ISD::SELECT:
4557 Tmp1 = Node->getOperand(0);
4558 Tmp2 = Node->getOperand(1);
4559 Tmp3 = Node->getOperand(2);
4560 if (Tmp1.getOpcode() == ISD::SETCC) {
4561 Tmp1 = DAG.getSelectCC(
4562 dl, Tmp1.getOperand(0), Tmp1.getOperand(1), Tmp2, Tmp3,
4563 cast<CondCodeSDNode>(Tmp1.getOperand(2))->get(), Node->getFlags());
4564 } else {
4565 Tmp1 =
4566 DAG.getSelectCC(dl, Tmp1, DAG.getConstant(0, dl, Tmp1.getValueType()),
4567 Tmp2, Tmp3, ISD::SETNE, Node->getFlags());
4568 }
4569 Results.push_back(Tmp1);
4570 break;
4571 case ISD::BR_JT: {
4572 SDValue Chain = Node->getOperand(0);
4573 SDValue Table = Node->getOperand(1);
4574 SDValue Index = Node->getOperand(2);
4575 int JTI = cast<JumpTableSDNode>(Table.getNode())->getIndex();
4576
4577 const DataLayout &TD = DAG.getDataLayout();
4578 EVT PTy = TLI.getPointerTy(TD);
4579
4580 unsigned EntrySize =
4582
4583 // For power-of-two jumptable entry sizes convert multiplication to a shift.
4584 // This transformation needs to be done here since otherwise the MIPS
4585 // backend will end up emitting a three instruction multiply sequence
4586 // instead of a single shift and MSP430 will call a runtime function.
4587 if (llvm::isPowerOf2_32(EntrySize))
4588 Index = DAG.getNode(
4589 ISD::SHL, dl, Index.getValueType(), Index,
4590 DAG.getConstant(llvm::Log2_32(EntrySize), dl, Index.getValueType()));
4591 else
4592 Index = DAG.getNode(ISD::MUL, dl, Index.getValueType(), Index,
4593 DAG.getConstant(EntrySize, dl, Index.getValueType()));
4594 SDValue Addr = DAG.getMemBasePlusOffset(Table, Index, dl);
4595
4596 EVT MemVT = EVT::getIntegerVT(*DAG.getContext(), EntrySize * 8);
4597 SDValue LD = DAG.getExtLoad(
4598 ISD::SEXTLOAD, dl, PTy, Chain, Addr,
4600 Addr = LD;
4601 if (TLI.isJumpTableRelative()) {
4602 // For PIC, the sequence is:
4603 // BRIND(RelocBase + load(Jumptable + index))
4604 // RelocBase can be JumpTable, GOT or some sort of global base.
4605 Addr = DAG.getMemBasePlusOffset(TLI.getPICJumpTableRelocBase(Table, DAG),
4606 Addr, dl);
4607 }
4608
4609 Tmp1 = TLI.expandIndirectJTBranch(dl, LD.getValue(1), Addr, JTI, DAG);
4610 Results.push_back(Tmp1);
4611 break;
4612 }
4613 case ISD::BRCOND:
4614 // Expand brcond's setcc into its constituent parts and create a BR_CC
4615 // Node.
4616 Tmp1 = Node->getOperand(0);
4617 Tmp2 = Node->getOperand(1);
4618 if (Tmp2.getOpcode() == ISD::SETCC &&
4620 Tmp2.getOperand(0).getValueType())) {
4621 Tmp1 = DAG.getNode(ISD::BR_CC, dl, MVT::Other, Tmp1, Tmp2.getOperand(2),
4622 Tmp2.getOperand(0), Tmp2.getOperand(1),
4623 Node->getOperand(2));
4624 } else {
4625 // We test only the i1 bit. Skip the AND if UNDEF or another AND.
4626 if (Tmp2.isUndef() ||
4627 (Tmp2.getOpcode() == ISD::AND && isOneConstant(Tmp2.getOperand(1))))
4628 Tmp3 = Tmp2;
4629 else
4630 Tmp3 = DAG.getNode(ISD::AND, dl, Tmp2.getValueType(), Tmp2,
4631 DAG.getConstant(1, dl, Tmp2.getValueType()));
4632 Tmp1 = DAG.getNode(ISD::BR_CC, dl, MVT::Other, Tmp1,
4633 DAG.getCondCode(ISD::SETNE), Tmp3,
4634 DAG.getConstant(0, dl, Tmp3.getValueType()),
4635 Node->getOperand(2));
4636 }
4637 Results.push_back(Tmp1);
4638 break;
4639 case ISD::SETCC:
4640 case ISD::VP_SETCC:
4641 case ISD::STRICT_FSETCC:
4642 case ISD::STRICT_FSETCCS: {
4643 bool IsVP = Node->getOpcode() == ISD::VP_SETCC;
4644 bool IsStrict = Node->getOpcode() == ISD::STRICT_FSETCC ||
4645 Node->getOpcode() == ISD::STRICT_FSETCCS;
4646 bool IsSignaling = Node->getOpcode() == ISD::STRICT_FSETCCS;
4647 SDValue Chain = IsStrict ? Node->getOperand(0) : SDValue();
4648 unsigned Offset = IsStrict ? 1 : 0;
4649 Tmp1 = Node->getOperand(0 + Offset);
4650 Tmp2 = Node->getOperand(1 + Offset);
4651 Tmp3 = Node->getOperand(2 + Offset);
4652 SDValue Mask, EVL;
4653 if (IsVP) {
4654 Mask = Node->getOperand(3 + Offset);
4655 EVL = Node->getOperand(4 + Offset);
4656 }
4657 bool Legalized = TLI.LegalizeSetCCCondCode(
4658 DAG, Node->getValueType(0), Tmp1, Tmp2, Tmp3, Mask, EVL, NeedInvert, dl,
4659 Chain, IsSignaling);
4660
4661 if (Legalized) {
4662 // If we expanded the SETCC by swapping LHS and RHS, or by inverting the
4663 // condition code, create a new SETCC node.
4664 if (Tmp3.getNode()) {
4665 if (IsStrict) {
4666 Tmp1 = DAG.getNode(Node->getOpcode(), dl, Node->getVTList(),
4667 {Chain, Tmp1, Tmp2, Tmp3}, Node->getFlags());
4668 Chain = Tmp1.getValue(1);
4669 } else if (IsVP) {
4670 Tmp1 = DAG.getNode(Node->getOpcode(), dl, Node->getValueType(0),
4671 {Tmp1, Tmp2, Tmp3, Mask, EVL}, Node->getFlags());
4672 } else {
4673 Tmp1 = DAG.getNode(Node->getOpcode(), dl, Node->getValueType(0), Tmp1,
4674 Tmp2, Tmp3, Node->getFlags());
4675 }
4676 }
4677
4678 // If we expanded the SETCC by inverting the condition code, then wrap
4679 // the existing SETCC in a NOT to restore the intended condition.
4680 if (NeedInvert) {
4681 if (!IsVP)
4682 Tmp1 = DAG.getLogicalNOT(dl, Tmp1, Tmp1->getValueType(0));
4683 else
4684 Tmp1 =
4685 DAG.getVPLogicalNOT(dl, Tmp1, Mask, EVL, Tmp1->getValueType(0));
4686 }
4687
4688 Results.push_back(Tmp1);
4689 if (IsStrict)
4690 Results.push_back(Chain);
4691
4692 break;
4693 }
4694
4695 // FIXME: It seems Legalized is false iff CCCode is Legal. I don't
4696 // understand if this code is useful for strict nodes.
4697 assert(!IsStrict && "Don't know how to expand for strict nodes.");
4698
4699 // Otherwise, SETCC for the given comparison type must be completely
4700 // illegal; expand it into a SELECT_CC.
4701 // FIXME: This drops the mask/evl for VP_SETCC.
4702 EVT VT = Node->getValueType(0);
4703 EVT Tmp1VT = Tmp1.getValueType();
4704 Tmp1 = DAG.getNode(ISD::SELECT_CC, dl, VT, Tmp1, Tmp2,
4705 DAG.getBoolConstant(true, dl, VT, Tmp1VT),
4706 DAG.getBoolConstant(false, dl, VT, Tmp1VT), Tmp3,
4707 Node->getFlags());
4708 Results.push_back(Tmp1);
4709 break;
4710 }
4711 case ISD::SELECT_CC: {
4712 // TODO: need to add STRICT_SELECT_CC and STRICT_SELECT_CCS
4713 Tmp1 = Node->getOperand(0); // LHS
4714 Tmp2 = Node->getOperand(1); // RHS
4715 Tmp3 = Node->getOperand(2); // True
4716 Tmp4 = Node->getOperand(3); // False
4717 EVT VT = Node->getValueType(0);
4718 SDValue Chain;
4719 SDValue CC = Node->getOperand(4);
4720 ISD::CondCode CCOp = cast<CondCodeSDNode>(CC)->get();
4721
4722 if (TLI.isCondCodeLegalOrCustom(CCOp, Tmp1.getSimpleValueType())) {
4723 // If the condition code is legal, then we need to expand this
4724 // node using SETCC and SELECT.
4725 EVT CmpVT = Tmp1.getValueType();
4727 "Cannot expand ISD::SELECT_CC when ISD::SELECT also needs to be "
4728 "expanded.");
4729 EVT CCVT = getSetCCResultType(CmpVT);
4730 SDValue Cond = DAG.getNode(ISD::SETCC, dl, CCVT, Tmp1, Tmp2, CC, Node->getFlags());
4731 Results.push_back(
4732 DAG.getSelect(dl, VT, Cond, Tmp3, Tmp4, Node->getFlags()));
4733 break;
4734 }
4735
4736 // SELECT_CC is legal, so the condition code must not be.
4737 bool Legalized = false;
4738 // Try to legalize by inverting the condition. This is for targets that
4739 // might support an ordered version of a condition, but not the unordered
4740 // version (or vice versa).
4741 ISD::CondCode InvCC = ISD::getSetCCInverse(CCOp, Tmp1.getValueType());
4742 if (TLI.isCondCodeLegalOrCustom(InvCC, Tmp1.getSimpleValueType())) {
4743 // Use the new condition code and swap true and false
4744 Legalized = true;
4745 Tmp1 =
4746 DAG.getSelectCC(dl, Tmp1, Tmp2, Tmp4, Tmp3, InvCC, Node->getFlags());
4747 } else {
4748 // If The inverse is not legal, then try to swap the arguments using
4749 // the inverse condition code.
4751 if (TLI.isCondCodeLegalOrCustom(SwapInvCC, Tmp1.getSimpleValueType())) {
4752 // The swapped inverse condition is legal, so swap true and false,
4753 // lhs and rhs.
4754 Legalized = true;
4755 Tmp1 = DAG.getSelectCC(dl, Tmp2, Tmp1, Tmp4, Tmp3, SwapInvCC,
4756 Node->getFlags());
4757 }
4758 }
4759
4760 if (!Legalized) {
4761 Legalized = TLI.LegalizeSetCCCondCode(
4762 DAG, getSetCCResultType(Tmp1.getValueType()), Tmp1, Tmp2, CC,
4763 /*Mask*/ SDValue(), /*EVL*/ SDValue(), NeedInvert, dl, Chain);
4764
4765 assert(Legalized && "Can't legalize SELECT_CC with legal condition!");
4766
4767 // If we expanded the SETCC by inverting the condition code, then swap
4768 // the True/False operands to match.
4769 if (NeedInvert)
4770 std::swap(Tmp3, Tmp4);
4771
4772 // If we expanded the SETCC by swapping LHS and RHS, or by inverting the
4773 // condition code, create a new SELECT_CC node.
4774 if (CC.getNode()) {
4775 Tmp1 = DAG.getNode(ISD::SELECT_CC, dl, Node->getValueType(0), Tmp1,
4776 Tmp2, Tmp3, Tmp4, CC, Node->getFlags());
4777 } else {
4778 Tmp2 = DAG.getConstant(0, dl, Tmp1.getValueType());
4779 CC = DAG.getCondCode(ISD::SETNE);
4780 Tmp1 = DAG.getNode(ISD::SELECT_CC, dl, Node->getValueType(0), Tmp1,
4781 Tmp2, Tmp3, Tmp4, CC, Node->getFlags());
4782 }
4783 }
4784 Results.push_back(Tmp1);
4785 break;
4786 }
4787 case ISD::BR_CC: {
4788 // TODO: need to add STRICT_BR_CC and STRICT_BR_CCS
4789 SDValue Chain;
4790 Tmp1 = Node->getOperand(0); // Chain
4791 Tmp2 = Node->getOperand(2); // LHS
4792 Tmp3 = Node->getOperand(3); // RHS
4793 Tmp4 = Node->getOperand(1); // CC
4794
4795 bool Legalized = TLI.LegalizeSetCCCondCode(
4796 DAG, getSetCCResultType(Tmp2.getValueType()), Tmp2, Tmp3, Tmp4,
4797 /*Mask*/ SDValue(), /*EVL*/ SDValue(), NeedInvert, dl, Chain);
4798 (void)Legalized;
4799 assert(Legalized && "Can't legalize BR_CC with legal condition!");
4800
4801 // If we expanded the SETCC by swapping LHS and RHS, create a new BR_CC
4802 // node.
4803 if (Tmp4.getNode()) {
4804 assert(!NeedInvert && "Don't know how to invert BR_CC!");
4805
4806 Tmp1 = DAG.getNode(ISD::BR_CC, dl, Node->getValueType(0), Tmp1,
4807 Tmp4, Tmp2, Tmp3, Node->getOperand(4));
4808 } else {
4809 Tmp3 = DAG.getConstant(0, dl, Tmp2.getValueType());
4810 Tmp4 = DAG.getCondCode(NeedInvert ? ISD::SETEQ : ISD::SETNE);
4811 Tmp1 = DAG.getNode(ISD::BR_CC, dl, Node->getValueType(0), Tmp1, Tmp4,
4812 Tmp2, Tmp3, Node->getOperand(4));
4813 }
4814 Results.push_back(Tmp1);
4815 break;
4816 }
4817 case ISD::BUILD_VECTOR:
4818 Results.push_back(ExpandBUILD_VECTOR(Node));
4819 break;
4820 case ISD::SPLAT_VECTOR:
4821 Results.push_back(ExpandSPLAT_VECTOR(Node));
4822 break;
4823 case ISD::SRA:
4824 case ISD::SRL:
4825 case ISD::SHL: {
4826 // Scalarize vector SRA/SRL/SHL.
4827 EVT VT = Node->getValueType(0);
4828 assert(VT.isVector() && "Unable to legalize non-vector shift");
4829 assert(TLI.isTypeLegal(VT.getScalarType())&& "Element type must be legal");
4830 unsigned NumElem = VT.getVectorNumElements();
4831
4833 for (unsigned Idx = 0; Idx < NumElem; Idx++) {
4834 SDValue Ex =
4836 Node->getOperand(0), DAG.getVectorIdxConstant(Idx, dl));
4837 SDValue Sh =
4839 Node->getOperand(1), DAG.getVectorIdxConstant(Idx, dl));
4840 Scalars.push_back(DAG.getNode(Node->getOpcode(), dl,
4841 VT.getScalarType(), Ex, Sh));
4842 }
4843
4844 SDValue Result = DAG.getBuildVector(Node->getValueType(0), dl, Scalars);
4845 Results.push_back(Result);
4846 break;
4847 }
4850 case ISD::VECREDUCE_ADD:
4851 case ISD::VECREDUCE_MUL:
4852 case ISD::VECREDUCE_AND:
4853 case ISD::VECREDUCE_OR:
4854 case ISD::VECREDUCE_XOR:
4863 Results.push_back(TLI.expandVecReduce(Node, DAG));
4864 break;
4865 case ISD::VP_CTTZ_ELTS:
4866 case ISD::VP_CTTZ_ELTS_ZERO_UNDEF:
4867 Results.push_back(TLI.expandVPCTTZElements(Node, DAG));
4868 break;
4869 case ISD::CLEAR_CACHE:
4870 // The default expansion of llvm.clear_cache is simply a no-op for those
4871 // targets where it is not needed.
4872 Results.push_back(Node->getOperand(0));
4873 break;
4874 case ISD::LRINT:
4875 case ISD::LLRINT: {
4876 SDValue Arg = Node->getOperand(0);
4877 EVT ArgVT = Arg.getValueType();
4878 EVT ResVT = Node->getValueType(0);
4879 SDLoc dl(Node);
4880 SDValue RoundNode = DAG.getNode(ISD::FRINT, dl, ArgVT, Arg);
4881 Results.push_back(DAG.getNode(ISD::FP_TO_SINT, dl, ResVT, RoundNode));
4882 break;
4883 }
4884 case ISD::ADDRSPACECAST:
4885 Results.push_back(DAG.UnrollVectorOp(Node));
4886 break;
4888 case ISD::GlobalAddress:
4891 case ISD::ConstantPool:
4892 case ISD::JumpTable:
4896 // FIXME: Custom lowering for these operations shouldn't return null!
4897 // Return true so that we don't call ConvertNodeToLibcall which also won't
4898 // do anything.
4899 return true;
4900 }
4901
4902 if (!TLI.isStrictFPEnabled() && Results.empty() && Node->isStrictFPOpcode()) {
4903 // FIXME: We were asked to expand a strict floating-point operation,
4904 // but there is currently no expansion implemented that would preserve
4905 // the "strict" properties. For now, we just fall back to the non-strict
4906 // version if that is legal on the target. The actual mutation of the
4907 // operation will happen in SelectionDAGISel::DoInstructionSelection.
4908 switch (Node->getOpcode()) {
4909 default:
4910 if (TLI.getStrictFPOperationAction(Node->getOpcode(),
4911 Node->getValueType(0))
4912 == TargetLowering::Legal)
4913 return true;
4914 break;
4915 case ISD::STRICT_FSUB: {
4917 ISD::STRICT_FSUB, Node->getValueType(0)) == TargetLowering::Legal)
4918 return true;
4920 ISD::STRICT_FADD, Node->getValueType(0)) != TargetLowering::Legal)
4921 break;
4922
4923 EVT VT = Node->getValueType(0);
4924 const SDNodeFlags Flags = Node->getFlags();
4925 SDValue Neg = DAG.getNode(ISD::FNEG, dl, VT, Node->getOperand(2), Flags);
4926 SDValue Fadd = DAG.getNode(ISD::STRICT_FADD, dl, Node->getVTList(),
4927 {Node->getOperand(0), Node->getOperand(1), Neg},
4928 Flags);
4929
4930 Results.push_back(Fadd);
4931 Results.push_back(Fadd.getValue(1));
4932 break;
4933 }
4936 case ISD::STRICT_LRINT:
4937 case ISD::STRICT_LLRINT:
4938 case ISD::STRICT_LROUND:
4940 // These are registered by the operand type instead of the value
4941 // type. Reflect that here.
4942 if (TLI.getStrictFPOperationAction(Node->getOpcode(),
4943 Node->getOperand(1).getValueType())
4944 == TargetLowering::Legal)
4945 return true;
4946 break;
4947 }
4948 }
4949
4950 // Replace the original node with the legalized result.
4951 if (Results.empty()) {
4952 LLVM_DEBUG(dbgs() << "Cannot expand node\n");
4953 return false;
4954 }
4955
4956 LLVM_DEBUG(dbgs() << "Successfully expanded node\n");
4957 ReplaceNode(Node, Results.data());
4958 return true;
4959}
4960
4961/// Return if we can use the FAST_* variant of a math libcall for the node.
4962/// FIXME: This is just guessing, we probably should have unique specific sets
4963/// flags required per libcall.
4964static bool canUseFastMathLibcall(const SDNode *Node) {
4965 // FIXME: Probably should define fast to respect nan/inf and only be
4966 // approximate functions.
4967
4968 SDNodeFlags Flags = Node->getFlags();
4969 return Flags.hasApproximateFuncs() && Flags.hasNoNaNs() &&
4970 Flags.hasNoInfs() && Flags.hasNoSignedZeros();
4971}
4972
4973void SelectionDAGLegalize::ConvertNodeToLibcall(SDNode *Node) {
4974 LLVM_DEBUG(dbgs() << "Trying to convert node to libcall\n");
4976 SDLoc dl(Node);
4977 TargetLowering::MakeLibCallOptions CallOptions;
4978 CallOptions.IsPostTypeLegalization = true;
4979 // FIXME: Check flags on the node to see if we can use a finite call.
4980 unsigned Opc = Node->getOpcode();
4981 switch (Opc) {
4982 case ISD::ATOMIC_FENCE: {
4983 // If the target didn't lower this, lower it to '__sync_synchronize()' call
4984 // FIXME: handle "fence singlethread" more efficiently.
4985 TargetLowering::ArgListTy Args;
4986
4987 TargetLowering::CallLoweringInfo CLI(DAG);
4988 CLI.setDebugLoc(dl)
4989 .setChain(Node->getOperand(0))
4990 .setLibCallee(
4991 CallingConv::C, Type::getVoidTy(*DAG.getContext()),
4992 DAG.getExternalSymbol("__sync_synchronize",
4993 TLI.getPointerTy(DAG.getDataLayout())),
4994 std::move(Args));
4995
4996 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
4997
4998 Results.push_back(CallResult.second);
4999 break;
5000 }
5001 // By default, atomic intrinsics are marked Legal and lowered. Targets
5002 // which don't support them directly, however, may want libcalls, in which
5003 // case they mark them Expand, and we get here.
5004 case ISD::ATOMIC_SWAP:
5016 case ISD::ATOMIC_CMP_SWAP: {
5017 MVT VT = cast<AtomicSDNode>(Node)->getMemoryVT().getSimpleVT();
5018 AtomicOrdering Order = cast<AtomicSDNode>(Node)->getMergedOrdering();
5019 RTLIB::Libcall LC = RTLIB::getOUTLINE_ATOMIC(Opc, Order, VT);
5020 EVT RetVT = Node->getValueType(0);
5022 if (DAG.getLibcalls().getLibcallImpl(LC) != RTLIB::Unsupported) {
5023 // If outline atomic available, prepare its arguments and expand.
5024 Ops.append(Node->op_begin() + 2, Node->op_end());
5025 Ops.push_back(Node->getOperand(1));
5026
5027 } else {
5028 LC = RTLIB::getSYNC(Opc, VT);
5029 assert(LC != RTLIB::UNKNOWN_LIBCALL &&
5030 "Unexpected atomic op or value type!");
5031 // Arguments for expansion to sync libcall
5032 Ops.append(Node->op_begin() + 1, Node->op_end());
5033 }
5034 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(DAG, LC, RetVT,
5035 Ops, CallOptions,
5036 SDLoc(Node),
5037 Node->getOperand(0));
5038 Results.push_back(Tmp.first);
5039 Results.push_back(Tmp.second);
5040 break;
5041 }
5042 case ISD::TRAP: {
5043 // If this operation is not supported, lower it to 'abort()' call
5044 TargetLowering::ArgListTy Args;
5045 TargetLowering::CallLoweringInfo CLI(DAG);
5046 CLI.setDebugLoc(dl)
5047 .setChain(Node->getOperand(0))
5048 .setLibCallee(CallingConv::C, Type::getVoidTy(*DAG.getContext()),
5050 "abort", TLI.getPointerTy(DAG.getDataLayout())),
5051 std::move(Args));
5052 std::pair<SDValue, SDValue> CallResult = TLI.LowerCallTo(CLI);
5053
5054 Results.push_back(CallResult.second);
5055 break;
5056 }
5057 case ISD::CLEAR_CACHE: {
5058 SDValue InputChain = Node->getOperand(0);
5059 SDValue StartVal = Node->getOperand(1);
5060 SDValue EndVal = Node->getOperand(2);
5061 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(
5062 DAG, RTLIB::CLEAR_CACHE, MVT::isVoid, {StartVal, EndVal}, CallOptions,
5063 SDLoc(Node), InputChain);
5064 Results.push_back(Tmp.second);
5065 break;
5066 }
5067 case ISD::FMINNUM:
5069 ExpandFPLibCall(Node, RTLIB::FMIN_F32, RTLIB::FMIN_F64,
5070 RTLIB::FMIN_F80, RTLIB::FMIN_F128,
5071 RTLIB::FMIN_PPCF128, Results);
5072 break;
5073 // FIXME: We do not have libcalls for FMAXIMUM and FMINIMUM. So, we cannot use
5074 // libcall legalization for these nodes, but there is no default expasion for
5075 // these nodes either (see PR63267 for example).
5076 case ISD::FMAXNUM:
5078 ExpandFPLibCall(Node, RTLIB::FMAX_F32, RTLIB::FMAX_F64,
5079 RTLIB::FMAX_F80, RTLIB::FMAX_F128,
5080 RTLIB::FMAX_PPCF128, Results);
5081 break;
5082 case ISD::FMINIMUMNUM:
5083 ExpandFPLibCall(Node, RTLIB::FMINIMUM_NUM_F32, RTLIB::FMINIMUM_NUM_F64,
5084 RTLIB::FMINIMUM_NUM_F80, RTLIB::FMINIMUM_NUM_F128,
5085 RTLIB::FMINIMUM_NUM_PPCF128, Results);
5086 break;
5087 case ISD::FMAXIMUMNUM:
5088 ExpandFPLibCall(Node, RTLIB::FMAXIMUM_NUM_F32, RTLIB::FMAXIMUM_NUM_F64,
5089 RTLIB::FMAXIMUM_NUM_F80, RTLIB::FMAXIMUM_NUM_F128,
5090 RTLIB::FMAXIMUM_NUM_PPCF128, Results);
5091 break;
5092 case ISD::FSQRT:
5093 case ISD::STRICT_FSQRT: {
5094 // FIXME: Probably should define fast to respect nan/inf and only be
5095 // approximate functions.
5096 ExpandFastFPLibCall(Node, canUseFastMathLibcall(Node),
5097 {RTLIB::FAST_SQRT_F32, RTLIB::SQRT_F32},
5098 {RTLIB::FAST_SQRT_F64, RTLIB::SQRT_F64},
5099 {RTLIB::FAST_SQRT_F80, RTLIB::SQRT_F80},
5100 {RTLIB::FAST_SQRT_F128, RTLIB::SQRT_F128},
5101 {RTLIB::FAST_SQRT_PPCF128, RTLIB::SQRT_PPCF128},
5102 Results);
5103 break;
5104 }
5105 case ISD::FCBRT:
5106 ExpandFPLibCall(Node, RTLIB::CBRT_F32, RTLIB::CBRT_F64,
5107 RTLIB::CBRT_F80, RTLIB::CBRT_F128,
5108 RTLIB::CBRT_PPCF128, Results);
5109 break;
5110 case ISD::FSIN:
5111 case ISD::STRICT_FSIN:
5112 ExpandFPLibCall(Node, RTLIB::SIN_F32, RTLIB::SIN_F64,
5113 RTLIB::SIN_F80, RTLIB::SIN_F128,
5114 RTLIB::SIN_PPCF128, Results);
5115 break;
5116 case ISD::FCOS:
5117 case ISD::STRICT_FCOS:
5118 ExpandFPLibCall(Node, RTLIB::COS_F32, RTLIB::COS_F64,
5119 RTLIB::COS_F80, RTLIB::COS_F128,
5120 RTLIB::COS_PPCF128, Results);
5121 break;
5122 case ISD::FTAN:
5123 case ISD::STRICT_FTAN:
5124 ExpandFPLibCall(Node, RTLIB::TAN_F32, RTLIB::TAN_F64, RTLIB::TAN_F80,
5125 RTLIB::TAN_F128, RTLIB::TAN_PPCF128, Results);
5126 break;
5127 case ISD::FASIN:
5128 case ISD::STRICT_FASIN:
5129 ExpandFPLibCall(Node, RTLIB::ASIN_F32, RTLIB::ASIN_F64, RTLIB::ASIN_F80,
5130 RTLIB::ASIN_F128, RTLIB::ASIN_PPCF128, Results);
5131 break;
5132 case ISD::FACOS:
5133 case ISD::STRICT_FACOS:
5134 ExpandFPLibCall(Node, RTLIB::ACOS_F32, RTLIB::ACOS_F64, RTLIB::ACOS_F80,
5135 RTLIB::ACOS_F128, RTLIB::ACOS_PPCF128, Results);
5136 break;
5137 case ISD::FATAN:
5138 case ISD::STRICT_FATAN:
5139 ExpandFPLibCall(Node, RTLIB::ATAN_F32, RTLIB::ATAN_F64, RTLIB::ATAN_F80,
5140 RTLIB::ATAN_F128, RTLIB::ATAN_PPCF128, Results);
5141 break;
5142 case ISD::FATAN2:
5143 case ISD::STRICT_FATAN2:
5144 ExpandFPLibCall(Node, RTLIB::ATAN2_F32, RTLIB::ATAN2_F64, RTLIB::ATAN2_F80,
5145 RTLIB::ATAN2_F128, RTLIB::ATAN2_PPCF128, Results);
5146 break;
5147 case ISD::FSINH:
5148 case ISD::STRICT_FSINH:
5149 ExpandFPLibCall(Node, RTLIB::SINH_F32, RTLIB::SINH_F64, RTLIB::SINH_F80,
5150 RTLIB::SINH_F128, RTLIB::SINH_PPCF128, Results);
5151 break;
5152 case ISD::FCOSH:
5153 case ISD::STRICT_FCOSH:
5154 ExpandFPLibCall(Node, RTLIB::COSH_F32, RTLIB::COSH_F64, RTLIB::COSH_F80,
5155 RTLIB::COSH_F128, RTLIB::COSH_PPCF128, Results);
5156 break;
5157 case ISD::FTANH:
5158 case ISD::STRICT_FTANH:
5159 ExpandFPLibCall(Node, RTLIB::TANH_F32, RTLIB::TANH_F64, RTLIB::TANH_F80,
5160 RTLIB::TANH_F128, RTLIB::TANH_PPCF128, Results);
5161 break;
5162 case ISD::FSINCOS:
5163 case ISD::FSINCOSPI: {
5164 EVT VT = Node->getValueType(0);
5165
5166 if (Node->getOpcode() == ISD::FSINCOS) {
5167 RTLIB::Libcall SincosStret = RTLIB::getSINCOS_STRET(VT);
5168 if (SincosStret != RTLIB::UNKNOWN_LIBCALL) {
5169 if (SDValue Expanded = ExpandSincosStretLibCall(Node)) {
5170 Results.push_back(Expanded);
5171 Results.push_back(Expanded.getValue(1));
5172 break;
5173 }
5174 }
5175 }
5176
5177 RTLIB::Libcall LC = Node->getOpcode() == ISD::FSINCOS
5178 ? RTLIB::getSINCOS(VT)
5179 : RTLIB::getSINCOSPI(VT);
5180 bool Expanded = TLI.expandMultipleResultFPLibCall(DAG, LC, Node, Results);
5181 if (!Expanded) {
5182 DAG.getContext()->emitError(Twine("no libcall available for ") +
5183 Node->getOperationName(&DAG));
5184 SDValue Poison = DAG.getPOISON(VT);
5185 Results.push_back(Poison);
5186 Results.push_back(Poison);
5187 }
5188
5189 break;
5190 }
5191 case ISD::FLOG:
5192 case ISD::STRICT_FLOG:
5193 ExpandFPLibCall(Node, RTLIB::LOG_F32, RTLIB::LOG_F64, RTLIB::LOG_F80,
5194 RTLIB::LOG_F128, RTLIB::LOG_PPCF128, Results);
5195 break;
5196 case ISD::FLOG2:
5197 case ISD::STRICT_FLOG2:
5198 ExpandFPLibCall(Node, RTLIB::LOG2_F32, RTLIB::LOG2_F64, RTLIB::LOG2_F80,
5199 RTLIB::LOG2_F128, RTLIB::LOG2_PPCF128, Results);
5200 break;
5201 case ISD::FLOG10:
5202 case ISD::STRICT_FLOG10:
5203 ExpandFPLibCall(Node, RTLIB::LOG10_F32, RTLIB::LOG10_F64, RTLIB::LOG10_F80,
5204 RTLIB::LOG10_F128, RTLIB::LOG10_PPCF128, Results);
5205 break;
5206 case ISD::FEXP:
5207 case ISD::STRICT_FEXP:
5208 ExpandFPLibCall(Node, RTLIB::EXP_F32, RTLIB::EXP_F64, RTLIB::EXP_F80,
5209 RTLIB::EXP_F128, RTLIB::EXP_PPCF128, Results);
5210 break;
5211 case ISD::FEXP2:
5212 case ISD::STRICT_FEXP2:
5213 ExpandFPLibCall(Node, RTLIB::EXP2_F32, RTLIB::EXP2_F64, RTLIB::EXP2_F80,
5214 RTLIB::EXP2_F128, RTLIB::EXP2_PPCF128, Results);
5215 break;
5216 case ISD::FEXP10:
5217 ExpandFPLibCall(Node, RTLIB::EXP10_F32, RTLIB::EXP10_F64, RTLIB::EXP10_F80,
5218 RTLIB::EXP10_F128, RTLIB::EXP10_PPCF128, Results);
5219 break;
5220 case ISD::FTRUNC:
5221 case ISD::STRICT_FTRUNC:
5222 ExpandFPLibCall(Node, RTLIB::TRUNC_F32, RTLIB::TRUNC_F64,
5223 RTLIB::TRUNC_F80, RTLIB::TRUNC_F128,
5224 RTLIB::TRUNC_PPCF128, Results);
5225 break;
5226 case ISD::FFLOOR:
5227 case ISD::STRICT_FFLOOR:
5228 ExpandFPLibCall(Node, RTLIB::FLOOR_F32, RTLIB::FLOOR_F64,
5229 RTLIB::FLOOR_F80, RTLIB::FLOOR_F128,
5230 RTLIB::FLOOR_PPCF128, Results);
5231 break;
5232 case ISD::FCEIL:
5233 case ISD::STRICT_FCEIL:
5234 ExpandFPLibCall(Node, RTLIB::CEIL_F32, RTLIB::CEIL_F64,
5235 RTLIB::CEIL_F80, RTLIB::CEIL_F128,
5236 RTLIB::CEIL_PPCF128, Results);
5237 break;
5238 case ISD::FRINT:
5239 case ISD::STRICT_FRINT:
5240 ExpandFPLibCall(Node, RTLIB::RINT_F32, RTLIB::RINT_F64,
5241 RTLIB::RINT_F80, RTLIB::RINT_F128,
5242 RTLIB::RINT_PPCF128, Results);
5243 break;
5244 case ISD::FNEARBYINT:
5246 ExpandFPLibCall(Node, RTLIB::NEARBYINT_F32,
5247 RTLIB::NEARBYINT_F64,
5248 RTLIB::NEARBYINT_F80,
5249 RTLIB::NEARBYINT_F128,
5250 RTLIB::NEARBYINT_PPCF128, Results);
5251 break;
5252 case ISD::FROUND:
5253 case ISD::STRICT_FROUND:
5254 ExpandFPLibCall(Node, RTLIB::ROUND_F32,
5255 RTLIB::ROUND_F64,
5256 RTLIB::ROUND_F80,
5257 RTLIB::ROUND_F128,
5258 RTLIB::ROUND_PPCF128, Results);
5259 break;
5260 case ISD::FROUNDEVEN:
5262 ExpandFPLibCall(Node, RTLIB::ROUNDEVEN_F32,
5263 RTLIB::ROUNDEVEN_F64,
5264 RTLIB::ROUNDEVEN_F80,
5265 RTLIB::ROUNDEVEN_F128,
5266 RTLIB::ROUNDEVEN_PPCF128, Results);
5267 break;
5268 case ISD::FLDEXP:
5269 case ISD::STRICT_FLDEXP:
5270 ExpandFPLibCall(Node, RTLIB::LDEXP_F32, RTLIB::LDEXP_F64, RTLIB::LDEXP_F80,
5271 RTLIB::LDEXP_F128, RTLIB::LDEXP_PPCF128, Results);
5272 break;
5273 case ISD::FMODF:
5274 case ISD::FFREXP: {
5275 EVT VT = Node->getValueType(0);
5276 RTLIB::Libcall LC = Node->getOpcode() == ISD::FMODF ? RTLIB::getMODF(VT)
5277 : RTLIB::getFREXP(VT);
5278 bool Expanded = TLI.expandMultipleResultFPLibCall(DAG, LC, Node, Results,
5279 /*CallRetResNo=*/0);
5280 if (!Expanded)
5281 llvm_unreachable("Expected scalar FFREXP/FMODF to expand to libcall!");
5282 break;
5283 }
5284 case ISD::FPOWI:
5285 case ISD::STRICT_FPOWI: {
5286 RTLIB::Libcall LC = RTLIB::getPOWI(Node->getSimpleValueType(0));
5287 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected fpowi.");
5288 if (DAG.getLibcalls().getLibcallImpl(LC) == RTLIB::Unsupported) {
5289 // Some targets don't have a powi libcall; use pow instead.
5290 if (Node->isStrictFPOpcode()) {
5292 DAG.getNode(ISD::STRICT_SINT_TO_FP, SDLoc(Node),
5293 {Node->getValueType(0), Node->getValueType(1)},
5294 {Node->getOperand(0), Node->getOperand(2)});
5295 SDValue FPOW =
5296 DAG.getNode(ISD::STRICT_FPOW, SDLoc(Node),
5297 {Node->getValueType(0), Node->getValueType(1)},
5298 {Exponent.getValue(1), Node->getOperand(1), Exponent});
5299 Results.push_back(FPOW);
5300 Results.push_back(FPOW.getValue(1));
5301 } else {
5303 DAG.getNode(ISD::SINT_TO_FP, SDLoc(Node), Node->getValueType(0),
5304 Node->getOperand(1));
5305 Results.push_back(DAG.getNode(ISD::FPOW, SDLoc(Node),
5306 Node->getValueType(0),
5307 Node->getOperand(0), Exponent));
5308 }
5309 break;
5310 }
5311 unsigned Offset = Node->isStrictFPOpcode() ? 1 : 0;
5312 bool ExponentHasSizeOfInt =
5313 DAG.getLibInfo().getIntSize() ==
5314 Node->getOperand(1 + Offset).getValueType().getSizeInBits();
5315 if (!ExponentHasSizeOfInt) {
5316 // If the exponent does not match with sizeof(int) a libcall to
5317 // RTLIB::POWI would use the wrong type for the argument.
5318 DAG.getContext()->emitError("POWI exponent does not match sizeof(int)");
5319 Results.push_back(DAG.getPOISON(Node->getValueType(0)));
5320 break;
5321 }
5322 ExpandFPLibCall(Node, LC, Results);
5323 break;
5324 }
5325 case ISD::FPOW:
5326 case ISD::STRICT_FPOW:
5327 ExpandFPLibCall(Node, RTLIB::POW_F32, RTLIB::POW_F64, RTLIB::POW_F80,
5328 RTLIB::POW_F128, RTLIB::POW_PPCF128, Results);
5329 break;
5330 case ISD::LROUND:
5331 case ISD::STRICT_LROUND:
5332 ExpandArgFPLibCall(Node, RTLIB::LROUND_F32,
5333 RTLIB::LROUND_F64, RTLIB::LROUND_F80,
5334 RTLIB::LROUND_F128,
5335 RTLIB::LROUND_PPCF128, Results);
5336 break;
5337 case ISD::LLROUND:
5339 ExpandArgFPLibCall(Node, RTLIB::LLROUND_F32,
5340 RTLIB::LLROUND_F64, RTLIB::LLROUND_F80,
5341 RTLIB::LLROUND_F128,
5342 RTLIB::LLROUND_PPCF128, Results);
5343 break;
5344 case ISD::LRINT:
5345 case ISD::STRICT_LRINT:
5346 ExpandArgFPLibCall(Node, RTLIB::LRINT_F32,
5347 RTLIB::LRINT_F64, RTLIB::LRINT_F80,
5348 RTLIB::LRINT_F128,
5349 RTLIB::LRINT_PPCF128, Results);
5350 break;
5351 case ISD::LLRINT:
5352 case ISD::STRICT_LLRINT:
5353 ExpandArgFPLibCall(Node, RTLIB::LLRINT_F32,
5354 RTLIB::LLRINT_F64, RTLIB::LLRINT_F80,
5355 RTLIB::LLRINT_F128,
5356 RTLIB::LLRINT_PPCF128, Results);
5357 break;
5358 case ISD::FDIV:
5359 case ISD::STRICT_FDIV: {
5360 ExpandFastFPLibCall(Node, canUseFastMathLibcall(Node),
5361 {RTLIB::FAST_DIV_F32, RTLIB::DIV_F32},
5362 {RTLIB::FAST_DIV_F64, RTLIB::DIV_F64},
5363 {RTLIB::FAST_DIV_F80, RTLIB::DIV_F80},
5364 {RTLIB::FAST_DIV_F128, RTLIB::DIV_F128},
5365 {RTLIB::FAST_DIV_PPCF128, RTLIB::DIV_PPCF128}, Results);
5366 break;
5367 }
5368 case ISD::FREM:
5369 case ISD::STRICT_FREM:
5370 ExpandFPLibCall(Node, RTLIB::REM_F32, RTLIB::REM_F64,
5371 RTLIB::REM_F80, RTLIB::REM_F128,
5372 RTLIB::REM_PPCF128, Results);
5373 break;
5374 case ISD::FMA:
5375 case ISD::STRICT_FMA:
5376 ExpandFPLibCall(Node, RTLIB::FMA_F32, RTLIB::FMA_F64,
5377 RTLIB::FMA_F80, RTLIB::FMA_F128,
5378 RTLIB::FMA_PPCF128, Results);
5379 break;
5380 case ISD::FADD:
5381 case ISD::STRICT_FADD: {
5382 ExpandFastFPLibCall(Node, canUseFastMathLibcall(Node),
5383 {RTLIB::FAST_ADD_F32, RTLIB::ADD_F32},
5384 {RTLIB::FAST_ADD_F64, RTLIB::ADD_F64},
5385 {RTLIB::FAST_ADD_F80, RTLIB::ADD_F80},
5386 {RTLIB::FAST_ADD_F128, RTLIB::ADD_F128},
5387 {RTLIB::FAST_ADD_PPCF128, RTLIB::ADD_PPCF128}, Results);
5388 break;
5389 }
5390 case ISD::FMUL:
5391 case ISD::STRICT_FMUL: {
5392 ExpandFastFPLibCall(Node, canUseFastMathLibcall(Node),
5393 {RTLIB::FAST_MUL_F32, RTLIB::MUL_F32},
5394 {RTLIB::FAST_MUL_F64, RTLIB::MUL_F64},
5395 {RTLIB::FAST_MUL_F80, RTLIB::MUL_F80},
5396 {RTLIB::FAST_MUL_F128, RTLIB::MUL_F128},
5397 {RTLIB::FAST_MUL_PPCF128, RTLIB::MUL_PPCF128}, Results);
5398 break;
5399 }
5400 case ISD::FP16_TO_FP:
5401 if (Node->getValueType(0) == MVT::f32) {
5402 Results.push_back(ExpandLibCall(RTLIB::FPEXT_F16_F32, Node, false).first);
5403 }
5404 break;
5406 if (Node->getValueType(0) == MVT::f32) {
5407 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(
5408 DAG, RTLIB::FPEXT_BF16_F32, MVT::f32, Node->getOperand(1),
5409 CallOptions, SDLoc(Node), Node->getOperand(0));
5410 Results.push_back(Tmp.first);
5411 Results.push_back(Tmp.second);
5412 }
5413 break;
5415 if (Node->getValueType(0) == MVT::f32) {
5416 std::pair<SDValue, SDValue> Tmp = TLI.makeLibCall(
5417 DAG, RTLIB::FPEXT_F16_F32, MVT::f32, Node->getOperand(1), CallOptions,
5418 SDLoc(Node), Node->getOperand(0));
5419 Results.push_back(Tmp.first);
5420 Results.push_back(Tmp.second);
5421 }
5422 break;
5423 }
5424 case ISD::FP_TO_FP16: {
5425 RTLIB::Libcall LC =
5426 RTLIB::getFPROUND(Node->getOperand(0).getValueType(), MVT::f16);
5427 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to expand fp_to_fp16");
5428 Results.push_back(ExpandLibCall(LC, Node, false).first);
5429 break;
5430 }
5431 case ISD::FP_TO_BF16: {
5432 RTLIB::Libcall LC =
5433 RTLIB::getFPROUND(Node->getOperand(0).getValueType(), MVT::bf16);
5434 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to expand fp_to_bf16");
5435 Results.push_back(ExpandLibCall(LC, Node, false).first);
5436 break;
5437 }
5440 case ISD::SINT_TO_FP:
5441 case ISD::UINT_TO_FP: {
5442 // TODO - Common the code with DAGTypeLegalizer::SoftenFloatRes_XINT_TO_FP
5443 bool IsStrict = Node->isStrictFPOpcode();
5444 bool Signed = Node->getOpcode() == ISD::SINT_TO_FP ||
5445 Node->getOpcode() == ISD::STRICT_SINT_TO_FP;
5446 EVT SVT = Node->getOperand(IsStrict ? 1 : 0).getValueType();
5447 EVT RVT = Node->getValueType(0);
5448 EVT NVT = EVT();
5449 SDLoc dl(Node);
5450
5451 // Even if the input is legal, no libcall may exactly match, eg. we don't
5452 // have i1 -> fp conversions. So, it needs to be promoted to a larger type,
5453 // eg: i13 -> fp. Then, look for an appropriate libcall.
5454 RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
5455 for (unsigned t = MVT::FIRST_INTEGER_VALUETYPE;
5456 t <= MVT::LAST_INTEGER_VALUETYPE && LC == RTLIB::UNKNOWN_LIBCALL;
5457 ++t) {
5458 NVT = (MVT::SimpleValueType)t;
5459 // The source needs to big enough to hold the operand.
5460 if (NVT.bitsGE(SVT))
5461 LC = Signed ? RTLIB::getSINTTOFP(NVT, RVT)
5462 : RTLIB::getUINTTOFP(NVT, RVT);
5463 }
5464 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to legalize as libcall");
5465
5466 SDValue Chain = IsStrict ? Node->getOperand(0) : SDValue();
5467 // Sign/zero extend the argument if the libcall takes a larger type.
5469 NVT, Node->getOperand(IsStrict ? 1 : 0));
5470 CallOptions.setIsSigned(Signed);
5471 std::pair<SDValue, SDValue> Tmp =
5472 TLI.makeLibCall(DAG, LC, RVT, Op, CallOptions, dl, Chain);
5473 Results.push_back(Tmp.first);
5474 if (IsStrict)
5475 Results.push_back(Tmp.second);
5476 break;
5477 }
5478 case ISD::FP_TO_SINT:
5479 case ISD::FP_TO_UINT:
5482 // TODO - Common the code with DAGTypeLegalizer::SoftenFloatOp_FP_TO_XINT.
5483 bool IsStrict = Node->isStrictFPOpcode();
5484 bool Signed = Node->getOpcode() == ISD::FP_TO_SINT ||
5485 Node->getOpcode() == ISD::STRICT_FP_TO_SINT;
5486
5487 SDValue Op = Node->getOperand(IsStrict ? 1 : 0);
5488 EVT SVT = Op.getValueType();
5489 EVT RVT = Node->getValueType(0);
5490 EVT NVT = EVT();
5491 SDLoc dl(Node);
5492
5493 // Even if the result is legal, no libcall may exactly match, eg. we don't
5494 // have fp -> i1 conversions. So, it needs to be promoted to a larger type,
5495 // eg: fp -> i32. Then, look for an appropriate libcall.
5496 RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
5497 for (unsigned IntVT = MVT::FIRST_INTEGER_VALUETYPE;
5498 IntVT <= MVT::LAST_INTEGER_VALUETYPE && LC == RTLIB::UNKNOWN_LIBCALL;
5499 ++IntVT) {
5500 NVT = (MVT::SimpleValueType)IntVT;
5501 // The type needs to big enough to hold the result.
5502 if (NVT.bitsGE(RVT))
5503 LC = Signed ? RTLIB::getFPTOSINT(SVT, NVT)
5504 : RTLIB::getFPTOUINT(SVT, NVT);
5505 }
5506 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to legalize as libcall");
5507
5508 SDValue Chain = IsStrict ? Node->getOperand(0) : SDValue();
5509 std::pair<SDValue, SDValue> Tmp =
5510 TLI.makeLibCall(DAG, LC, NVT, Op, CallOptions, dl, Chain);
5511
5512 // Truncate the result if the libcall returns a larger type.
5513 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, RVT, Tmp.first));
5514 if (IsStrict)
5515 Results.push_back(Tmp.second);
5516 break;
5517 }
5518
5519 case ISD::FP_ROUND:
5520 case ISD::STRICT_FP_ROUND: {
5521 // X = FP_ROUND(Y, TRUNC)
5522 // TRUNC is a flag, which is always an integer that is zero or one.
5523 // If TRUNC is 0, this is a normal rounding, if it is 1, this FP_ROUND
5524 // is known to not change the value of Y.
5525 // We can only expand it into libcall if the TRUNC is 0.
5526 bool IsStrict = Node->isStrictFPOpcode();
5527 SDValue Op = Node->getOperand(IsStrict ? 1 : 0);
5528 SDValue Chain = IsStrict ? Node->getOperand(0) : SDValue();
5529 EVT VT = Node->getValueType(0);
5530 assert(cast<ConstantSDNode>(Node->getOperand(IsStrict ? 2 : 1))->isZero() &&
5531 "Unable to expand as libcall if it is not normal rounding");
5532
5533 RTLIB::Libcall LC = RTLIB::getFPROUND(Op.getValueType(), VT);
5534 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to legalize as libcall");
5535
5536 std::pair<SDValue, SDValue> Tmp =
5537 TLI.makeLibCall(DAG, LC, VT, Op, CallOptions, SDLoc(Node), Chain);
5538 Results.push_back(Tmp.first);
5539 if (IsStrict)
5540 Results.push_back(Tmp.second);
5541 break;
5542 }
5543 case ISD::FP_EXTEND: {
5544 Results.push_back(
5545 ExpandLibCall(RTLIB::getFPEXT(Node->getOperand(0).getValueType(),
5546 Node->getValueType(0)),
5547 Node, false).first);
5548 break;
5549 }
5553 RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
5554 if (Node->getOpcode() == ISD::STRICT_FP_TO_FP16)
5555 LC = RTLIB::getFPROUND(Node->getOperand(1).getValueType(), MVT::f16);
5556 else if (Node->getOpcode() == ISD::STRICT_FP_TO_BF16)
5557 LC = RTLIB::getFPROUND(Node->getOperand(1).getValueType(), MVT::bf16);
5558 else
5559 LC = RTLIB::getFPEXT(Node->getOperand(1).getValueType(),
5560 Node->getValueType(0));
5561
5562 assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unable to legalize as libcall");
5563
5564 std::pair<SDValue, SDValue> Tmp =
5565 TLI.makeLibCall(DAG, LC, Node->getValueType(0), Node->getOperand(1),
5566 CallOptions, SDLoc(Node), Node->getOperand(0));
5567 Results.push_back(Tmp.first);
5568 Results.push_back(Tmp.second);
5569 break;
5570 }
5571 case ISD::FSUB:
5572 case ISD::STRICT_FSUB: {
5573 ExpandFastFPLibCall(Node, canUseFastMathLibcall(Node),
5574 {RTLIB::FAST_SUB_F32, RTLIB::SUB_F32},
5575 {RTLIB::FAST_SUB_F64, RTLIB::SUB_F64},
5576 {RTLIB::FAST_SUB_F80, RTLIB::SUB_F80},
5577 {RTLIB::FAST_SUB_F128, RTLIB::SUB_F128},
5578 {RTLIB::FAST_SUB_PPCF128, RTLIB::SUB_PPCF128}, Results);
5579 break;
5580 }
5581 case ISD::SREM:
5582 Results.push_back(ExpandIntLibCall(Node, true,
5583 RTLIB::SREM_I8,
5584 RTLIB::SREM_I16, RTLIB::SREM_I32,
5585 RTLIB::SREM_I64, RTLIB::SREM_I128));
5586 break;
5587 case ISD::UREM:
5588 Results.push_back(ExpandIntLibCall(Node, false,
5589 RTLIB::UREM_I8,
5590 RTLIB::UREM_I16, RTLIB::UREM_I32,
5591 RTLIB::UREM_I64, RTLIB::UREM_I128));
5592 break;
5593 case ISD::SDIV:
5594 Results.push_back(ExpandIntLibCall(Node, true,
5595 RTLIB::SDIV_I8,
5596 RTLIB::SDIV_I16, RTLIB::SDIV_I32,
5597 RTLIB::SDIV_I64, RTLIB::SDIV_I128));
5598 break;
5599 case ISD::UDIV:
5600 Results.push_back(ExpandIntLibCall(Node, false,
5601 RTLIB::UDIV_I8,
5602 RTLIB::UDIV_I16, RTLIB::UDIV_I32,
5603 RTLIB::UDIV_I64, RTLIB::UDIV_I128));
5604 break;
5605 case ISD::SDIVREM:
5606 case ISD::UDIVREM:
5607 // Expand into divrem libcall
5608 ExpandDivRemLibCall(Node, Results);
5609 break;
5610 case ISD::MUL:
5611 Results.push_back(ExpandIntLibCall(Node, false,
5612 RTLIB::MUL_I8,
5613 RTLIB::MUL_I16, RTLIB::MUL_I32,
5614 RTLIB::MUL_I64, RTLIB::MUL_I128));
5615 break;
5617 Results.push_back(ExpandBitCountingLibCall(
5618 Node, RTLIB::CTLZ_I32, RTLIB::CTLZ_I64, RTLIB::CTLZ_I128));
5619 break;
5620 case ISD::CTPOP:
5621 Results.push_back(ExpandBitCountingLibCall(
5622 Node, RTLIB::CTPOP_I32, RTLIB::CTPOP_I64, RTLIB::CTPOP_I128));
5623 break;
5624 case ISD::RESET_FPENV: {
5625 // It is legalized to call 'fesetenv(FE_DFL_ENV)'. On most targets
5626 // FE_DFL_ENV is defined as '((const fenv_t *) -1)' in glibc.
5627 EVT PtrTy = TLI.getPointerTy(DAG.getDataLayout());
5628 SDValue Ptr = DAG.getAllOnesConstant(dl, PtrTy);
5629 SDValue Chain = Node->getOperand(0);
5630 Results.push_back(
5631 DAG.makeStateFunctionCall(RTLIB::FESETENV, Ptr, Chain, dl));
5632 break;
5633 }
5634 case ISD::GET_FPENV_MEM: {
5635 SDValue Chain = Node->getOperand(0);
5636 SDValue EnvPtr = Node->getOperand(1);
5637 Results.push_back(
5638 DAG.makeStateFunctionCall(RTLIB::FEGETENV, EnvPtr, Chain, dl));
5639 break;
5640 }
5641 case ISD::SET_FPENV_MEM: {
5642 SDValue Chain = Node->getOperand(0);
5643 SDValue EnvPtr = Node->getOperand(1);
5644 Results.push_back(
5645 DAG.makeStateFunctionCall(RTLIB::FESETENV, EnvPtr, Chain, dl));
5646 break;
5647 }
5648 case ISD::GET_FPMODE: {
5649 // Call fegetmode, which saves control modes into a stack slot. Then load
5650 // the value to return from the stack.
5651 EVT ModeVT = Node->getValueType(0);
5653 int SPFI = cast<FrameIndexSDNode>(StackPtr.getNode())->getIndex();
5654 SDValue Chain = DAG.makeStateFunctionCall(RTLIB::FEGETMODE, StackPtr,
5655 Node->getOperand(0), dl);
5656 SDValue LdInst = DAG.getLoad(
5657 ModeVT, dl, Chain, StackPtr,
5659 Results.push_back(LdInst);
5660 Results.push_back(LdInst.getValue(1));
5661 break;
5662 }
5663 case ISD::SET_FPMODE: {
5664 // Move control modes to stack slot and then call fesetmode with the pointer
5665 // to the slot as argument.
5666 SDValue Mode = Node->getOperand(1);
5667 EVT ModeVT = Mode.getValueType();
5669 int SPFI = cast<FrameIndexSDNode>(StackPtr.getNode())->getIndex();
5670 SDValue StInst = DAG.getStore(
5671 Node->getOperand(0), dl, Mode, StackPtr,
5673 Results.push_back(
5674 DAG.makeStateFunctionCall(RTLIB::FESETMODE, StackPtr, StInst, dl));
5675 break;
5676 }
5677 case ISD::RESET_FPMODE: {
5678 // It is legalized to a call 'fesetmode(FE_DFL_MODE)'. On most targets
5679 // FE_DFL_MODE is defined as '((const femode_t *) -1)' in glibc. If not, the
5680 // target must provide custom lowering.
5681 const DataLayout &DL = DAG.getDataLayout();
5682 EVT PtrTy = TLI.getPointerTy(DL);
5683 SDValue Mode = DAG.getAllOnesConstant(dl, PtrTy);
5684 Results.push_back(DAG.makeStateFunctionCall(RTLIB::FESETMODE, Mode,
5685 Node->getOperand(0), dl));
5686 break;
5687 }
5688 }
5689
5690 // Replace the original node with the legalized result.
5691 if (!Results.empty()) {
5692 LLVM_DEBUG(dbgs() << "Successfully converted node to libcall\n");
5693 ReplaceNode(Node, Results.data());
5694 } else
5695 LLVM_DEBUG(dbgs() << "Could not convert node to libcall\n");
5696}
5697
5698// Determine the vector type to use in place of an original scalar element when
5699// promoting equally sized vectors.
5701 MVT EltVT, MVT NewEltVT) {
5702 unsigned OldEltsPerNewElt = EltVT.getSizeInBits() / NewEltVT.getSizeInBits();
5703 MVT MidVT = OldEltsPerNewElt == 1
5704 ? NewEltVT
5705 : MVT::getVectorVT(NewEltVT, OldEltsPerNewElt);
5706 assert(TLI.isTypeLegal(MidVT) && "unexpected");
5707 return MidVT;
5708}
5709
5710void SelectionDAGLegalize::PromoteNode(SDNode *Node) {
5711 LLVM_DEBUG(dbgs() << "Trying to promote node\n");
5713 MVT OVT = Node->getSimpleValueType(0);
5714 if (Node->getOpcode() == ISD::UINT_TO_FP ||
5715 Node->getOpcode() == ISD::SINT_TO_FP ||
5716 Node->getOpcode() == ISD::SETCC ||
5717 Node->getOpcode() == ISD::EXTRACT_VECTOR_ELT ||
5718 Node->getOpcode() == ISD::INSERT_VECTOR_ELT ||
5719 Node->getOpcode() == ISD::VECREDUCE_FMAX ||
5720 Node->getOpcode() == ISD::VECREDUCE_FMIN ||
5721 Node->getOpcode() == ISD::VECREDUCE_FMAXIMUM ||
5722 Node->getOpcode() == ISD::VECREDUCE_FMINIMUM) {
5723 OVT = Node->getOperand(0).getSimpleValueType();
5724 }
5725 if (Node->getOpcode() == ISD::ATOMIC_STORE ||
5726 Node->getOpcode() == ISD::STRICT_UINT_TO_FP ||
5727 Node->getOpcode() == ISD::STRICT_SINT_TO_FP ||
5728 Node->getOpcode() == ISD::STRICT_FSETCC ||
5729 Node->getOpcode() == ISD::STRICT_FSETCCS ||
5730 Node->getOpcode() == ISD::STRICT_LRINT ||
5731 Node->getOpcode() == ISD::STRICT_LLRINT ||
5732 Node->getOpcode() == ISD::STRICT_LROUND ||
5733 Node->getOpcode() == ISD::STRICT_LLROUND ||
5734 Node->getOpcode() == ISD::VP_REDUCE_FADD ||
5735 Node->getOpcode() == ISD::VP_REDUCE_FMUL ||
5736 Node->getOpcode() == ISD::VP_REDUCE_FMAX ||
5737 Node->getOpcode() == ISD::VP_REDUCE_FMIN ||
5738 Node->getOpcode() == ISD::VP_REDUCE_FMAXIMUM ||
5739 Node->getOpcode() == ISD::VP_REDUCE_FMINIMUM ||
5740 Node->getOpcode() == ISD::VP_REDUCE_SEQ_FADD)
5741 OVT = Node->getOperand(1).getSimpleValueType();
5742 if (Node->getOpcode() == ISD::BR_CC ||
5743 Node->getOpcode() == ISD::SELECT_CC)
5744 OVT = Node->getOperand(2).getSimpleValueType();
5745 // Preserve fast math flags
5746 SDNodeFlags FastMathFlags = Node->getFlags() & SDNodeFlags::FastMathFlags;
5747 SelectionDAG::FlagInserter FlagsInserter(DAG, FastMathFlags);
5748 MVT NVT = TLI.getTypeToPromoteTo(Node->getOpcode(), OVT);
5749 SDLoc dl(Node);
5750 SDValue Tmp1, Tmp2, Tmp3, Tmp4;
5751 switch (Node->getOpcode()) {
5752 case ISD::CTTZ:
5754 case ISD::CTLZ:
5755 case ISD::CTPOP: {
5756 // Zero extend the argument unless its cttz, then use any_extend.
5757 if (Node->getOpcode() == ISD::CTTZ ||
5758 Node->getOpcode() == ISD::CTTZ_ZERO_UNDEF)
5759 Tmp1 = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Node->getOperand(0));
5760 else
5761 Tmp1 = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Node->getOperand(0));
5762
5763 unsigned NewOpc = Node->getOpcode();
5764 if (NewOpc == ISD::CTTZ) {
5765 // The count is the same in the promoted type except if the original
5766 // value was zero. This can be handled by setting the bit just off
5767 // the top of the original type.
5768 auto TopBit = APInt::getOneBitSet(NVT.getSizeInBits(),
5769 OVT.getSizeInBits());
5770 Tmp1 = DAG.getNode(ISD::OR, dl, NVT, Tmp1,
5771 DAG.getConstant(TopBit, dl, NVT));
5772 NewOpc = ISD::CTTZ_ZERO_UNDEF;
5773 }
5774 // Perform the larger operation. For CTPOP and CTTZ_ZERO_UNDEF, this is
5775 // already the correct result.
5776 Tmp1 = DAG.getNode(NewOpc, dl, NVT, Tmp1);
5777 if (NewOpc == ISD::CTLZ) {
5778 // Tmp1 = Tmp1 - (sizeinbits(NVT) - sizeinbits(Old VT))
5779 Tmp1 = DAG.getNode(ISD::SUB, dl, NVT, Tmp1,
5780 DAG.getConstant(NVT.getSizeInBits() -
5781 OVT.getSizeInBits(), dl, NVT));
5782 }
5783 Results.push_back(
5784 DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp1, SDNodeFlags::NoWrap));
5785 break;
5786 }
5787 case ISD::CTLZ_ZERO_UNDEF: {
5788 // We know that the argument is unlikely to be zero, hence we can take a
5789 // different approach as compared to ISD::CTLZ
5790
5791 // Any Extend the argument
5792 auto AnyExtendedNode =
5793 DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Node->getOperand(0));
5794
5795 // Tmp1 = Tmp1 << (sizeinbits(NVT) - sizeinbits(Old VT))
5796 auto ShiftConstant = DAG.getShiftAmountConstant(
5797 NVT.getSizeInBits() - OVT.getSizeInBits(), NVT, dl);
5798 auto LeftShiftResult =
5799 DAG.getNode(ISD::SHL, dl, NVT, AnyExtendedNode, ShiftConstant);
5800
5801 // Perform the larger operation
5802 auto CTLZResult = DAG.getNode(Node->getOpcode(), dl, NVT, LeftShiftResult);
5803 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, CTLZResult));
5804 break;
5805 }
5806 case ISD::BITREVERSE:
5807 case ISD::BSWAP: {
5808 unsigned DiffBits = NVT.getSizeInBits() - OVT.getSizeInBits();
5809 Tmp1 = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Node->getOperand(0));
5810 Tmp1 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1);
5811 Tmp1 = DAG.getNode(ISD::SRL, dl, NVT, Tmp1,
5812 DAG.getShiftAmountConstant(DiffBits, NVT, dl));
5813
5814 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp1));
5815 break;
5816 }
5817 case ISD::FP_TO_UINT:
5819 case ISD::FP_TO_SINT:
5821 PromoteLegalFP_TO_INT(Node, dl, Results);
5822 break;
5825 Results.push_back(PromoteLegalFP_TO_INT_SAT(Node, dl));
5826 break;
5827 case ISD::UINT_TO_FP:
5829 case ISD::SINT_TO_FP:
5831 PromoteLegalINT_TO_FP(Node, dl, Results);
5832 break;
5833 case ISD::VAARG: {
5834 SDValue Chain = Node->getOperand(0); // Get the chain.
5835 SDValue Ptr = Node->getOperand(1); // Get the pointer.
5836
5837 unsigned TruncOp;
5838 if (OVT.isVector()) {
5839 TruncOp = ISD::BITCAST;
5840 } else {
5841 assert(OVT.isInteger()
5842 && "VAARG promotion is supported only for vectors or integer types");
5843 TruncOp = ISD::TRUNCATE;
5844 }
5845
5846 // Perform the larger operation, then convert back
5847 Tmp1 = DAG.getVAArg(NVT, dl, Chain, Ptr, Node->getOperand(2),
5848 Node->getConstantOperandVal(3));
5849 Chain = Tmp1.getValue(1);
5850
5851 Tmp2 = DAG.getNode(TruncOp, dl, OVT, Tmp1);
5852
5853 // Modified the chain result - switch anything that used the old chain to
5854 // use the new one.
5855 DAG.ReplaceAllUsesOfValueWith(SDValue(Node, 0), Tmp2);
5856 DAG.ReplaceAllUsesOfValueWith(SDValue(Node, 1), Chain);
5857 if (UpdatedNodes) {
5858 UpdatedNodes->insert(Tmp2.getNode());
5859 UpdatedNodes->insert(Chain.getNode());
5860 }
5861 ReplacedNode(Node);
5862 break;
5863 }
5864 case ISD::MUL:
5865 case ISD::SDIV:
5866 case ISD::SREM:
5867 case ISD::UDIV:
5868 case ISD::UREM:
5869 case ISD::SMIN:
5870 case ISD::SMAX:
5871 case ISD::UMIN:
5872 case ISD::UMAX:
5873 case ISD::AND:
5874 case ISD::OR:
5875 case ISD::XOR: {
5876 unsigned ExtOp, TruncOp;
5877 if (OVT.isVector()) {
5878 ExtOp = ISD::BITCAST;
5879 TruncOp = ISD::BITCAST;
5880 } else {
5881 assert(OVT.isInteger() && "Cannot promote logic operation");
5882
5883 switch (Node->getOpcode()) {
5884 default:
5885 ExtOp = ISD::ANY_EXTEND;
5886 break;
5887 case ISD::SDIV:
5888 case ISD::SREM:
5889 case ISD::SMIN:
5890 case ISD::SMAX:
5891 ExtOp = ISD::SIGN_EXTEND;
5892 break;
5893 case ISD::UDIV:
5894 case ISD::UREM:
5895 ExtOp = ISD::ZERO_EXTEND;
5896 break;
5897 case ISD::UMIN:
5898 case ISD::UMAX:
5899 if (TLI.isSExtCheaperThanZExt(OVT, NVT))
5900 ExtOp = ISD::SIGN_EXTEND;
5901 else
5902 ExtOp = ISD::ZERO_EXTEND;
5903 break;
5904 }
5905 TruncOp = ISD::TRUNCATE;
5906 }
5907 // Promote each of the values to the new type.
5908 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(0));
5909 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(1));
5910 // Perform the larger operation, then convert back
5911 Tmp1 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1, Tmp2);
5912 Results.push_back(DAG.getNode(TruncOp, dl, OVT, Tmp1));
5913 break;
5914 }
5915 case ISD::UMUL_LOHI:
5916 case ISD::SMUL_LOHI: {
5917 // Promote to a multiply in a wider integer type.
5918 unsigned ExtOp = Node->getOpcode() == ISD::UMUL_LOHI ? ISD::ZERO_EXTEND
5920 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(0));
5921 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(1));
5922 Tmp1 = DAG.getNode(ISD::MUL, dl, NVT, Tmp1, Tmp2);
5923
5924 unsigned OriginalSize = OVT.getScalarSizeInBits();
5925 Tmp2 = DAG.getNode(ISD::SRL, dl, NVT, Tmp1,
5926 DAG.getShiftAmountConstant(OriginalSize, NVT, dl));
5927 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp1));
5928 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp2));
5929 break;
5930 }
5931 case ISD::SELECT: {
5932 unsigned ExtOp, TruncOp;
5933 if (Node->getValueType(0).isVector() ||
5934 Node->getValueType(0).getSizeInBits() == NVT.getSizeInBits()) {
5935 ExtOp = ISD::BITCAST;
5936 TruncOp = ISD::BITCAST;
5937 } else if (Node->getValueType(0).isInteger()) {
5938 ExtOp = ISD::ANY_EXTEND;
5939 TruncOp = ISD::TRUNCATE;
5940 } else {
5941 ExtOp = ISD::FP_EXTEND;
5942 TruncOp = ISD::FP_ROUND;
5943 }
5944 Tmp1 = Node->getOperand(0);
5945 // Promote each of the values to the new type.
5946 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(1));
5947 Tmp3 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(2));
5948 // Perform the larger operation, then round down.
5949 Tmp1 = DAG.getSelect(dl, NVT, Tmp1, Tmp2, Tmp3);
5950 if (TruncOp != ISD::FP_ROUND)
5951 Tmp1 = DAG.getNode(TruncOp, dl, Node->getValueType(0), Tmp1);
5952 else
5953 Tmp1 = DAG.getNode(TruncOp, dl, Node->getValueType(0), Tmp1,
5954 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true));
5955 Results.push_back(Tmp1);
5956 break;
5957 }
5958 case ISD::VECTOR_SHUFFLE: {
5959 ArrayRef<int> Mask = cast<ShuffleVectorSDNode>(Node)->getMask();
5960
5961 // Cast the two input vectors.
5962 Tmp1 = DAG.getNode(ISD::BITCAST, dl, NVT, Node->getOperand(0));
5963 Tmp2 = DAG.getNode(ISD::BITCAST, dl, NVT, Node->getOperand(1));
5964
5965 // Convert the shuffle mask to the right # elements.
5966 Tmp1 = ShuffleWithNarrowerEltType(NVT, OVT, dl, Tmp1, Tmp2, Mask);
5967 Tmp1 = DAG.getNode(ISD::BITCAST, dl, OVT, Tmp1);
5968 Results.push_back(Tmp1);
5969 break;
5970 }
5973 Tmp1 = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Node->getOperand(0));
5974 Tmp2 = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Node->getOperand(1));
5975 Tmp3 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1, Tmp2,
5976 Node->getOperand(2));
5977 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp3));
5978 break;
5979 }
5980 case ISD::SELECT_CC: {
5981 SDValue Cond = Node->getOperand(4);
5982 ISD::CondCode CCCode = cast<CondCodeSDNode>(Cond)->get();
5983 // Type of the comparison operands.
5984 MVT CVT = Node->getSimpleValueType(0);
5985 assert(CVT == OVT && "not handled");
5986
5987 unsigned ExtOp = ISD::FP_EXTEND;
5988 if (NVT.isInteger()) {
5990 }
5991
5992 // Promote the comparison operands, if needed.
5993 if (TLI.isCondCodeLegal(CCCode, CVT)) {
5994 Tmp1 = Node->getOperand(0);
5995 Tmp2 = Node->getOperand(1);
5996 } else {
5997 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(0));
5998 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(1));
5999 }
6000 // Cast the true/false operands.
6001 Tmp3 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(2));
6002 Tmp4 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(3));
6003
6004 Tmp1 = DAG.getNode(ISD::SELECT_CC, dl, NVT, {Tmp1, Tmp2, Tmp3, Tmp4, Cond},
6005 Node->getFlags());
6006
6007 // Cast the result back to the original type.
6008 if (ExtOp != ISD::FP_EXTEND)
6009 Tmp1 = DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp1);
6010 else
6011 Tmp1 = DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp1,
6012 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true));
6013
6014 Results.push_back(Tmp1);
6015 break;
6016 }
6017 case ISD::SETCC:
6018 case ISD::STRICT_FSETCC:
6019 case ISD::STRICT_FSETCCS: {
6020 unsigned ExtOp = ISD::FP_EXTEND;
6021 if (NVT.isInteger()) {
6022 ISD::CondCode CCCode = cast<CondCodeSDNode>(Node->getOperand(2))->get();
6023 if (isSignedIntSetCC(CCCode) ||
6024 TLI.isSExtCheaperThanZExt(Node->getOperand(0).getValueType(), NVT))
6025 ExtOp = ISD::SIGN_EXTEND;
6026 else
6027 ExtOp = ISD::ZERO_EXTEND;
6028 }
6029 if (Node->isStrictFPOpcode()) {
6030 SDValue InChain = Node->getOperand(0);
6031 std::tie(Tmp1, std::ignore) =
6032 DAG.getStrictFPExtendOrRound(Node->getOperand(1), InChain, dl, NVT);
6033 std::tie(Tmp2, std::ignore) =
6034 DAG.getStrictFPExtendOrRound(Node->getOperand(2), InChain, dl, NVT);
6035 SmallVector<SDValue, 2> TmpChains = {Tmp1.getValue(1), Tmp2.getValue(1)};
6036 SDValue OutChain = DAG.getTokenFactor(dl, TmpChains);
6037 SDVTList VTs = DAG.getVTList(Node->getValueType(0), MVT::Other);
6038 Results.push_back(DAG.getNode(Node->getOpcode(), dl, VTs,
6039 {OutChain, Tmp1, Tmp2, Node->getOperand(3)},
6040 Node->getFlags()));
6041 Results.push_back(Results.back().getValue(1));
6042 break;
6043 }
6044 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(0));
6045 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(1));
6046 Results.push_back(DAG.getNode(ISD::SETCC, dl, Node->getValueType(0), Tmp1,
6047 Tmp2, Node->getOperand(2), Node->getFlags()));
6048 break;
6049 }
6050 case ISD::BR_CC: {
6051 unsigned ExtOp = ISD::FP_EXTEND;
6052 if (NVT.isInteger()) {
6053 ISD::CondCode CCCode =
6054 cast<CondCodeSDNode>(Node->getOperand(1))->get();
6056 }
6057 Tmp1 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(2));
6058 Tmp2 = DAG.getNode(ExtOp, dl, NVT, Node->getOperand(3));
6059 Results.push_back(DAG.getNode(ISD::BR_CC, dl, Node->getValueType(0),
6060 Node->getOperand(0), Node->getOperand(1),
6061 Tmp1, Tmp2, Node->getOperand(4)));
6062 break;
6063 }
6064 case ISD::FADD:
6065 case ISD::FSUB:
6066 case ISD::FMUL:
6067 case ISD::FDIV:
6068 case ISD::FREM:
6069 case ISD::FMINNUM:
6070 case ISD::FMAXNUM:
6071 case ISD::FMINIMUM:
6072 case ISD::FMAXIMUM:
6073 case ISD::FMINIMUMNUM:
6074 case ISD::FMAXIMUMNUM:
6075 case ISD::FPOW:
6076 case ISD::FATAN2:
6077 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6078 Tmp2 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(1));
6079 Tmp3 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1, Tmp2);
6080 Results.push_back(
6081 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp3,
6082 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)));
6083 break;
6084
6086 case ISD::STRICT_FMAXIMUM: {
6087 SDValue InChain = Node->getOperand(0);
6088 SDVTList VTs = DAG.getVTList(NVT, MVT::Other);
6089 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, VTs, InChain,
6090 Node->getOperand(1));
6091 Tmp2 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, VTs, InChain,
6092 Node->getOperand(2));
6093 SmallVector<SDValue, 4> Ops = {InChain, Tmp1, Tmp2};
6094 Tmp3 = DAG.getNode(Node->getOpcode(), dl, VTs, Ops, Node->getFlags());
6095 Tmp4 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, DAG.getVTList(OVT, MVT::Other),
6096 InChain, Tmp3,
6097 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true));
6098 Results.push_back(Tmp4);
6099 Results.push_back(Tmp4.getValue(1));
6100 break;
6101 }
6102
6103 case ISD::STRICT_FADD:
6104 case ISD::STRICT_FSUB:
6105 case ISD::STRICT_FMUL:
6106 case ISD::STRICT_FDIV:
6109 case ISD::STRICT_FREM:
6110 case ISD::STRICT_FPOW:
6111 case ISD::STRICT_FATAN2:
6112 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6113 {Node->getOperand(0), Node->getOperand(1)});
6114 Tmp2 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6115 {Node->getOperand(0), Node->getOperand(2)});
6116 Tmp3 = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Tmp1.getValue(1),
6117 Tmp2.getValue(1));
6118 Tmp1 = DAG.getNode(Node->getOpcode(), dl, {NVT, MVT::Other},
6119 {Tmp3, Tmp1, Tmp2});
6120 Tmp1 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, {OVT, MVT::Other},
6121 {Tmp1.getValue(1), Tmp1,
6122 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)});
6123 Results.push_back(Tmp1);
6124 Results.push_back(Tmp1.getValue(1));
6125 break;
6126 case ISD::FMA:
6127 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6128 Tmp2 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(1));
6129 Tmp3 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(2));
6130 Results.push_back(
6131 DAG.getNode(ISD::FP_ROUND, dl, OVT,
6132 DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1, Tmp2, Tmp3),
6133 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)));
6134 break;
6135 case ISD::STRICT_FMA:
6136 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6137 {Node->getOperand(0), Node->getOperand(1)});
6138 Tmp2 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6139 {Node->getOperand(0), Node->getOperand(2)});
6140 Tmp3 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6141 {Node->getOperand(0), Node->getOperand(3)});
6142 Tmp4 = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Tmp1.getValue(1),
6143 Tmp2.getValue(1), Tmp3.getValue(1));
6144 Tmp4 = DAG.getNode(Node->getOpcode(), dl, {NVT, MVT::Other},
6145 {Tmp4, Tmp1, Tmp2, Tmp3});
6146 Tmp4 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, {OVT, MVT::Other},
6147 {Tmp4.getValue(1), Tmp4,
6148 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)});
6149 Results.push_back(Tmp4);
6150 Results.push_back(Tmp4.getValue(1));
6151 break;
6152 case ISD::FCOPYSIGN:
6153 case ISD::FLDEXP:
6154 case ISD::FPOWI: {
6155 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6156 Tmp2 = Node->getOperand(1);
6157 Tmp3 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1, Tmp2);
6158
6159 // fcopysign doesn't change anything but the sign bit, so
6160 // (fp_round (fcopysign (fpext a), b))
6161 // is as precise as
6162 // (fp_round (fpext a))
6163 // which is a no-op. Mark it as a TRUNCating FP_ROUND.
6164 const bool isTrunc = (Node->getOpcode() == ISD::FCOPYSIGN);
6165 Results.push_back(
6166 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp3,
6167 DAG.getIntPtrConstant(isTrunc, dl, /*isTarget=*/true)));
6168 break;
6169 }
6170 case ISD::STRICT_FLDEXP: {
6171 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6172 {Node->getOperand(0), Node->getOperand(1)});
6173 Tmp2 = Node->getOperand(2);
6174 Tmp3 = DAG.getNode(ISD::STRICT_FLDEXP, dl, {NVT, MVT::Other},
6175 {Tmp1.getValue(1), Tmp1, Tmp2});
6176 Tmp4 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, {OVT, MVT::Other},
6177 {Tmp3.getValue(1), Tmp3,
6178 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)});
6179 Results.push_back(Tmp4);
6180 Results.push_back(Tmp4.getValue(1));
6181 break;
6182 }
6183 case ISD::STRICT_FPOWI:
6184 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6185 {Node->getOperand(0), Node->getOperand(1)});
6186 Tmp2 = DAG.getNode(Node->getOpcode(), dl, {NVT, MVT::Other},
6187 {Tmp1.getValue(1), Tmp1, Node->getOperand(2)});
6188 Tmp3 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, {OVT, MVT::Other},
6189 {Tmp2.getValue(1), Tmp2,
6190 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)});
6191 Results.push_back(Tmp3);
6192 Results.push_back(Tmp3.getValue(1));
6193 break;
6194 case ISD::FFREXP: {
6195 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6196 Tmp2 = DAG.getNode(ISD::FFREXP, dl, {NVT, Node->getValueType(1)}, Tmp1);
6197
6198 Results.push_back(
6199 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp2,
6200 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)));
6201
6202 Results.push_back(Tmp2.getValue(1));
6203 break;
6204 }
6205 case ISD::FMODF:
6206 case ISD::FSINCOS:
6207 case ISD::FSINCOSPI: {
6208 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6209 Tmp2 = DAG.getNode(Node->getOpcode(), dl, DAG.getVTList(NVT, NVT), Tmp1);
6210 Tmp3 = DAG.getIntPtrConstant(0, dl, /*isTarget=*/true);
6211 for (unsigned ResNum = 0; ResNum < Node->getNumValues(); ResNum++)
6212 Results.push_back(
6213 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp2.getValue(ResNum), Tmp3));
6214 break;
6215 }
6216 case ISD::FFLOOR:
6217 case ISD::FCEIL:
6218 case ISD::FRINT:
6219 case ISD::FNEARBYINT:
6220 case ISD::FROUND:
6221 case ISD::FROUNDEVEN:
6222 case ISD::FTRUNC:
6223 case ISD::FNEG:
6224 case ISD::FSQRT:
6225 case ISD::FSIN:
6226 case ISD::FCOS:
6227 case ISD::FTAN:
6228 case ISD::FASIN:
6229 case ISD::FACOS:
6230 case ISD::FATAN:
6231 case ISD::FSINH:
6232 case ISD::FCOSH:
6233 case ISD::FTANH:
6234 case ISD::FLOG:
6235 case ISD::FLOG2:
6236 case ISD::FLOG10:
6237 case ISD::FABS:
6238 case ISD::FEXP:
6239 case ISD::FEXP2:
6240 case ISD::FEXP10:
6241 case ISD::FCANONICALIZE:
6242 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6243 Tmp2 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1);
6244 Results.push_back(
6245 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp2,
6246 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)));
6247 break;
6248 case ISD::STRICT_FFLOOR:
6249 case ISD::STRICT_FCEIL:
6250 case ISD::STRICT_FRINT:
6252 case ISD::STRICT_FROUND:
6254 case ISD::STRICT_FTRUNC:
6255 case ISD::STRICT_FSQRT:
6256 case ISD::STRICT_FSIN:
6257 case ISD::STRICT_FCOS:
6258 case ISD::STRICT_FTAN:
6259 case ISD::STRICT_FASIN:
6260 case ISD::STRICT_FACOS:
6261 case ISD::STRICT_FATAN:
6262 case ISD::STRICT_FSINH:
6263 case ISD::STRICT_FCOSH:
6264 case ISD::STRICT_FTANH:
6265 case ISD::STRICT_FLOG:
6266 case ISD::STRICT_FLOG2:
6267 case ISD::STRICT_FLOG10:
6268 case ISD::STRICT_FEXP:
6269 case ISD::STRICT_FEXP2:
6270 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6271 {Node->getOperand(0), Node->getOperand(1)});
6272 Tmp2 = DAG.getNode(Node->getOpcode(), dl, {NVT, MVT::Other},
6273 {Tmp1.getValue(1), Tmp1});
6274 Tmp3 = DAG.getNode(ISD::STRICT_FP_ROUND, dl, {OVT, MVT::Other},
6275 {Tmp2.getValue(1), Tmp2,
6276 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)});
6277 Results.push_back(Tmp3);
6278 Results.push_back(Tmp3.getValue(1));
6279 break;
6280 case ISD::LLROUND:
6281 case ISD::LROUND:
6282 case ISD::LRINT:
6283 case ISD::LLRINT:
6284 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NVT, Node->getOperand(0));
6285 Tmp2 = DAG.getNode(Node->getOpcode(), dl, Node->getValueType(0), Tmp1);
6286 Results.push_back(Tmp2);
6287 break;
6289 case ISD::STRICT_LROUND:
6290 case ISD::STRICT_LRINT:
6291 case ISD::STRICT_LLRINT:
6292 Tmp1 = DAG.getNode(ISD::STRICT_FP_EXTEND, dl, {NVT, MVT::Other},
6293 {Node->getOperand(0), Node->getOperand(1)});
6294 Tmp2 = DAG.getNode(Node->getOpcode(), dl, {NVT, MVT::Other},
6295 {Tmp1.getValue(1), Tmp1});
6296 Results.push_back(Tmp2);
6297 Results.push_back(Tmp2.getValue(1));
6298 break;
6299 case ISD::BUILD_VECTOR: {
6300 MVT EltVT = OVT.getVectorElementType();
6301 MVT NewEltVT = NVT.getVectorElementType();
6302
6303 // Handle bitcasts to a different vector type with the same total bit size
6304 //
6305 // e.g. v2i64 = build_vector i64:x, i64:y => v4i32
6306 // =>
6307 // v4i32 = concat_vectors (v2i32 (bitcast i64:x)), (v2i32 (bitcast i64:y))
6308
6309 assert(NVT.isVector() && OVT.getSizeInBits() == NVT.getSizeInBits() &&
6310 "Invalid promote type for build_vector");
6311 assert(NewEltVT.bitsLE(EltVT) && "not handled");
6312
6313 MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
6314
6316 for (const SDValue &Op : Node->op_values())
6317 NewOps.push_back(DAG.getNode(ISD::BITCAST, SDLoc(Op), MidVT, Op));
6318
6319 SDLoc SL(Node);
6320 SDValue Concat =
6321 DAG.getNode(MidVT == NewEltVT ? ISD::BUILD_VECTOR : ISD::CONCAT_VECTORS,
6322 SL, NVT, NewOps);
6323 SDValue CvtVec = DAG.getNode(ISD::BITCAST, SL, OVT, Concat);
6324 Results.push_back(CvtVec);
6325 break;
6326 }
6328 MVT EltVT = OVT.getVectorElementType();
6329 MVT NewEltVT = NVT.getVectorElementType();
6330
6331 // Handle bitcasts to a different vector type with the same total bit size.
6332 //
6333 // e.g. v2i64 = extract_vector_elt x:v2i64, y:i32
6334 // =>
6335 // v4i32:castx = bitcast x:v2i64
6336 //
6337 // i64 = bitcast
6338 // (v2i32 build_vector (i32 (extract_vector_elt castx, (2 * y))),
6339 // (i32 (extract_vector_elt castx, (2 * y + 1)))
6340 //
6341
6342 assert(NVT.isVector() && OVT.getSizeInBits() == NVT.getSizeInBits() &&
6343 "Invalid promote type for extract_vector_elt");
6344 assert(NewEltVT.bitsLT(EltVT) && "not handled");
6345
6346 MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
6347 unsigned NewEltsPerOldElt = MidVT.getVectorNumElements();
6348
6349 SDValue Idx = Node->getOperand(1);
6350 EVT IdxVT = Idx.getValueType();
6351 SDLoc SL(Node);
6352 SDValue Factor = DAG.getConstant(NewEltsPerOldElt, SL, IdxVT);
6353 SDValue NewBaseIdx = DAG.getNode(ISD::MUL, SL, IdxVT, Idx, Factor);
6354
6355 SDValue CastVec = DAG.getNode(ISD::BITCAST, SL, NVT, Node->getOperand(0));
6356
6358 for (unsigned I = 0; I < NewEltsPerOldElt; ++I) {
6359 SDValue IdxOffset = DAG.getConstant(I, SL, IdxVT);
6360 SDValue TmpIdx = DAG.getNode(ISD::ADD, SL, IdxVT, NewBaseIdx, IdxOffset);
6361
6362 SDValue Elt = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, SL, NewEltVT,
6363 CastVec, TmpIdx);
6364 NewOps.push_back(Elt);
6365 }
6366
6367 SDValue NewVec = DAG.getBuildVector(MidVT, SL, NewOps);
6368 Results.push_back(DAG.getNode(ISD::BITCAST, SL, EltVT, NewVec));
6369 break;
6370 }
6372 MVT EltVT = OVT.getVectorElementType();
6373 MVT NewEltVT = NVT.getVectorElementType();
6374
6375 // Handle bitcasts to a different vector type with the same total bit size
6376 //
6377 // e.g. v2i64 = insert_vector_elt x:v2i64, y:i64, z:i32
6378 // =>
6379 // v4i32:castx = bitcast x:v2i64
6380 // v2i32:casty = bitcast y:i64
6381 //
6382 // v2i64 = bitcast
6383 // (v4i32 insert_vector_elt
6384 // (v4i32 insert_vector_elt v4i32:castx,
6385 // (extract_vector_elt casty, 0), 2 * z),
6386 // (extract_vector_elt casty, 1), (2 * z + 1))
6387
6388 assert(NVT.isVector() && OVT.getSizeInBits() == NVT.getSizeInBits() &&
6389 "Invalid promote type for insert_vector_elt");
6390 assert(NewEltVT.bitsLT(EltVT) && "not handled");
6391
6392 MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
6393 unsigned NewEltsPerOldElt = MidVT.getVectorNumElements();
6394
6395 SDValue Val = Node->getOperand(1);
6396 SDValue Idx = Node->getOperand(2);
6397 EVT IdxVT = Idx.getValueType();
6398 SDLoc SL(Node);
6399
6400 SDValue Factor = DAG.getConstant(NewEltsPerOldElt, SDLoc(), IdxVT);
6401 SDValue NewBaseIdx = DAG.getNode(ISD::MUL, SL, IdxVT, Idx, Factor);
6402
6403 SDValue CastVec = DAG.getNode(ISD::BITCAST, SL, NVT, Node->getOperand(0));
6404 SDValue CastVal = DAG.getNode(ISD::BITCAST, SL, MidVT, Val);
6405
6406 SDValue NewVec = CastVec;
6407 for (unsigned I = 0; I < NewEltsPerOldElt; ++I) {
6408 SDValue IdxOffset = DAG.getConstant(I, SL, IdxVT);
6409 SDValue InEltIdx = DAG.getNode(ISD::ADD, SL, IdxVT, NewBaseIdx, IdxOffset);
6410
6411 SDValue Elt = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, SL, NewEltVT,
6412 CastVal, IdxOffset);
6413
6414 NewVec = DAG.getNode(ISD::INSERT_VECTOR_ELT, SL, NVT,
6415 NewVec, Elt, InEltIdx);
6416 }
6417
6418 Results.push_back(DAG.getNode(ISD::BITCAST, SL, OVT, NewVec));
6419 break;
6420 }
6421 case ISD::SCALAR_TO_VECTOR: {
6422 MVT EltVT = OVT.getVectorElementType();
6423 MVT NewEltVT = NVT.getVectorElementType();
6424
6425 // Handle bitcasts to different vector type with the same total bit size.
6426 //
6427 // e.g. v2i64 = scalar_to_vector x:i64
6428 // =>
6429 // concat_vectors (v2i32 bitcast x:i64), (v2i32 undef)
6430 //
6431
6432 MVT MidVT = getPromotedVectorElementType(TLI, EltVT, NewEltVT);
6433 SDValue Val = Node->getOperand(0);
6434 SDLoc SL(Node);
6435
6436 SDValue CastVal = DAG.getNode(ISD::BITCAST, SL, MidVT, Val);
6437 SDValue Undef = DAG.getUNDEF(MidVT);
6438
6440 NewElts.push_back(CastVal);
6441 for (unsigned I = 1, NElts = OVT.getVectorNumElements(); I != NElts; ++I)
6442 NewElts.push_back(Undef);
6443
6444 SDValue Concat = DAG.getNode(ISD::CONCAT_VECTORS, SL, NVT, NewElts);
6445 SDValue CvtVec = DAG.getNode(ISD::BITCAST, SL, OVT, Concat);
6446 Results.push_back(CvtVec);
6447 break;
6448 }
6449 case ISD::ATOMIC_SWAP:
6450 case ISD::ATOMIC_STORE: {
6451 AtomicSDNode *AM = cast<AtomicSDNode>(Node);
6452 SDLoc SL(Node);
6453 SDValue CastVal = DAG.getNode(ISD::BITCAST, SL, NVT, AM->getVal());
6454 assert(NVT.getSizeInBits() == OVT.getSizeInBits() &&
6455 "unexpected promotion type");
6456 assert(AM->getMemoryVT().getSizeInBits() == NVT.getSizeInBits() &&
6457 "unexpected atomic_swap with illegal type");
6458
6459 SDValue Op0 = AM->getBasePtr();
6460 SDValue Op1 = CastVal;
6461
6462 // ATOMIC_STORE uses a swapped operand order from every other AtomicSDNode,
6463 // but really it should merge with ISD::STORE.
6464 if (AM->getOpcode() == ISD::ATOMIC_STORE)
6465 std::swap(Op0, Op1);
6466
6467 SDValue NewAtomic = DAG.getAtomic(AM->getOpcode(), SL, NVT, AM->getChain(),
6468 Op0, Op1, AM->getMemOperand());
6469
6470 if (AM->getOpcode() != ISD::ATOMIC_STORE) {
6471 Results.push_back(DAG.getNode(ISD::BITCAST, SL, OVT, NewAtomic));
6472 Results.push_back(NewAtomic.getValue(1));
6473 } else
6474 Results.push_back(NewAtomic);
6475 break;
6476 }
6477 case ISD::ATOMIC_LOAD: {
6478 AtomicSDNode *AM = cast<AtomicSDNode>(Node);
6479 SDLoc SL(Node);
6480 assert(NVT.getSizeInBits() == OVT.getSizeInBits() &&
6481 "unexpected promotion type");
6482 assert(AM->getMemoryVT().getSizeInBits() == NVT.getSizeInBits() &&
6483 "unexpected atomic_load with illegal type");
6484
6485 SDValue NewAtomic =
6486 DAG.getAtomic(ISD::ATOMIC_LOAD, SL, NVT, DAG.getVTList(NVT, MVT::Other),
6487 {AM->getChain(), AM->getBasePtr()}, AM->getMemOperand());
6488 Results.push_back(DAG.getNode(ISD::BITCAST, SL, OVT, NewAtomic));
6489 Results.push_back(NewAtomic.getValue(1));
6490 break;
6491 }
6492 case ISD::SPLAT_VECTOR: {
6493 SDValue Scalar = Node->getOperand(0);
6494 MVT ScalarType = Scalar.getSimpleValueType();
6495 MVT NewScalarType = NVT.getVectorElementType();
6496 if (ScalarType.isInteger()) {
6497 Tmp1 = DAG.getNode(ISD::ANY_EXTEND, dl, NewScalarType, Scalar);
6498 Tmp2 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1);
6499 Results.push_back(DAG.getNode(ISD::TRUNCATE, dl, OVT, Tmp2));
6500 break;
6501 }
6502 Tmp1 = DAG.getNode(ISD::FP_EXTEND, dl, NewScalarType, Scalar);
6503 Tmp2 = DAG.getNode(Node->getOpcode(), dl, NVT, Tmp1);
6504 Results.push_back(
6505 DAG.getNode(ISD::FP_ROUND, dl, OVT, Tmp2,
6506 DAG.getIntPtrConstant(0, dl, /*isTarget=*/true)));
6507 break;
6508 }
6513 case ISD::VP_REDUCE_FMAX:
6514 case ISD::VP_REDUCE_FMIN:
6515 case ISD::VP_REDUCE_FMAXIMUM:
6516 case ISD::VP_REDUCE_FMINIMUM:
6517 Results.push_back(PromoteReduction(Node));
6518 break;
6519 }
6520
6521 // Replace the original node with the legalized result.
6522 if (!Results.empty()) {
6523 LLVM_DEBUG(dbgs() << "Successfully promoted node\n");
6524 ReplaceNode(Node, Results.data());
6525 } else
6526 LLVM_DEBUG(dbgs() << "Could not promote node\n");
6527}
6528
6529/// This is the entry point for the file.
6532
6533 SmallPtrSet<SDNode *, 16> LegalizedNodes;
6534 // Use a delete listener to remove nodes which were deleted during
6535 // legalization from LegalizeNodes. This is needed to handle the situation
6536 // where a new node is allocated by the object pool to the same address of a
6537 // previously deleted node.
6538 DAGNodeDeletedListener DeleteListener(
6539 *this,
6540 [&LegalizedNodes](SDNode *N, SDNode *E) { LegalizedNodes.erase(N); });
6541
6542 SelectionDAGLegalize Legalizer(*this, LegalizedNodes);
6543
6544 // Visit all the nodes. We start in topological order, so that we see
6545 // nodes with their original operands intact. Legalization can produce
6546 // new nodes which may themselves need to be legalized. Iterate until all
6547 // nodes have been legalized.
6548 while (true) {
6549 bool AnyLegalized = false;
6550 for (auto NI = allnodes_end(); NI != allnodes_begin();) {
6551 --NI;
6552
6553 SDNode *N = &*NI;
6554 if (N->use_empty() && N != getRoot().getNode()) {
6555 ++NI;
6556 DeleteNode(N);
6557 continue;
6558 }
6559
6560 if (LegalizedNodes.insert(N).second) {
6561 AnyLegalized = true;
6562 Legalizer.LegalizeOp(N);
6563
6564 if (N->use_empty() && N != getRoot().getNode()) {
6565 ++NI;
6566 DeleteNode(N);
6567 }
6568 }
6569 }
6570 if (!AnyLegalized)
6571 break;
6572
6573 }
6574
6575 // Remove dead nodes now.
6577}
6578
6580 SmallSetVector<SDNode *, 16> &UpdatedNodes) {
6581 SmallPtrSet<SDNode *, 16> LegalizedNodes;
6582 SelectionDAGLegalize Legalizer(*this, LegalizedNodes, &UpdatedNodes);
6583
6584 // Directly insert the node in question, and legalize it. This will recurse
6585 // as needed through operands.
6586 LegalizedNodes.insert(N);
6587 Legalizer.LegalizeOp(N);
6588
6589 return LegalizedNodes.count(N);
6590}
#define Success
aarch64 falkor hwpf fix Falkor HW Prefetch Fix Late Phase
return SDValue()
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static msgpack::DocNode getNode(msgpack::DocNode DN, msgpack::Type Type, MCValue Val)
static bool isConstant(const MachineInstr &MI)
This file declares a class to represent arbitrary precision floating point values and provide a varie...
This file implements a class to represent arbitrary precision integral constant values and operations...
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Function Alias Analysis Results
#define X(NUM, ENUM, NAME)
Definition ELF.h:849
This file contains the declarations for the subclasses of Constant, which represent the different fla...
DXIL Legalizer
Utilities for dealing with flags related to floating point properties and mode controls.
static MaybeAlign getAlign(Value *Ptr)
const AbstractManglingParser< Derived, Alloc >::OperatorInfo AbstractManglingParser< Derived, Alloc >::Ops[]
static bool ExpandBVWithShuffles(SDNode *Node, SelectionDAG &DAG, const TargetLowering &TLI, SDValue &Res)
static bool isSinCosLibcallAvailable(SDNode *Node, const LibcallLoweringInfo &Libcalls)
Return true if sincos or __sincos_stret libcall is available.
static bool useSinCos(SDNode *Node)
Only issue sincos libcall if both sin and cos are needed.
static bool canUseFastMathLibcall(const SDNode *Node)
Return if we can use the FAST_* variant of a math libcall for the node.
static MachineMemOperand * getStackAlignedMMO(SDValue StackPtr, MachineFunction &MF, bool isObjectScalable)
static MVT getPromotedVectorElementType(const TargetLowering &TLI, MVT EltVT, MVT NewEltVT)
#define F(x, y, z)
Definition MD5.cpp:54
#define I(x, y, z)
Definition MD5.cpp:57
std::pair< MCSymbol *, MachineModuleInfoImpl::StubValueTy > PairTy
Promote Memory to Register
Definition Mem2Reg.cpp:110
This file contains the declarations for metadata subclasses.
PowerPC Reduce CR logical Operation
static constexpr MCPhysReg SPReg
const SmallVectorImpl< MachineOperand > & Cond
static cl::opt< RegAllocEvictionAdvisorAnalysisLegacy::AdvisorMode > Mode("regalloc-enable-advisor", cl::Hidden, cl::init(RegAllocEvictionAdvisorAnalysisLegacy::AdvisorMode::Default), cl::desc("Enable regalloc advisor mode"), cl::values(clEnumValN(RegAllocEvictionAdvisorAnalysisLegacy::AdvisorMode::Default, "default", "Default"), clEnumValN(RegAllocEvictionAdvisorAnalysisLegacy::AdvisorMode::Release, "release", "precompiled"), clEnumValN(RegAllocEvictionAdvisorAnalysisLegacy::AdvisorMode::Development, "development", "for training")))
This file implements a set that has insertion order iteration characteristics.
This file defines the SmallPtrSet class.
This file defines the SmallSet class.
This file defines the SmallVector class.
#define LLVM_DEBUG(...)
Definition Debug.h:114
This file describes how to lower LLVM code to machine code.
static constexpr int Concat[]
Value * RHS
Value * LHS
BinaryOperator * Mul
static LLVM_ABI const llvm::fltSemantics & EnumToSemantics(Semantics S)
Definition APFloat.cpp:98
bool isSignaling() const
Definition APFloat.h:1518
static APFloat getSmallestNormalized(const fltSemantics &Sem, bool Negative=false)
Returns the smallest (by magnitude) normalized finite number in the given semantics.
Definition APFloat.h:1213
APInt bitcastToAPInt() const
Definition APFloat.h:1408
static APFloat getInf(const fltSemantics &Sem, bool Negative=false)
Factory for Positive and Negative Infinity.
Definition APFloat.h:1153
Class for arbitrary precision integers.
Definition APInt.h:78
static APInt getSignMask(unsigned BitWidth)
Get the SignMask for a specific bit width.
Definition APInt.h:230
void setBit(unsigned BitPosition)
Set the given bit to 1 whose position is given as "bitPosition".
Definition APInt.h:1345
static APInt getBitsSet(unsigned numBits, unsigned loBit, unsigned hiBit)
Get a value with a block of bits set.
Definition APInt.h:259
static APInt getSignedMaxValue(unsigned numBits)
Gets maximum signed value of APInt for a specific bit width.
Definition APInt.h:210
static APInt getOneBitSet(unsigned numBits, unsigned BitNo)
Return an APInt with exactly one bit set in the result.
Definition APInt.h:240
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
const SDValue & getBasePtr() const
const SDValue & getVal() const
LLVM_ABI Type * getStructRetType() const
static LLVM_ABI bool isValueValidForType(EVT VT, const APFloat &Val)
const APFloat & getValueAPF() const
const ConstantFP * getConstantFPValue() const
const APFloat & getValueAPF() const
Definition Constants.h:463
uint64_t getZExtValue() const
Return the constant as a 64-bit unsigned integer value after it has been zero extended as appropriate...
Definition Constants.h:168
const ConstantInt * getConstantIntValue() const
static LLVM_ABI Constant * get(ArrayRef< Constant * > V)
bool isLittleEndian() const
Layout endianness...
Definition DataLayout.h:215
bool isBigEndian() const
Definition DataLayout.h:216
unsigned getAllocaAddrSpace() const
Definition DataLayout.h:250
LLVM_ABI Align getPrefTypeAlign(Type *Ty) const
Returns the preferred stack/global alignment for the specified type.
bool empty() const
Definition Function.h:859
const BasicBlock & back() const
Definition Function.h:862
LLVM_ABI void emitError(const Instruction *I, const Twine &ErrorStr)
emitError - Emit an error message to the currently installed error handler with optional location inf...
LLVM_ABI void diagnose(const DiagnosticInfo &DI)
Report a message to the currently installed diagnostic handler.
Tracks which library functions to use for a particular subtarget.
LLVM_ABI CallingConv::ID getLibcallImplCallingConv(RTLIB::LibcallImpl Call) const
Get the CallingConv that should be used for the specified libcall.
LLVM_ABI RTLIB::LibcallImpl getLibcallImpl(RTLIB::Libcall Call) const
Return the lowering's selection of implementation call for Call.
static LocationSize precise(uint64_t Value)
static constexpr LocationSize beforeOrAfterPointer()
Any location before or after the base pointer (but still within the underlying object).
Machine Value Type.
SimpleValueType SimpleTy
uint64_t getScalarSizeInBits() const
bool bitsLE(MVT VT) const
Return true if this has no more bits than VT.
unsigned getVectorNumElements() const
bool isVector() const
Return true if this is a vector value type.
bool isInteger() const
Return true if this is an integer or a vector integer type.
bool bitsLT(MVT VT) const
Return true if this has less bits than VT.
TypeSize getSizeInBits() const
Returns the size of the specified MVT in bits.
static MVT getVectorVT(MVT VT, unsigned NumElements)
MVT getVectorElementType() const
bool isFloatingPoint() const
Return true if this is a FP or a vector FP type.
LLVM_ABI int CreateStackObject(uint64_t Size, Align Alignment, bool isSpillSlot, const AllocaInst *Alloca=nullptr, uint8_t ID=0)
Create a new statically sized stack object, returning a nonnegative identifier to represent it.
Align getObjectAlign(int ObjectIdx) const
Return the alignment of the specified stack object.
MachineMemOperand * getMachineMemOperand(MachinePointerInfo PtrInfo, MachineMemOperand::Flags f, LLT MemTy, Align base_alignment, const AAMDNodes &AAInfo=AAMDNodes(), const MDNode *Ranges=nullptr, SyncScope::ID SSID=SyncScope::System, AtomicOrdering Ordering=AtomicOrdering::NotAtomic, AtomicOrdering FailureOrdering=AtomicOrdering::NotAtomic)
getMachineMemOperand - Allocate a new MachineMemOperand.
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
Function & getFunction()
Return the LLVM function that this machine code represents.
const MachineJumpTableInfo * getJumpTableInfo() const
getJumpTableInfo - Return the jump table info object for the current function.
LLVM_ABI unsigned getEntrySize(const DataLayout &TD) const
getEntrySize - Return the size of each entry in the jump table.
A description of a memory reference used in the backend.
Flags
Flags values. These may be or'd together.
@ MOStore
The memory access writes data.
MachineMemOperand * getMemOperand() const
Return the unique MachineMemOperand object describing the memory reference performed by operation.
const SDValue & getChain() const
EVT getMemoryVT() const
Return the type of the in-memory value.
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
const DebugLoc & getDebugLoc() const
Represents one node in the SelectionDAG.
bool isStrictFPOpcode()
Test if this node is a strict floating point pseudo-op.
ArrayRef< SDUse > ops() const
LLVM_ABI void dump() const
Dump this node, for debugging.
unsigned getOpcode() const
Return the SelectionDAG opcode value for this node.
static bool hasPredecessorHelper(const SDNode *N, SmallPtrSetImpl< const SDNode * > &Visited, SmallVectorImpl< const SDNode * > &Worklist, unsigned int MaxSteps=0, bool TopologicalPrune=false)
Returns true if N is a predecessor of any node in Worklist.
unsigned getNumValues() const
Return the number of values defined/returned by this operator.
const SDValue & getOperand(unsigned Num) const
EVT getValueType(unsigned ResNo) const
Return the type of a specified result.
iterator_range< user_iterator > users()
Unlike LLVM values, Selection DAG nodes may return multiple values as the result of a computation.
bool isUndef() const
SDNode * getNode() const
get the SDNode which holds the desired result
SDValue getValue(unsigned R) const
EVT getValueType() const
Return the ValueType of the referenced return value.
const SDValue & getOperand(unsigned i) const
uint64_t getScalarValueSizeInBits() const
unsigned getResNo() const
get the index which selects a specific result in the SDNode
MVT getSimpleValueType() const
Return the simple ValueType of the referenced return value.
unsigned getOpcode() const
This is used to represent a portion of an LLVM function in a low-level Data Dependence DAG representa...
LLVM_ABI SDValue getShiftAmountOperand(EVT LHSTy, SDValue Op)
Return the specified value casted to the target's desired shift amount type.
LLVM_ABI 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())
const SDValue & getRoot() const
Return the root tag of the SelectionDAG.
bool isKnownNeverSNaN(SDValue Op, const APInt &DemandedElts, unsigned Depth=0) const
const TargetSubtargetInfo & getSubtarget() const
SDValue getCopyToReg(SDValue Chain, const SDLoc &dl, Register Reg, SDValue N)
LLVM_ABI SDValue getMergeValues(ArrayRef< SDValue > Ops, const SDLoc &dl)
Create a MERGE_VALUES node from the given operands.
LLVM_ABI SDVTList getVTList(EVT VT)
Return an SDVTList that represents the list of values specified.
LLVM_ABI SDValue getShiftAmountConstant(uint64_t Val, EVT VT, const SDLoc &DL)
LLVM_ABI SDValue getAllOnesConstant(const SDLoc &DL, EVT VT, bool IsTarget=false, bool IsOpaque=false)
LLVM_ABI SDValue getFreeze(SDValue V)
Return a freeze using the SDLoc of the value operand.
LLVM_ABI SDValue getConstantPool(const Constant *C, EVT VT, MaybeAlign Align=std::nullopt, int Offs=0, bool isT=false, unsigned TargetFlags=0)
LLVM_ABI 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.
LLVM_ABI SDValue UnrollVectorOp(SDNode *N, unsigned ResNE=0)
Utility function used by legalize and lowering to "unroll" a vector operation by splitting out the sc...
LLVM_ABI SDValue getConstantFP(double Val, const SDLoc &DL, EVT VT, bool isTarget=false)
Create a ConstantFPSDNode wrapping a constant value.
LLVM_ABI 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 getSetCC(const SDLoc &DL, EVT VT, SDValue LHS, SDValue RHS, ISD::CondCode Cond, SDValue Chain=SDValue(), bool IsSignaling=false, SDNodeFlags Flags={})
Helper function to make it easier to build SetCC's if you just have an ISD::CondCode instead of an SD...
LLVM_ABI 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.
LLVM_ABI bool shouldOptForSize() const
LLVM_ABI SDValue getNOT(const SDLoc &DL, SDValue Val, EVT VT)
Create a bitwise NOT operation as (XOR Val, -1).
const TargetLowering & getTargetLoweringInfo() const
LLVM_ABI SDValue expandVACopy(SDNode *Node)
Expand the specified ISD::VACOPY node as the Legalize pass would.
allnodes_const_iterator allnodes_begin() const
SDValue getUNDEF(EVT VT)
Return an UNDEF node. UNDEF does not have a useful SDLoc.
SDValue getCALLSEQ_END(SDValue Chain, SDValue Op1, SDValue Op2, SDValue InGlue, const SDLoc &DL)
Return a new CALLSEQ_END node, which always must have a glue result (to ensure it's not CSE'd).
SDValue getBuildVector(EVT VT, const SDLoc &DL, ArrayRef< SDValue > Ops)
Return an ISD::BUILD_VECTOR node.
allnodes_const_iterator allnodes_end() const
LLVM_ABI void DeleteNode(SDNode *N)
Remove the specified node from the system.
SDValue getCopyFromReg(SDValue Chain, const SDLoc &dl, Register Reg, EVT VT)
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...
LLVM_ABI 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
LLVM_ABI SDValue expandVAArg(SDNode *Node)
Expand the specified ISD::VAARG node as the Legalize pass would.
LLVM_ABI void Legalize()
This transforms the SelectionDAG into a SelectionDAG that is compatible with the target instruction s...
LLVM_ABI SDValue getTokenFactor(const SDLoc &DL, SmallVectorImpl< SDValue > &Vals)
Creates a new TokenFactor containing Vals.
LLVM_ABI bool LegalizeOp(SDNode *N, SmallSetVector< SDNode *, 16 > &UpdatedNodes)
Transforms a SelectionDAG node and any operands to it into a node that is compatible with the target ...
LLVM_ABI SDValue getConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isTarget=false, bool isOpaque=false)
Create a ConstantSDNode wrapping a constant value.
LLVM_ABI SDValue getMemBasePlusOffset(SDValue Base, TypeSize Offset, const SDLoc &DL, const SDNodeFlags Flags=SDNodeFlags())
Returns sum of the base pointer and offset.
LLVM_ABI 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.
LLVM_ABI 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())
LLVM_ABI void ReplaceAllUsesWith(SDValue From, SDValue To)
Modify anything using 'From' to use 'To' instead.
LLVM_ABI SDValue makeStateFunctionCall(unsigned LibFunc, SDValue Ptr, SDValue InChain, const SDLoc &DLoc)
Helper used to make a call to a library function that has one argument of pointer type.
LLVM_ABI 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.
LLVM_ABI SDValue getSignedConstant(int64_t Val, const SDLoc &DL, EVT VT, bool isTarget=false, bool isOpaque=false)
SDValue getCALLSEQ_START(SDValue Chain, uint64_t InSize, uint64_t OutSize, const SDLoc &DL)
Return a new CALLSEQ_START node, that starts new call frame, in which InSize bytes are set up inside ...
LLVM_ABI void RemoveDeadNodes()
This method deletes all unreachable nodes in the SelectionDAG.
SDValue getSelectCC(const SDLoc &DL, SDValue LHS, SDValue RHS, SDValue True, SDValue False, ISD::CondCode Cond, SDNodeFlags Flags=SDNodeFlags())
Helper function to make it easier to build SelectCC's if you just have an ISD::CondCode instead of an...
LLVM_ABI 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...
LLVM_ABI 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 ...
LLVM_ABI SDValue getExternalSymbol(const char *Sym, EVT VT)
const TargetMachine & getTarget() const
LLVM_ABI std::pair< SDValue, SDValue > getStrictFPExtendOrRound(SDValue Op, SDValue Chain, const SDLoc &DL, EVT VT)
Convert Op, which must be a STRICT operation of float type, to the float type VT, by either extending...
LLVM_ABI SDValue getVPLogicalNOT(const SDLoc &DL, SDValue Val, SDValue Mask, SDValue EVL, EVT VT)
Create a vector-predicated logical NOT operation as (VP_XOR Val, BooleanOne, Mask,...
LLVM_ABI 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...
const LibcallLoweringInfo & getLibcalls() const
LLVM_ABI SDValue getIntPtrConstant(uint64_t Val, const SDLoc &DL, bool isTarget=false)
LLVM_ABI SDValue getValueType(EVT)
LLVM_ABI SDValue getNode(unsigned Opcode, const SDLoc &DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
LLVM_ABI SDValue getFPExtendOrRound(SDValue Op, const SDLoc &DL, EVT VT)
Convert Op, which must be of float type, to the float type VT, by either extending or rounding (by tr...
LLVM_ABI unsigned AssignTopologicalOrder()
Topological-sort the AllNodes list and a assign a unique node id for each node in the DAG based on th...
const TargetLibraryInfo & getLibInfo() const
LLVM_ABI SDValue getBoolConstant(bool V, const SDLoc &DL, EVT VT, EVT OpVT)
Create a true or false constant of type VT using the target's BooleanContent for type OpVT.
LLVM_ABI SDValue getVectorIdxConstant(uint64_t Val, const SDLoc &DL, bool isTarget=false)
LLVM_ABI void ReplaceAllUsesOfValueWith(SDValue From, SDValue To)
Replace any uses of From with To, leaving uses of other values produced by From.getNode() alone.
MachineFunction & getMachineFunction() const
SDValue getPOISON(EVT VT)
Return a POISON node. POISON does not have a useful SDLoc.
SDValue getSplatBuildVector(EVT VT, const SDLoc &DL, SDValue Op)
Return a splat ISD::BUILD_VECTOR node, consisting of Op splatted to all elements.
LLVM_ABI SDValue getFrameIndex(int FI, EVT VT, bool isTarget=false)
LLVM_ABI SDValue getZExtOrTrunc(SDValue Op, const SDLoc &DL, EVT VT)
Convert Op, which must be of integer type, to the integer type VT, by either zero-extending or trunca...
LLVM_ABI 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
LLVM_ABI SDValue CreateStackTemporary(TypeSize Bytes, Align Alignment)
Create a stack temporary based on the size in bytes and the alignment.
LLVM_ABI 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.
LLVM_ABI SDValue getVectorShuffle(EVT VT, const SDLoc &dl, SDValue N1, SDValue N2, ArrayRef< int > Mask)
Return an ISD::VECTOR_SHUFFLE node.
LLVM_ABI SDValue getLogicalNOT(const SDLoc &DL, SDValue Val, EVT VT)
Create a logical NOT operation as (XOR Val, BooleanOne).
bool insert(const value_type &X)
Insert a new element into the SetVector.
Definition SetVector.h:151
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
bool erase(PtrType Ptr)
Remove pointer from the set.
size_type count(ConstPtrType Ptr) const
count - Return 1 if the specified pointer is in the set, 0 otherwise.
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
A SetVector that performs no allocations if smaller than a certain size.
Definition SetVector.h:339
std::pair< const_iterator, bool > insert(const T &V)
insert - Insert an element into the set if it isn't already there.
Definition SmallSet.h:184
size_type size() const
Definition SmallSet.h:171
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
void reserve(size_type N)
void swap(SmallVectorImpl &RHS)
void push_back(const T &Elt)
pointer data()
Return a pointer to the vector's buffer, even if empty().
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
This class is used to represent ISD::STORE nodes.
Align getStackAlign() const
getStackAlignment - This method returns the number of bytes to which the stack pointer must be aligne...
StackDirection getStackGrowthDirection() const
getStackGrowthDirection - Return the direction the stack grows
unsigned getIntSize() const
Get size of a C-level int or unsigned int, in bits.
bool isOperationExpand(unsigned Op, EVT VT) const
Return true if the specified operation is illegal on this target or unlikely to be made legal with cu...
virtual bool isShuffleMaskLegal(ArrayRef< int >, EVT) const
Targets can use this to indicate that they only support some VECTOR_SHUFFLE operations,...
virtual bool shouldExpandBuildVectorWithShuffles(EVT, unsigned DefinedValues) const
virtual bool isSExtCheaperThanZExt(EVT FromTy, EVT ToTy) const
Return true if sign-extension from FromTy to ToTy is cheaper than zero-extension.
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...
bool isOperationLegalOrPromote(unsigned Op, EVT VT, bool LegalOnly=false) const
Return true if the specified operation is legal on this target or can be made legal using promotion.
LegalizeAction getCondCodeAction(ISD::CondCode CC, MVT VT) const
Return how the condition code should be treated: either it is legal, needs to be expanded to some oth...
virtual bool isFPImmLegal(const APFloat &, EVT, bool ForCodeSize=false) const
Returns true if the target can instruction select the specified FP immediate natively.
LegalizeAction getTruncStoreAction(EVT ValVT, EVT MemVT, Align Alignment, unsigned AddrSpace) const
Return how this store with truncation should be treated: either it is legal, needs to be promoted to ...
Register getStackPointerRegisterToSaveRestore() const
If a physical register, this specifies the register that llvm.savestack/llvm.restorestack should save...
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.
bool isStrictFPEnabled() const
Return true if the target support strict float operation.
virtual EVT getSetCCResultType(const DataLayout &DL, LLVMContext &Context, EVT VT) const
Return the ValueType of the result of SETCC operations.
virtual EVT getTypeToTransformTo(LLVMContext &Context, EVT VT) const
For types supported by the target, this is an identity function.
bool isCondCodeLegal(ISD::CondCode CC, MVT VT) const
Return true if the specified condition code is legal for a comparison of the specified types on this ...
bool isTypeLegal(EVT VT) const
Return true if the target has native support for the specified value type.
MVT getProgramPointerTy(const DataLayout &DL) const
Return the type for code pointers, which is determined by the program address space specified through...
virtual bool isJumpTableRelative() const
virtual bool ShouldShrinkFPConstant(EVT) const
If true, then instruction selection should seek to shrink the FP constant of the specified type to a ...
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.
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...
virtual bool allowsMemoryAccess(LLVMContext &Context, const DataLayout &DL, EVT VT, unsigned AddrSpace=0, Align Alignment=Align(1), MachineMemOperand::Flags Flags=MachineMemOperand::MONone, unsigned *Fast=nullptr) const
Return true if the target supports a memory access of this type for the given address space and align...
virtual LegalizeAction getCustomOperationAction(SDNode &Op) const
How to legalize this custom operation?
LegalizeAction getLoadAction(EVT ValVT, EVT MemVT, Align Alignment, unsigned AddrSpace, unsigned ExtType, bool Atomic) const
Return how this load with extension should be treated: either it is legal, needs to be promoted to a ...
LegalizeAction getStrictFPOperationAction(unsigned Op, EVT VT) const
virtual bool useSoftFloat() const
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 ...
virtual bool shouldSignExtendTypeInLibCall(Type *Ty, bool IsSigned) const
Returns true if arguments should be sign-extended in lib calls.
std::vector< ArgListEntry > ArgListTy
bool allowsMemoryAccessForAlignment(LLVMContext &Context, const DataLayout &DL, EVT VT, unsigned AddrSpace=0, Align Alignment=Align(1), MachineMemOperand::Flags Flags=MachineMemOperand::MONone, unsigned *Fast=nullptr) const
This function returns true if the memory access is aligned or if the target allows this specific unal...
bool isTruncStoreLegalOrCustom(EVT ValVT, EVT MemVT, Align Alignment, unsigned AddrSpace) const
Return true if the specified store with truncation has solution on this target.
bool isCondCodeLegalOrCustom(ISD::CondCode CC, MVT VT) const
Return true if the specified condition code is legal or custom for a comparison of the specified type...
MVT getFrameIndexTy(const DataLayout &DL) const
Return the type for frame index, which is determined by the alloca address space specified through th...
bool isLoadLegal(EVT ValVT, EVT MemVT, Align Alignment, unsigned AddrSpace, unsigned ExtType, bool Atomic) const
Return true if the specified load with extension is legal on this target.
MVT getRegisterType(MVT VT) const
Return the type of registers that this ValueType will eventually require.
bool isLoadLegalOrCustom(EVT ValVT, EVT MemVT, Align Alignment, unsigned AddrSpace, unsigned ExtType, bool Atomic) const
Return true if the specified load with extension is legal or custom on this target.
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...
MVT getTypeToPromoteTo(unsigned Op, MVT VT) const
If the action for this operation is to promote, this method returns the ValueType to promote to.
const RTLIB::RuntimeLibcallsInfo & getRuntimeLibcallsInfo() const
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 expandMultipleResultFPLibCall(SelectionDAG &DAG, RTLIB::Libcall LC, SDNode *Node, SmallVectorImpl< SDValue > &Results, std::optional< unsigned > CallRetResNo={}) const
Expands a node with multiple results to an FP or vector libcall.
bool expandMULO(SDNode *Node, SDValue &Result, SDValue &Overflow, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::[US]MULO.
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.
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.
virtual SDValue expandIndirectJTBranch(const SDLoc &dl, SDValue Value, SDValue Addr, int JTI, SelectionDAG &DAG) const
Expands target specific indirect branch for the case of JumpTable expansion.
SDValue expandABD(SDNode *N, SelectionDAG &DAG) const
Expand ABDS/ABDU nodes.
SDValue expandCLMUL(SDNode *N, SelectionDAG &DAG) const
Expand carryless multiply.
SDValue expandShlSat(SDNode *Node, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::[US]SHLSAT.
SDValue expandIS_FPCLASS(EVT ResultVT, SDValue Op, FPClassTest Test, SDNodeFlags Flags, const SDLoc &DL, SelectionDAG &DAG) const
Expand check for floating point class.
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 expandUnalignedStore(StoreSDNode *ST, SelectionDAG &DAG) const
Expands an unaligned store to 2 half-size stores for integer values, and possibly more for vectors.
void expandSADDSUBO(SDNode *Node, SDValue &Result, SDValue &Overflow, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::S(ADD|SUB)O.
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 expandVPCTTZElements(SDNode *N, SelectionDAG &DAG) const
Expand VP_CTTZ_ELTS/VP_CTTZ_ELTS_ZERO_UNDEF nodes.
bool expandFP_TO_UINT(SDNode *N, SDValue &Result, SDValue &Chain, SelectionDAG &DAG) const
Expand float to UINT conversion.
bool expandREM(SDNode *Node, SDValue &Result, SelectionDAG &DAG) const
Expand an SREM or UREM using SDIV/UDIV or SDIVREM/UDIVREM, if legal.
std::pair< SDValue, SDValue > expandUnalignedLoad(LoadSDNode *LD, SelectionDAG &DAG) const
Expands an unaligned load to 2 half-size loads for an integer, and possibly more for vectors.
SDValue expandFMINIMUMNUM_FMAXIMUMNUM(SDNode *N, SelectionDAG &DAG) const
Expand fminimumnum/fmaximumnum into multiple comparison with selects.
SDValue expandVectorSplice(SDNode *Node, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::VECTOR_SPLICE.
SDValue getVectorSubVecPointer(SelectionDAG &DAG, SDValue VecPtr, EVT VecVT, EVT SubVecVT, SDValue Index, const SDNodeFlags PtrArithFlags=SDNodeFlags()) const
Get a pointer to a sub-vector of type SubVecVT at index Idx located in memory for a vector of type Ve...
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.
SDValue expandFMINIMUM_FMAXIMUM(SDNode *N, SelectionDAG &DAG) const
Expand fminimum/fmaximum into multiple comparison with selects.
bool expandFP_TO_SINT(SDNode *N, SDValue &Result, SelectionDAG &DAG) const
Expand float(f32) to SINT(i64) conversion.
virtual SDValue getPICJumpTableRelocBase(SDValue Table, SelectionDAG &DAG) const
Returns relocation base for the given PIC jumptable.
bool isInTailCallPosition(SelectionDAG &DAG, SDNode *Node, SDValue &Chain) const
Check whether a given call node is in tail position within its function.
SDValue expandFunnelShift(SDNode *N, SelectionDAG &DAG) const
Expand funnel shift.
bool LegalizeSetCCCondCode(SelectionDAG &DAG, EVT VT, SDValue &LHS, SDValue &RHS, SDValue &CC, SDValue Mask, SDValue EVL, bool &NeedInvert, const SDLoc &dl, SDValue &Chain, bool IsSignaling=false) const
Legalize a SETCC or VP_SETCC with given LHS and RHS and condition code CC on the current target.
virtual SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const
This callback is invoked for operations that are unsupported by the target, which are registered to u...
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 expandFP_ROUND(SDNode *Node, SelectionDAG &DAG) const
Expand round(fp) to fp conversion.
SDValue expandROT(SDNode *N, bool AllowVectorOps, SelectionDAG &DAG) const
Expand rotations.
SDValue getVectorElementPointer(SelectionDAG &DAG, SDValue VecPtr, EVT VecVT, SDValue Index, const SDNodeFlags PtrArithFlags=SDNodeFlags()) const
Get a pointer to vector element Idx located in memory for a vector of type VecVT starting at a base a...
SDValue expandFMINNUM_FMAXNUM(SDNode *N, SelectionDAG &DAG) const
Expand fminnum/fmaxnum into fminnum_ieee/fmaxnum_ieee with quieted inputs.
std::pair< SDValue, SDValue > makeLibCall(SelectionDAG &DAG, RTLIB::LibcallImpl LibcallImpl, EVT RetVT, ArrayRef< SDValue > Ops, MakeLibCallOptions CallOptions, const SDLoc &dl, SDValue Chain=SDValue()) const
Returns a pair of (return value, chain).
SDValue expandCMP(SDNode *Node, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::[US]CMP.
SDValue expandFixedPointMul(SDNode *Node, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::[U|S]MULFIX[SAT].
void expandUADDSUBO(SDNode *Node, SDValue &Result, SDValue &Overflow, SelectionDAG &DAG) const
Method for building the DAG expansion of ISD::U(ADD|SUB)O.
bool expandUINT_TO_FP(SDNode *N, SDValue &Result, SDValue &Chain, SelectionDAG &DAG) const
Expand UINT(i64) to double(f64) conversion.
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.
SDValue expandCTLS(SDNode *N, SelectionDAG &DAG) const
Expand CTLS (count leading sign bits) nodes.
Primary interface to the complete machine description for the target machine.
const Triple & getTargetTriple() const
virtual const TargetFrameLowering * getFrameLowering() const
static constexpr TypeSize getFixed(ScalarTy ExactSize)
Definition TypeSize.h:343
LLVMContext & getContext() const
Return the LLVMContext in which this type was uniqued.
Definition Type.h:130
bool isVoidTy() const
Return true if this is 'void'.
Definition Type.h:141
static LLVM_ABI UndefValue * get(Type *T)
Static factory methods - Return an 'undef' object of the specified type.
LLVM Value Representation.
Definition Value.h:75
constexpr ScalarTy getFixedValue() const
Definition TypeSize.h:200
constexpr ScalarTy getKnownMinValue() const
Returns the minimum value this quantity can represent.
Definition TypeSize.h:165
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
constexpr char Args[]
Key for Kernel::Metadata::mArgs.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
@ Entry
Definition COFF.h:862
@ Fast
Attempts to make calls as fast as possible (e.g.
Definition CallingConv.h:41
@ SETCC
SetCC operator - This evaluates to a true value iff the condition is true.
Definition ISDOpcodes.h:819
@ MERGE_VALUES
MERGE_VALUES - This node takes multiple discrete operands and returns them all as its individual resu...
Definition ISDOpcodes.h:261
@ STACKRESTORE
STACKRESTORE has two operands, an input chain and a pointer to restore to it returns an output chain.
@ STACKSAVE
STACKSAVE - STACKSAVE has one operand, an input chain.
@ CTLZ_ZERO_UNDEF
Definition ISDOpcodes.h:788
@ STRICT_FSETCC
STRICT_FSETCC/STRICT_FSETCCS - Constrained versions of SETCC, used for floating-point operands only.
Definition ISDOpcodes.h:511
@ POISON
POISON - A poison node.
Definition ISDOpcodes.h:236
@ SET_FPENV
Sets the current floating-point environment.
@ VECREDUCE_SEQ_FADD
Generic reduction nodes.
@ EH_SJLJ_LONGJMP
OUTCHAIN = EH_SJLJ_LONGJMP(INCHAIN, buffer) This corresponds to the eh.sjlj.longjmp intrinsic.
Definition ISDOpcodes.h:168
@ SMUL_LOHI
SMUL_LOHI/UMUL_LOHI - Multiply two integers of type iN, producing a signed/unsigned value of type i[2...
Definition ISDOpcodes.h:275
@ INSERT_SUBVECTOR
INSERT_SUBVECTOR(VECTOR1, VECTOR2, IDX) - Returns a vector with VECTOR2 inserted into VECTOR1.
Definition ISDOpcodes.h:600
@ STACKADDRESS
STACKADDRESS - Represents the llvm.stackaddress intrinsic.
Definition ISDOpcodes.h:127
@ BSWAP
Byte Swap and Counting operators.
Definition ISDOpcodes.h:779
@ SMULFIX
RESULT = [US]MULFIX(LHS, RHS, SCALE) - Perform fixed point multiplication on 2 integers with the same...
Definition ISDOpcodes.h:394
@ VAEND
VAEND, VASTART - VAEND and VASTART have three operands: an input chain, pointer, and a SRCVALUE.
@ ATOMIC_STORE
OUTCHAIN = ATOMIC_STORE(INCHAIN, val, ptr) This corresponds to "store atomic" instruction.
@ FRAME_TO_ARGS_OFFSET
FRAME_TO_ARGS_OFFSET - This node represents offset from frame pointer to first (possible) on-stack ar...
Definition ISDOpcodes.h:145
@ RESET_FPENV
Set floating-point environment to default state.
@ FMAD
FMAD - Perform a * b + c, while getting the same result as the separately rounded operations.
Definition ISDOpcodes.h:522
@ ADD
Simple integer binary arithmetic operators.
Definition ISDOpcodes.h:264
@ LOAD
LOAD and STORE have token chains as their first operand, then the same operands as an LLVM load/store...
@ SMULFIXSAT
Same as the corresponding unsaturated fixed point instructions, but the result is clamped between the...
Definition ISDOpcodes.h:400
@ SET_FPMODE
Sets the current dynamic floating-point control modes.
@ ANY_EXTEND
ANY_EXTEND - Used for integer types. The high bits are undefined.
Definition ISDOpcodes.h:853
@ CTTZ_ELTS
Returns the number of number of trailing (least significant) zero elements in a vector.
@ FMA
FMA - Perform a * b + c with no intermediate rounding step.
Definition ISDOpcodes.h:518
@ FMODF
FMODF - Decomposes the operand into integral and fractional parts, each having the same type and sign...
@ FATAN2
FATAN2 - atan2, inspired by libm.
@ FSINCOSPI
FSINCOSPI - Compute both the sine and cosine times pi more accurately than FSINCOS(pi*x),...
@ INTRINSIC_VOID
OUTCHAIN = INTRINSIC_VOID(INCHAIN, INTRINSICID, arg1, arg2, ...) This node represents a target intrin...
Definition ISDOpcodes.h:220
@ EH_SJLJ_SETUP_DISPATCH
OUTCHAIN = EH_SJLJ_SETUP_DISPATCH(INCHAIN) The target initializes the dispatch table here.
Definition ISDOpcodes.h:172
@ GlobalAddress
Definition ISDOpcodes.h:88
@ ATOMIC_CMP_SWAP_WITH_SUCCESS
Val, Success, OUTCHAIN = ATOMIC_CMP_SWAP_WITH_SUCCESS(INCHAIN, ptr, cmp, swap) N.b.
@ STRICT_FMINIMUM
Definition ISDOpcodes.h:471
@ SINT_TO_FP
[SU]INT_TO_FP - These operators convert integers (whose interpreted sign depends on the first letter)...
Definition ISDOpcodes.h:880
@ CONCAT_VECTORS
CONCAT_VECTORS(VECTOR0, VECTOR1, ...) - Given a number of values of vector type with the same length ...
Definition ISDOpcodes.h:584
@ VECREDUCE_FMAX
FMIN/FMAX nodes can have flags, for NaN/NoNaN variants.
@ FADD
Simple binary floating point operators.
Definition ISDOpcodes.h:417
@ VECREDUCE_FMAXIMUM
FMINIMUM/FMAXIMUM nodes propatate NaNs and signed zeroes using the llvm.minimum and llvm....
@ ABS
ABS - Determine the unsigned absolute value of a signed integer value of the same bitwidth.
Definition ISDOpcodes.h:747
@ ATOMIC_FENCE
OUTCHAIN = ATOMIC_FENCE(INCHAIN, ordering, scope) This corresponds to the fence instruction.
@ RESET_FPMODE
Sets default dynamic floating-point control modes.
@ SDIVREM
SDIVREM/UDIVREM - Divide two integers and produce both a quotient and remainder result.
Definition ISDOpcodes.h:280
@ FP16_TO_FP
FP16_TO_FP, FP_TO_FP16 - These operators are used to perform promotions and truncation for half-preci...
@ BITCAST
BITCAST - This operator converts between integer, vector and FP values, as if the value was stored to...
Definition ISDOpcodes.h:993
@ BUILD_PAIR
BUILD_PAIR - This is the opposite of EXTRACT_ELEMENT in some ways.
Definition ISDOpcodes.h:254
@ CLMUL
Carry-less multiplication operations.
Definition ISDOpcodes.h:774
@ INIT_TRAMPOLINE
INIT_TRAMPOLINE - This corresponds to the init_trampoline intrinsic.
@ FLDEXP
FLDEXP - ldexp, inspired by libm (op0 * 2**op1).
@ SDIVFIX
RESULT = [US]DIVFIX(LHS, RHS, SCALE) - Perform fixed point division on 2 integers with the same width...
Definition ISDOpcodes.h:407
@ STRICT_FSQRT
Constrained versions of libm-equivalent floating point intrinsics.
Definition ISDOpcodes.h:438
@ BUILTIN_OP_END
BUILTIN_OP_END - This must be the last enum value in this list.
@ GlobalTLSAddress
Definition ISDOpcodes.h:89
@ CONVERT_FROM_ARBITRARY_FP
CONVERT_FROM_ARBITRARY_FP - This operator converts from an arbitrary floating-point represented as an...
@ EH_LABEL
EH_LABEL - Represents a label in mid basic block used to track locations needed for debug and excepti...
@ EH_RETURN
OUTCHAIN = EH_RETURN(INCHAIN, OFFSET, HANDLER) - This node represents 'eh_return' gcc dwarf builtin,...
Definition ISDOpcodes.h:156
@ SIGN_EXTEND
Conversion operators.
Definition ISDOpcodes.h:844
@ AVGCEILS
AVGCEILS/AVGCEILU - Rounding averaging add - Add two integers using an integer of type i[N+2],...
Definition ISDOpcodes.h:715
@ STRICT_UINT_TO_FP
Definition ISDOpcodes.h:485
@ SCALAR_TO_VECTOR
SCALAR_TO_VECTOR(VAL) - This represents the operation of loading a scalar value into element 0 of the...
Definition ISDOpcodes.h:665
@ READSTEADYCOUNTER
READSTEADYCOUNTER - This corresponds to the readfixedcounter intrinsic.
@ ADDROFRETURNADDR
ADDROFRETURNADDR - Represents the llvm.addressofreturnaddress intrinsic.
Definition ISDOpcodes.h:117
@ VECREDUCE_FADD
These reductions have relaxed evaluation order semantics, and have a single vector operand.
@ CTTZ_ZERO_UNDEF
Bit counting operators with an undefined result for zero inputs.
Definition ISDOpcodes.h:787
@ PREFETCH
PREFETCH - This corresponds to a prefetch intrinsic.
@ FSINCOS
FSINCOS - Compute both fsin and fcos as a single operation.
@ 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:827
@ FNEG
Perform various unary floating-point operations inspired by libm.
@ BR_CC
BR_CC - Conditional branch.
@ SSUBO
Same for subtraction.
Definition ISDOpcodes.h:352
@ BR_JT
BR_JT - Jumptable branch.
@ VECTOR_INTERLEAVE
VECTOR_INTERLEAVE(VEC1, VEC2, ...) - Returns N vectors from N input vectors, where N is the factor to...
Definition ISDOpcodes.h:635
@ FCANONICALIZE
Returns platform specific canonical encoding of a floating point number.
Definition ISDOpcodes.h:541
@ IS_FPCLASS
Performs a check of floating point class property, defined by IEEE-754.
Definition ISDOpcodes.h:548
@ SSUBSAT
RESULT = [US]SUBSAT(LHS, RHS) - Perform saturation subtraction on 2 integers with the same bit width ...
Definition ISDOpcodes.h:374
@ SELECT
Select(COND, TRUEVAL, FALSEVAL).
Definition ISDOpcodes.h:796
@ ATOMIC_LOAD
Val, OUTCHAIN = ATOMIC_LOAD(INCHAIN, ptr) This corresponds to "load atomic" instruction.
@ UNDEF
UNDEF - An undefined node.
Definition ISDOpcodes.h:233
@ EXTRACT_ELEMENT
EXTRACT_ELEMENT - This is used to get the lower or upper (determined by a Constant,...
Definition ISDOpcodes.h:247
@ SPLAT_VECTOR
SPLAT_VECTOR(VAL) - Returns a vector with the scalar value VAL duplicated in all lanes.
Definition ISDOpcodes.h:672
@ VACOPY
VACOPY - VACOPY has 5 operands: an input chain, a destination pointer, a source pointer,...
@ SADDO
RESULT, BOOL = [SU]ADDO(LHS, RHS) - Overflow-aware nodes for addition.
Definition ISDOpcodes.h:348
@ CTLS
Count leading redundant sign bits.
Definition ISDOpcodes.h:792
@ VECREDUCE_ADD
Integer reductions may have a result type larger than the vector element type.
@ GET_ROUNDING
Returns current rounding mode: -1 Undefined 0 Round to 0 1 Round to nearest, ties to even 2 Round to ...
Definition ISDOpcodes.h:970
@ STRICT_FP_TO_FP16
@ MULHU
MULHU/MULHS - Multiply high - Multiply two integers of type iN, producing an unsigned/signed value of...
Definition ISDOpcodes.h:704
@ GET_FPMODE
Reads the current dynamic floating-point control modes.
@ STRICT_FP16_TO_FP
@ SHL
Shift and rotation operations.
Definition ISDOpcodes.h:765
@ VECTOR_SHUFFLE
VECTOR_SHUFFLE(VEC1, VEC2) - Returns a vector, of the same type as VEC1/VEC2.
Definition ISDOpcodes.h:649
@ EXTRACT_SUBVECTOR
EXTRACT_SUBVECTOR(VECTOR, IDX) - Returns a subvector from VECTOR.
Definition ISDOpcodes.h:614
@ STRICT_FMAXIMUM
Definition ISDOpcodes.h:470
@ READ_REGISTER
READ_REGISTER, WRITE_REGISTER - This node represents llvm.register on the DAG, which implements the n...
Definition ISDOpcodes.h:139
@ EXTRACT_VECTOR_ELT
EXTRACT_VECTOR_ELT(VECTOR, IDX) - Returns a single element from VECTOR identified by the (potentially...
Definition ISDOpcodes.h:576
@ ZERO_EXTEND
ZERO_EXTEND - Used for integer types, zeroing the new bits.
Definition ISDOpcodes.h:850
@ TargetConstantFP
Definition ISDOpcodes.h:180
@ DEBUGTRAP
DEBUGTRAP - Trap intended to get the attention of a debugger.
@ SELECT_CC
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
Definition ISDOpcodes.h:811
@ ATOMIC_CMP_SWAP
Val, OUTCHAIN = ATOMIC_CMP_SWAP(INCHAIN, ptr, cmp, swap) For double-word atomic operations: ValLo,...
@ FMINNUM
FMINNUM/FMAXNUM - Perform floating-point minimum maximum on two values, following IEEE-754 definition...
@ UBSANTRAP
UBSANTRAP - Trap with an immediate describing the kind of sanitizer failure.
@ SSHLSAT
RESULT = [US]SHLSAT(LHS, RHS) - Perform saturation left shift.
Definition ISDOpcodes.h:386
@ SMULO
Same for multiplication.
Definition ISDOpcodes.h:356
@ DYNAMIC_STACKALLOC
DYNAMIC_STACKALLOC - Allocate some number of bytes on the stack aligned to a specified boundary.
@ VECTOR_SPLICE_LEFT
VECTOR_SPLICE_LEFT(VEC1, VEC2, OFFSET) - Shifts CONCAT_VECTORS(VEC1, VEC2) left by OFFSET elements an...
Definition ISDOpcodes.h:653
@ SIGN_EXTEND_INREG
SIGN_EXTEND_INREG - This operator atomically performs a SHL/SRA pair to sign extend a small value in ...
Definition ISDOpcodes.h:888
@ SMIN
[US]{MIN/MAX} - Binary minimum or maximum of signed or unsigned integers.
Definition ISDOpcodes.h:727
@ SDIVFIXSAT
Same as the corresponding unsaturated fixed point instructions, but the result is clamped between the...
Definition ISDOpcodes.h:413
@ FP_EXTEND
X = FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
Definition ISDOpcodes.h:978
@ GLOBAL_OFFSET_TABLE
The address of the GOT.
Definition ISDOpcodes.h:103
@ UADDO_CARRY
Carry-using nodes for multiple precision addition and subtraction.
Definition ISDOpcodes.h:328
@ STRICT_SINT_TO_FP
STRICT_[US]INT_TO_FP - Convert a signed or unsigned integer to a floating point value.
Definition ISDOpcodes.h:484
@ STRICT_BF16_TO_FP
@ STRICT_FROUNDEVEN
Definition ISDOpcodes.h:464
@ EH_DWARF_CFA
EH_DWARF_CFA - This node represents the pointer to the DWARF Canonical Frame Address (CFA),...
Definition ISDOpcodes.h:150
@ BF16_TO_FP
BF16_TO_FP, FP_TO_BF16 - These operators are used to perform promotions and truncation for bfloat16.
@ FRAMEADDR
FRAMEADDR, RETURNADDR - These nodes represent llvm.frameaddress and llvm.returnaddress on the DAG.
Definition ISDOpcodes.h:110
@ STRICT_FP_TO_UINT
Definition ISDOpcodes.h:478
@ STRICT_FP_ROUND
X = STRICT_FP_ROUND(Y, TRUNC) - Rounding 'Y' from a larger floating point type down to the precision ...
Definition ISDOpcodes.h:500
@ STRICT_FP_TO_SINT
STRICT_FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
Definition ISDOpcodes.h:477
@ FMINIMUM
FMINIMUM/FMAXIMUM - NaN-propagating minimum/maximum that also treat -0.0 as less than 0....
@ FP_TO_SINT
FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
Definition ISDOpcodes.h:926
@ READCYCLECOUNTER
READCYCLECOUNTER - This corresponds to the readcyclecounter intrinsic.
@ TargetConstant
TargetConstant* - Like Constant*, but the DAG does not do any folding, simplification,...
Definition ISDOpcodes.h:179
@ STRICT_FP_EXTEND
X = STRICT_FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
Definition ISDOpcodes.h:505
@ AND
Bitwise operators - logical and, logical or, logical xor.
Definition ISDOpcodes.h:739
@ TRAP
TRAP - Trapping instruction.
@ INTRINSIC_WO_CHAIN
RESULT = INTRINSIC_WO_CHAIN(INTRINSICID, arg1, arg2, ...) This node represents a target intrinsic fun...
Definition ISDOpcodes.h:205
@ GET_FPENV_MEM
Gets the current floating-point environment.
@ STRICT_FP_TO_BF16
@ SCMP
[US]CMP - 3-way comparison of signed or unsigned integers.
Definition ISDOpcodes.h:735
@ AVGFLOORS
AVGFLOORS/AVGFLOORU - Averaging add - Add two integers using an integer of type i[N+1],...
Definition ISDOpcodes.h:710
@ VECTOR_SPLICE_RIGHT
VECTOR_SPLICE_RIGHT(VEC1, VEC2, OFFSET) - Shifts CONCAT_VECTORS(VEC1,VEC2) right by OFFSET elements a...
Definition ISDOpcodes.h:657
@ STRICT_FADD
Constrained versions of the binary floating point operators.
Definition ISDOpcodes.h:427
@ INSERT_VECTOR_ELT
INSERT_VECTOR_ELT(VECTOR, VAL, IDX) - Returns VECTOR with the element at IDX replaced with VAL.
Definition ISDOpcodes.h:565
@ TokenFactor
TokenFactor - This node takes multiple tokens as input and produces a single token result.
Definition ISDOpcodes.h:53
@ ATOMIC_SWAP
Val, OUTCHAIN = ATOMIC_SWAP(INCHAIN, ptr, amt) Val, OUTCHAIN = ATOMIC_LOAD_[OpName](INCHAIN,...
@ ExternalSymbol
Definition ISDOpcodes.h:93
@ FFREXP
FFREXP - frexp, extract fractional and exponent component of a floating-point value.
@ FP_ROUND
X = FP_ROUND(Y, TRUNC) - Rounding 'Y' from a larger floating point type down to the precision of the ...
Definition ISDOpcodes.h:959
@ SPONENTRY
SPONENTRY - Represents the llvm.sponentry intrinsic.
Definition ISDOpcodes.h:122
@ CLEAR_CACHE
llvm.clear_cache intrinsic Operands: Input Chain, Start Addres, End Address Outputs: Output Chain
@ ADDRSPACECAST
ADDRSPACECAST - This operator converts between pointers of different address spaces.
Definition ISDOpcodes.h:997
@ EXPERIMENTAL_VECTOR_HISTOGRAM
Experimental vector histogram intrinsic Operands: Input Chain, Inc, Mask, Base, Index,...
@ STRICT_FNEARBYINT
Definition ISDOpcodes.h:458
@ 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:945
@ VECREDUCE_FMINIMUM
@ EH_SJLJ_SETJMP
RESULT, OUTCHAIN = EH_SJLJ_SETJMP(INCHAIN, buffer) This corresponds to the eh.sjlj....
Definition ISDOpcodes.h:162
@ TRUNCATE
TRUNCATE - Completely drop the high bits.
Definition ISDOpcodes.h:856
@ VAARG
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
@ BRCOND
BRCOND - Conditional branch.
@ VECREDUCE_SEQ_FMUL
@ SHL_PARTS
SHL_PARTS/SRA_PARTS/SRL_PARTS - These operators are used for expanded integer shift operations.
Definition ISDOpcodes.h:833
@ AssertSext
AssertSext, AssertZext - These nodes record if a register contains a value that has already been zero...
Definition ISDOpcodes.h:62
@ FCOPYSIGN
FCOPYSIGN(X, Y) - Return the value of X with the sign of Y.
Definition ISDOpcodes.h:534
@ SADDSAT
RESULT = [US]ADDSAT(LHS, RHS) - Perform saturation addition on 2 integers with the same bit width (W)...
Definition ISDOpcodes.h:365
@ CALLSEQ_START
CALLSEQ_START/CALLSEQ_END - These operators mark the beginning and end of a call sequence,...
@ VECTOR_DEINTERLEAVE
VECTOR_DEINTERLEAVE(VEC1, VEC2, ...) - Returns N vectors from N input vectors, where N is the factor ...
Definition ISDOpcodes.h:624
@ GET_DYNAMIC_AREA_OFFSET
GET_DYNAMIC_AREA_OFFSET - get offset from native SP to the address of the most recent dynamic alloca.
@ CTTZ_ELTS_ZERO_POISON
@ SET_FPENV_MEM
Sets the current floating point environment.
@ FMINIMUMNUM
FMINIMUMNUM/FMAXIMUMNUM - minimumnum/maximumnum that is same with FMINNUM_IEEE and FMAXNUM_IEEE besid...
@ ABDS
ABDS/ABDU - Absolute difference - Return the absolute difference between two numbers interpreted as s...
Definition ISDOpcodes.h:722
@ ADJUST_TRAMPOLINE
ADJUST_TRAMPOLINE - This corresponds to the adjust_trampoline intrinsic.
@ INTRINSIC_W_CHAIN
RESULT,OUTCHAIN = INTRINSIC_W_CHAIN(INCHAIN, INTRINSICID, arg1, ...) This node represents a target in...
Definition ISDOpcodes.h:213
@ BUILD_VECTOR
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a fixed-width vector with the specified,...
Definition ISDOpcodes.h:556
LLVM_ABI NodeType getExtForLoadExtType(bool IsFP, LoadExtType)
bool isNormalStore(const SDNode *N)
Returns true if the specified node is a non-truncating and unindexed store.
LLVM_ABI CondCode getSetCCInverse(CondCode Operation, EVT Type)
Return the operation corresponding to !(X op Y), where 'op' is a valid SetCC operation.
LLVM_ABI std::optional< unsigned > getVPMaskIdx(unsigned Opcode)
The operand position of the vector mask.
LLVM_ABI CondCode getSetCCSwappedOperands(CondCode Operation)
Return the operation corresponding to (Y op X) when given the operation for (X op Y).
bool isSignedIntSetCC(CondCode Code)
Return true if this is a setcc instruction that performs a signed comparison when used with integer o...
CondCode
ISD::CondCode enum - These are ordered carefully to make the bitfields below work out,...
LoadExtType
LoadExtType enum - This enum defines the three variants of LOADEXT (load with extension).
LLVM_ABI bool isVPOpcode(unsigned Opcode)
Whether this is a vector-predicated Opcode.
LLVM_ABI Libcall getPOWI(EVT RetVT)
getPOWI - Return the POWI_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSINTTOFP(EVT OpVT, EVT RetVT)
getSINTTOFP - Return the SINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSYNC(unsigned Opc, MVT VT)
Return the SYNC_FETCH_AND_* value for the given opcode and type, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getLDEXP(EVT RetVT)
getLDEXP - Return the LDEXP_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getUINTTOFP(EVT OpVT, EVT RetVT)
getUINTTOFP - Return the UINTTOFP_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getFREXP(EVT RetVT)
getFREXP - Return the FREXP_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSINCOSPI(EVT RetVT)
getSINCOSPI - Return the SINCOSPI_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getFPLibCall(EVT VT, Libcall Call_F32, Libcall Call_F64, Libcall Call_F80, Libcall Call_F128, Libcall Call_PPCF128)
GetFPLibCall - Helper to return the right libcall for the given floating point type,...
LLVM_ABI Libcall getFPTOUINT(EVT OpVT, EVT RetVT)
getFPTOUINT - Return the FPTOUINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getMODF(EVT VT)
getMODF - Return the MODF_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getFPTOSINT(EVT OpVT, EVT RetVT)
getFPTOSINT - Return the FPTOSINT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getOUTLINE_ATOMIC(unsigned Opc, AtomicOrdering Order, MVT VT)
Return the outline atomics value for the given opcode, atomic ordering and type, or UNKNOWN_LIBCALL i...
LLVM_ABI Libcall getFPEXT(EVT OpVT, EVT RetVT)
getFPEXT - Return the FPEXT_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getFPROUND(EVT OpVT, EVT RetVT)
getFPROUND - Return the FPROUND_*_* value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSINCOS_STRET(EVT RetVT)
Return the SINCOS_STRET_ value for the given types, or UNKNOWN_LIBCALL if there is none.
LLVM_ABI Libcall getSINCOS(EVT RetVT)
getSINCOS - Return the SINCOS_* value for the given types, or UNKNOWN_LIBCALL if there is none.
std::enable_if_t< detail::IsValidPointer< X, Y >::value, X * > extract(Y &&MD)
Extract a Value from Metadata.
Definition Metadata.h:668
constexpr double e
NodeAddr< NodeBase * > Node
Definition RDFGraph.h:381
This is an optimization pass for GlobalISel generic memory operations.
auto drop_begin(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the first N elements excluded.
Definition STLExtras.h:316
void dump(const SparseBitVector< ElementSize > &LHS, raw_ostream &out)
unsigned Log2_32_Ceil(uint32_t Value)
Return the ceil log base 2 of the specified value, 32 if the value is zero.
Definition MathExtras.h:344
@ Offset
Definition DWP.cpp:532
FunctionAddr VTableAddr Value
Definition InstrProf.h:137
@ Undef
Value of the register doesn't matter.
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
constexpr bool isPowerOf2_64(uint64_t Value)
Return true if the argument is a power of two > 0 (64 bit edition.)
Definition MathExtras.h:284
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:331
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
Definition MathExtras.h:279
FPClassTest
Floating-point class tests, supported by 'is_fpclass' intrinsic.
APFloat scalbn(APFloat X, int Exp, APFloat::roundingMode RM)
Returns: X * 2^Exp for integral exponents.
Definition APFloat.h:1610
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:207
LLVM_ABI Constant * ConstantFoldCastOperand(unsigned Opcode, Constant *C, Type *DestTy, const DataLayout &DL)
Attempt to constant fold a cast with the specified operand.
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Definition Casting.h:547
AtomicOrdering
Atomic ordering for LLVM's memory model.
To bit_cast(const From &from) noexcept
Definition bit.h:90
@ Or
Bitwise or logical OR of integers.
@ And
Bitwise or logical AND of integers.
@ Sub
Subtraction of integers.
@ Add
Sum of integers.
fltNonfiniteBehavior
Definition APFloat.h:948
DWARFExpression::Operation Op
ArrayRef(const T &OneElt) -> ArrayRef< T >
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
LLVM_ABI bool isOneConstant(SDValue V)
Returns true if V is a constant integer one.
Align commonAlignment(Align A, uint64_t Offset)
Returns the alignment that satisfies both alignments.
Definition Alignment.h:201
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition BitVector.h:872
#define N
constexpr uint64_t value() const
This is a hole in the type system and should not be abused.
Definition Alignment.h:77
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:403
static EVT getVectorVT(LLVMContext &Context, EVT VT, unsigned NumElements, bool IsScalable=false)
Returns the EVT that represents a vector NumElements in length, where each element is of type VT.
Definition ValueTypes.h:70
EVT changeTypeToInteger() const
Return the type converted to an equivalently sized integer or vector with integer element type.
Definition ValueTypes.h:129
bool bitsGT(EVT VT) const
Return true if this has more bits than VT.
Definition ValueTypes.h:292
bool bitsLT(EVT VT) const
Return true if this has less bits than VT.
Definition ValueTypes.h:308
bool isFloatingPoint() const
Return true if this is a FP or a vector FP type.
Definition ValueTypes.h:155
TypeSize getSizeInBits() const
Return the size of the specified value type in bits.
Definition ValueTypes.h:381
bool isByteSized() const
Return true if the bit size is a multiple of 8.
Definition ValueTypes.h:251
uint64_t getScalarSizeInBits() const
Definition ValueTypes.h:393
EVT getHalfSizedIntegerVT(LLVMContext &Context) const
Finds the smallest simple value type that is greater than or equal to half the width of this EVT.
Definition ValueTypes.h:438
TypeSize getStoreSizeInBits() const
Return the number of bits overwritten by a store of the specified value type.
Definition ValueTypes.h:420
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
Definition ValueTypes.h:324
static EVT getIntegerVT(LLVMContext &Context, unsigned BitWidth)
Returns the EVT that represents an integer with the given number of bits.
Definition ValueTypes.h:61
bool isVector() const
Return true if this is a vector value type.
Definition ValueTypes.h:176
EVT getScalarType() const
If this is a vector type, return the element type, otherwise return this.
Definition ValueTypes.h:331
bool bitsGE(EVT VT) const
Return true if this has no less bits than VT.
Definition ValueTypes.h:300
bool bitsEq(EVT VT) const
Return true if this has the same number of bits as VT.
Definition ValueTypes.h:264
LLVM_ABI Type * getTypeForEVT(LLVMContext &Context) const
This method returns an LLVM type corresponding to the specified EVT.
bool isScalableVector() const
Return true if this is a vector type where the runtime length is machine dependent.
Definition ValueTypes.h:182
EVT getVectorElementType() const
Given a vector type, return the type of each element.
Definition ValueTypes.h:336
bool isScalarInteger() const
Return true if this is an integer, but not a vector.
Definition ValueTypes.h:165
LLVM_ABI const fltSemantics & getFltSemantics() const
Returns an APFloat semantics tag appropriate for the value type.
unsigned getVectorNumElements() const
Given a vector type, return the number of elements it contains.
Definition ValueTypes.h:344
bool bitsLE(EVT VT) const
Return true if this has no more bits than VT.
Definition ValueTypes.h:316
bool isInteger() const
Return true if this is an integer or a vector integer type.
Definition ValueTypes.h:160
This class contains a discriminated union of information about pointers in memory operands,...
static LLVM_ABI MachinePointerInfo getJumpTable(MachineFunction &MF)
Return a MachinePointerInfo record that refers to a jump table entry.
LLVM_ABI unsigned getAddrSpace() const
Return the LLVM IR address space number that this pointer points into.
static LLVM_ABI MachinePointerInfo getConstantPool(MachineFunction &MF)
Return a MachinePointerInfo record that refers to the constant pool.
MachinePointerInfo getWithOffset(int64_t O) const
static LLVM_ABI MachinePointerInfo getUnknownStack(MachineFunction &MF)
Stack memory without other information.
static LLVM_ABI MachinePointerInfo getFixedStack(MachineFunction &MF, int FI, int64_t Offset=0)
Return a MachinePointerInfo record that refers to the specified FrameIndex.
CallingConv::ID getLibcallImplCallingConv(RTLIB::LibcallImpl Call) const
Get the CallingConv that should be used for the specified libcall.
std::pair< FunctionType *, AttributeList > getFunctionTy(LLVMContext &Ctx, const Triple &TT, const DataLayout &DL, RTLIB::LibcallImpl LibcallImpl) const
These are IR-level optimization flags that may be propagated to SDNodes.
void setNoFPExcept(bool b)
void setNoUnsignedWrap(bool b)
void setNoSignedWrap(bool b)
MakeLibCallOptions & setIsSigned(bool Value=true)
fltNonfiniteBehavior nonFiniteBehavior
Definition APFloat.h:1009
fltNanEncoding nanEncoding
Definition APFloat.h:1011