LLVM 20.0.0git
LanaiISelLowering.cpp
Go to the documentation of this file.
1//===-- LanaiISelLowering.cpp - Lanai DAG Lowering Implementation ---------===//
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 LanaiTargetLowering class.
10//
11//===----------------------------------------------------------------------===//
12
13#include "LanaiISelLowering.h"
14#include "Lanai.h"
15#include "LanaiCondCode.h"
17#include "LanaiSubtarget.h"
20#include "llvm/ADT/APInt.h"
21#include "llvm/ADT/ArrayRef.h"
23#include "llvm/ADT/StringRef.h"
36#include "llvm/IR/CallingConv.h"
38#include "llvm/IR/Function.h"
39#include "llvm/IR/GlobalValue.h"
43#include "llvm/Support/Debug.h"
49#include <cassert>
50#include <cmath>
51#include <cstdint>
52#include <cstdlib>
53#include <utility>
54
55#define DEBUG_TYPE "lanai-lower"
56
57using namespace llvm;
58
59// Limit on number of instructions the lowered multiplication may have before a
60// call to the library function should be generated instead. The threshold is
61// currently set to 14 as this was the smallest threshold that resulted in all
62// constant multiplications being lowered. A threshold of 5 covered all cases
63// except for one multiplication which required 14. mulsi3 requires 16
64// instructions (including the prologue and epilogue but excluding instructions
65// at call site). Until we can inline mulsi3, generating at most 14 instructions
66// will be faster than invoking mulsi3.
68 "lanai-constant-mul-threshold", cl::Hidden,
69 cl::desc("Maximum number of instruction to generate when lowering constant "
70 "multiplication instead of calling library function [default=14]"),
71 cl::init(14));
72
74 const LanaiSubtarget &STI)
75 : TargetLowering(TM) {
76 // Set up the register classes.
77 addRegisterClass(MVT::i32, &Lanai::GPRRegClass);
78
79 // Compute derived properties from the register classes
80 TRI = STI.getRegisterInfo();
82
84
91
96
100
105
112
118
124
129
133
134 // Extended load operations for i1 types must be promoted
135 for (MVT VT : MVT::integer_valuetypes()) {
139 }
140
142
143 // Function alignments
146
147 setJumpIsExpensive(true);
148
149 // TODO: Setting the minimum jump table entries needed before a
150 // switch is transformed to a jump table to 100 to avoid creating jump tables
151 // as this was causing bad performance compared to a large group of if
152 // statements. Re-evaluate this on new benchmarks.
154
155 // Use fast calling convention for library functions.
156 for (int I = 0; I < RTLIB::UNKNOWN_LIBCALL; ++I) {
158 }
159
160 MaxStoresPerMemset = 16; // For @llvm.memset -> sequence of stores
162 MaxStoresPerMemcpy = 16; // For @llvm.memcpy -> sequence of stores
164 MaxStoresPerMemmove = 16; // For @llvm.memmove -> sequence of stores
166
167 // Booleans always contain 0 or 1.
169
171}
172
174 SelectionDAG &DAG) const {
175 switch (Op.getOpcode()) {
176 case ISD::MUL:
177 return LowerMUL(Op, DAG);
178 case ISD::BR_CC:
179 return LowerBR_CC(Op, DAG);
181 return LowerConstantPool(Op, DAG);
183 return LowerGlobalAddress(Op, DAG);
185 return LowerBlockAddress(Op, DAG);
186 case ISD::JumpTable:
187 return LowerJumpTable(Op, DAG);
188 case ISD::SELECT_CC:
189 return LowerSELECT_CC(Op, DAG);
190 case ISD::SETCC:
191 return LowerSETCC(Op, DAG);
192 case ISD::SHL_PARTS:
193 return LowerSHL_PARTS(Op, DAG);
194 case ISD::SRL_PARTS:
195 return LowerSRL_PARTS(Op, DAG);
196 case ISD::VASTART:
197 return LowerVASTART(Op, DAG);
199 return LowerDYNAMIC_STACKALLOC(Op, DAG);
200 case ISD::RETURNADDR:
201 return LowerRETURNADDR(Op, DAG);
202 case ISD::FRAMEADDR:
203 return LowerFRAMEADDR(Op, DAG);
204 default:
205 llvm_unreachable("unimplemented operand");
206 }
207}
208
209//===----------------------------------------------------------------------===//
210// Lanai Inline Assembly Support
211//===----------------------------------------------------------------------===//
212
214 const char *RegName, LLT /*VT*/,
215 const MachineFunction & /*MF*/) const {
216 // Only unallocatable registers should be matched here.
218 .Case("pc", Lanai::PC)
219 .Case("sp", Lanai::SP)
220 .Case("fp", Lanai::FP)
221 .Case("rr1", Lanai::RR1)
222 .Case("r10", Lanai::R10)
223 .Case("rr2", Lanai::RR2)
224 .Case("r11", Lanai::R11)
225 .Case("rca", Lanai::RCA)
226 .Default(0);
227
228 if (Reg)
229 return Reg;
230 report_fatal_error("Invalid register name global variable");
231}
232
233std::pair<unsigned, const TargetRegisterClass *>
235 StringRef Constraint,
236 MVT VT) const {
237 if (Constraint.size() == 1)
238 // GCC Constraint Letters
239 switch (Constraint[0]) {
240 case 'r': // GENERAL_REGS
241 return std::make_pair(0U, &Lanai::GPRRegClass);
242 default:
243 break;
244 }
245
247}
248
249// Examine constraint type and operand type and determine a weight value.
250// This object must already have been set up with the operand type
251// and the current alternative constraint selected.
254 AsmOperandInfo &Info, const char *Constraint) const {
256 Value *CallOperandVal = Info.CallOperandVal;
257 // If we don't have a value, we can't do a match,
258 // but allow it at the lowest weight.
259 if (CallOperandVal == nullptr)
260 return CW_Default;
261 // Look at the constraint type.
262 switch (*Constraint) {
263 case 'I': // signed 16 bit immediate
264 case 'J': // integer zero
265 case 'K': // unsigned 16 bit immediate
266 case 'L': // immediate in the range 0 to 31
267 case 'M': // signed 32 bit immediate where lower 16 bits are 0
268 case 'N': // signed 26 bit immediate
269 case 'O': // integer zero
270 if (isa<ConstantInt>(CallOperandVal))
271 Weight = CW_Constant;
272 break;
273 default:
275 break;
276 }
277 return Weight;
278}
279
280// LowerAsmOperandForConstraint - Lower the specified operand into the Ops
281// vector. If it is invalid, don't add anything to Ops.
283 SDValue Op, StringRef Constraint, std::vector<SDValue> &Ops,
284 SelectionDAG &DAG) const {
285 SDValue Result;
286
287 // Only support length 1 constraints for now.
288 if (Constraint.size() > 1)
289 return;
290
291 char ConstraintLetter = Constraint[0];
292 switch (ConstraintLetter) {
293 case 'I': // Signed 16 bit constant
294 // If this fails, the parent routine will give an error
295 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
296 if (isInt<16>(C->getSExtValue())) {
297 Result = DAG.getTargetConstant(C->getSExtValue(), SDLoc(C),
298 Op.getValueType());
299 break;
300 }
301 }
302 return;
303 case 'J': // integer zero
304 case 'O':
305 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
306 if (C->getZExtValue() == 0) {
307 Result = DAG.getTargetConstant(0, SDLoc(C), Op.getValueType());
308 break;
309 }
310 }
311 return;
312 case 'K': // unsigned 16 bit immediate
313 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
314 if (isUInt<16>(C->getZExtValue())) {
315 Result = DAG.getTargetConstant(C->getSExtValue(), SDLoc(C),
316 Op.getValueType());
317 break;
318 }
319 }
320 return;
321 case 'L': // immediate in the range 0 to 31
322 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
323 if (C->getZExtValue() <= 31) {
324 Result = DAG.getTargetConstant(C->getZExtValue(), SDLoc(C),
325 Op.getValueType());
326 break;
327 }
328 }
329 return;
330 case 'M': // signed 32 bit immediate where lower 16 bits are 0
331 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
332 int64_t Val = C->getSExtValue();
333 if ((isInt<32>(Val)) && ((Val & 0xffff) == 0)) {
334 Result = DAG.getTargetConstant(Val, SDLoc(C), Op.getValueType());
335 break;
336 }
337 }
338 return;
339 case 'N': // signed 26 bit immediate
340 if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op)) {
341 int64_t Val = C->getSExtValue();
342 if ((Val >= -33554432) && (Val <= 33554431)) {
343 Result = DAG.getTargetConstant(Val, SDLoc(C), Op.getValueType());
344 break;
345 }
346 }
347 return;
348 default:
349 break; // This will fall through to the generic implementation
350 }
351
352 if (Result.getNode()) {
353 Ops.push_back(Result);
354 return;
355 }
356
358}
359
360//===----------------------------------------------------------------------===//
361// Calling Convention Implementation
362//===----------------------------------------------------------------------===//
363
364#include "LanaiGenCallingConv.inc"
365
366static unsigned NumFixedArgs;
367static bool CC_Lanai32_VarArg(unsigned ValNo, MVT ValVT, MVT LocVT,
368 CCValAssign::LocInfo LocInfo,
369 ISD::ArgFlagsTy ArgFlags, CCState &State) {
370 // Handle fixed arguments with default CC.
371 // Note: Both the default and fast CC handle VarArg the same and hence the
372 // calling convention of the function is not considered here.
373 if (ValNo < NumFixedArgs) {
374 return CC_Lanai32(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State);
375 }
376
377 // Promote i8/i16 args to i32
378 if (LocVT == MVT::i8 || LocVT == MVT::i16) {
379 LocVT = MVT::i32;
380 if (ArgFlags.isSExt())
381 LocInfo = CCValAssign::SExt;
382 else if (ArgFlags.isZExt())
383 LocInfo = CCValAssign::ZExt;
384 else
385 LocInfo = CCValAssign::AExt;
386 }
387
388 // VarArgs get passed on stack
389 unsigned Offset = State.AllocateStack(4, Align(4));
390 State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
391 return false;
392}
393
394SDValue LanaiTargetLowering::LowerFormalArguments(
395 SDValue Chain, CallingConv::ID CallConv, bool IsVarArg,
396 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL,
397 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
398 switch (CallConv) {
399 case CallingConv::C:
401 return LowerCCCArguments(Chain, CallConv, IsVarArg, Ins, DL, DAG, InVals);
402 default:
403 report_fatal_error("Unsupported calling convention");
404 }
405}
406
407SDValue LanaiTargetLowering::LowerCall(TargetLowering::CallLoweringInfo &CLI,
408 SmallVectorImpl<SDValue> &InVals) const {
409 SelectionDAG &DAG = CLI.DAG;
410 SDLoc &DL = CLI.DL;
412 SmallVectorImpl<SDValue> &OutVals = CLI.OutVals;
414 SDValue Chain = CLI.Chain;
415 SDValue Callee = CLI.Callee;
416 bool &IsTailCall = CLI.IsTailCall;
417 CallingConv::ID CallConv = CLI.CallConv;
418 bool IsVarArg = CLI.IsVarArg;
419
420 // Lanai target does not yet support tail call optimization.
421 IsTailCall = false;
422
423 switch (CallConv) {
425 case CallingConv::C:
426 return LowerCCCCallTo(Chain, Callee, CallConv, IsVarArg, IsTailCall, Outs,
427 OutVals, Ins, DL, DAG, InVals);
428 default:
429 report_fatal_error("Unsupported calling convention");
430 }
431}
432
433// LowerCCCArguments - transform physical registers into virtual registers and
434// generate load operations for arguments places on the stack.
435SDValue LanaiTargetLowering::LowerCCCArguments(
436 SDValue Chain, CallingConv::ID CallConv, bool IsVarArg,
437 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL,
438 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
440 MachineFrameInfo &MFI = MF.getFrameInfo();
443
444 // Assign locations to all of the incoming arguments.
446 CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), ArgLocs,
447 *DAG.getContext());
448 if (CallConv == CallingConv::Fast) {
449 CCInfo.AnalyzeFormalArguments(Ins, CC_Lanai32_Fast);
450 } else {
451 CCInfo.AnalyzeFormalArguments(Ins, CC_Lanai32);
452 }
453
454 for (const CCValAssign &VA : ArgLocs) {
455 if (VA.isRegLoc()) {
456 // Arguments passed in registers
457 EVT RegVT = VA.getLocVT();
458 switch (RegVT.getSimpleVT().SimpleTy) {
459 case MVT::i32: {
460 Register VReg = RegInfo.createVirtualRegister(&Lanai::GPRRegClass);
461 RegInfo.addLiveIn(VA.getLocReg(), VReg);
462 SDValue ArgValue = DAG.getCopyFromReg(Chain, DL, VReg, RegVT);
463
464 // If this is an 8/16-bit value, it is really passed promoted to 32
465 // bits. Insert an assert[sz]ext to capture this, then truncate to the
466 // right size.
467 if (VA.getLocInfo() == CCValAssign::SExt)
468 ArgValue = DAG.getNode(ISD::AssertSext, DL, RegVT, ArgValue,
469 DAG.getValueType(VA.getValVT()));
470 else if (VA.getLocInfo() == CCValAssign::ZExt)
471 ArgValue = DAG.getNode(ISD::AssertZext, DL, RegVT, ArgValue,
472 DAG.getValueType(VA.getValVT()));
473
474 if (VA.getLocInfo() != CCValAssign::Full)
475 ArgValue = DAG.getNode(ISD::TRUNCATE, DL, VA.getValVT(), ArgValue);
476
477 InVals.push_back(ArgValue);
478 break;
479 }
480 default:
481 LLVM_DEBUG(dbgs() << "LowerFormalArguments Unhandled argument type: "
482 << RegVT << "\n");
483 llvm_unreachable("unhandled argument type");
484 }
485 } else {
486 // Only arguments passed on the stack should make it here.
487 assert(VA.isMemLoc());
488 // Load the argument to a virtual register
489 unsigned ObjSize = VA.getLocVT().getSizeInBits() / 8;
490 // Check that the argument fits in stack slot
491 if (ObjSize > 4) {
492 errs() << "LowerFormalArguments Unhandled argument type: "
493 << VA.getLocVT() << "\n";
494 }
495 // Create the frame index object for this incoming parameter...
496 int FI = MFI.CreateFixedObject(ObjSize, VA.getLocMemOffset(), true);
497
498 // Create the SelectionDAG nodes corresponding to a load
499 // from this parameter
500 SDValue FIN = DAG.getFrameIndex(FI, MVT::i32);
501 InVals.push_back(DAG.getLoad(
502 VA.getLocVT(), DL, Chain, FIN,
504 }
505 }
506
507 // The Lanai ABI for returning structs by value requires that we copy
508 // the sret argument into rv for the return. Save the argument into
509 // a virtual register so that we can access it from the return points.
510 if (MF.getFunction().hasStructRetAttr()) {
511 Register Reg = LanaiMFI->getSRetReturnReg();
512 if (!Reg) {
514 LanaiMFI->setSRetReturnReg(Reg);
515 }
516 SDValue Copy = DAG.getCopyToReg(DAG.getEntryNode(), DL, Reg, InVals[0]);
517 Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other, Copy, Chain);
518 }
519
520 if (IsVarArg) {
521 // Record the frame index of the first variable argument
522 // which is a value necessary to VASTART.
523 int FI = MFI.CreateFixedObject(4, CCInfo.getStackSize(), true);
524 LanaiMFI->setVarArgsFrameIndex(FI);
525 }
526
527 return Chain;
528}
529
531 CallingConv::ID CallConv, MachineFunction &MF, bool IsVarArg,
532 const SmallVectorImpl<ISD::OutputArg> &Outs, LLVMContext &Context) const {
534 CCState CCInfo(CallConv, IsVarArg, MF, RVLocs, Context);
535
536 return CCInfo.CheckReturn(Outs, RetCC_Lanai32);
537}
538
540LanaiTargetLowering::LowerReturn(SDValue Chain, CallingConv::ID CallConv,
541 bool IsVarArg,
543 const SmallVectorImpl<SDValue> &OutVals,
544 const SDLoc &DL, SelectionDAG &DAG) const {
545 // CCValAssign - represent the assignment of the return value to a location
547
548 // CCState - Info about the registers and stack slot.
549 CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), RVLocs,
550 *DAG.getContext());
551
552 // Analize return values.
553 CCInfo.AnalyzeReturn(Outs, RetCC_Lanai32);
554
555 SDValue Glue;
556 SmallVector<SDValue, 4> RetOps(1, Chain);
557
558 // Copy the result values into the output registers.
559 for (unsigned i = 0; i != RVLocs.size(); ++i) {
560 CCValAssign &VA = RVLocs[i];
561 assert(VA.isRegLoc() && "Can only return in registers!");
562
563 Chain = DAG.getCopyToReg(Chain, DL, VA.getLocReg(), OutVals[i], Glue);
564
565 // Guarantee that all emitted copies are stuck together with flags.
566 Glue = Chain.getValue(1);
567 RetOps.push_back(DAG.getRegister(VA.getLocReg(), VA.getLocVT()));
568 }
569
570 // The Lanai ABI for returning structs by value requires that we copy
571 // the sret argument into rv for the return. We saved the argument into
572 // a virtual register in the entry block, so now we copy the value out
573 // and into rv.
577 Register Reg = LanaiMFI->getSRetReturnReg();
578 assert(Reg &&
579 "SRetReturnReg should have been set in LowerFormalArguments().");
580 SDValue Val =
581 DAG.getCopyFromReg(Chain, DL, Reg, getPointerTy(DAG.getDataLayout()));
582
583 Chain = DAG.getCopyToReg(Chain, DL, Lanai::RV, Val, Glue);
584 Glue = Chain.getValue(1);
585 RetOps.push_back(
586 DAG.getRegister(Lanai::RV, getPointerTy(DAG.getDataLayout())));
587 }
588
589 RetOps[0] = Chain; // Update chain
590
591 unsigned Opc = LanaiISD::RET_GLUE;
592 if (Glue.getNode())
593 RetOps.push_back(Glue);
594
595 // Return Void
596 return DAG.getNode(Opc, DL, MVT::Other,
597 ArrayRef<SDValue>(&RetOps[0], RetOps.size()));
598}
599
600// LowerCCCCallTo - functions arguments are copied from virtual regs to
601// (physical regs)/(stack frame), CALLSEQ_START and CALLSEQ_END are emitted.
602SDValue LanaiTargetLowering::LowerCCCCallTo(
603 SDValue Chain, SDValue Callee, CallingConv::ID CallConv, bool IsVarArg,
604 bool /*IsTailCall*/, const SmallVectorImpl<ISD::OutputArg> &Outs,
605 const SmallVectorImpl<SDValue> &OutVals,
606 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL,
607 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
608 // Analyze operands of the call, assigning locations to each operand.
610 CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), ArgLocs,
611 *DAG.getContext());
612 GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee);
614
615 NumFixedArgs = 0;
616 if (IsVarArg && G) {
617 const Function *CalleeFn = dyn_cast<Function>(G->getGlobal());
618 if (CalleeFn)
620 }
621 if (NumFixedArgs)
622 CCInfo.AnalyzeCallOperands(Outs, CC_Lanai32_VarArg);
623 else {
624 if (CallConv == CallingConv::Fast)
625 CCInfo.AnalyzeCallOperands(Outs, CC_Lanai32_Fast);
626 else
627 CCInfo.AnalyzeCallOperands(Outs, CC_Lanai32);
628 }
629
630 // Get a count of how many bytes are to be pushed on the stack.
631 unsigned NumBytes = CCInfo.getStackSize();
632
633 // Create local copies for byval args.
634 SmallVector<SDValue, 8> ByValArgs;
635 for (unsigned I = 0, E = Outs.size(); I != E; ++I) {
636 ISD::ArgFlagsTy Flags = Outs[I].Flags;
637 if (!Flags.isByVal())
638 continue;
639
640 SDValue Arg = OutVals[I];
641 unsigned Size = Flags.getByValSize();
642 Align Alignment = Flags.getNonZeroByValAlign();
643
644 int FI = MFI.CreateStackObject(Size, Alignment, false);
645 SDValue FIPtr = DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
646 SDValue SizeNode = DAG.getConstant(Size, DL, MVT::i32);
647
648 Chain = DAG.getMemcpy(Chain, DL, FIPtr, Arg, SizeNode, Alignment,
649 /*IsVolatile=*/false,
650 /*AlwaysInline=*/false,
651 /*CI=*/nullptr, std::nullopt, MachinePointerInfo(),
653 ByValArgs.push_back(FIPtr);
654 }
655
656 Chain = DAG.getCALLSEQ_START(Chain, NumBytes, 0, DL);
657
659 SmallVector<SDValue, 12> MemOpChains;
661
662 // Walk the register/memloc assignments, inserting copies/loads.
663 for (unsigned I = 0, J = 0, E = ArgLocs.size(); I != E; ++I) {
664 CCValAssign &VA = ArgLocs[I];
665 SDValue Arg = OutVals[I];
666 ISD::ArgFlagsTy Flags = Outs[I].Flags;
667
668 // Promote the value if needed.
669 switch (VA.getLocInfo()) {
671 break;
673 Arg = DAG.getNode(ISD::SIGN_EXTEND, DL, VA.getLocVT(), Arg);
674 break;
676 Arg = DAG.getNode(ISD::ZERO_EXTEND, DL, VA.getLocVT(), Arg);
677 break;
679 Arg = DAG.getNode(ISD::ANY_EXTEND, DL, VA.getLocVT(), Arg);
680 break;
681 default:
682 llvm_unreachable("Unknown loc info!");
683 }
684
685 // Use local copy if it is a byval arg.
686 if (Flags.isByVal())
687 Arg = ByValArgs[J++];
688
689 // Arguments that can be passed on register must be kept at RegsToPass
690 // vector
691 if (VA.isRegLoc()) {
692 RegsToPass.push_back(std::make_pair(VA.getLocReg(), Arg));
693 } else {
694 assert(VA.isMemLoc());
695
696 if (StackPtr.getNode() == nullptr)
697 StackPtr = DAG.getCopyFromReg(Chain, DL, Lanai::SP,
699
700 SDValue PtrOff =
701 DAG.getNode(ISD::ADD, DL, getPointerTy(DAG.getDataLayout()), StackPtr,
703
704 MemOpChains.push_back(
705 DAG.getStore(Chain, DL, Arg, PtrOff, MachinePointerInfo()));
706 }
707 }
708
709 // Transform all store nodes into one single node because all store nodes are
710 // independent of each other.
711 if (!MemOpChains.empty())
712 Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other,
713 ArrayRef<SDValue>(&MemOpChains[0], MemOpChains.size()));
714
715 SDValue InGlue;
716
717 // Build a sequence of copy-to-reg nodes chained together with token chain and
718 // flag operands which copy the outgoing args into registers. The InGlue in
719 // necessary since all emitted instructions must be stuck together.
720 for (unsigned I = 0, E = RegsToPass.size(); I != E; ++I) {
721 Chain = DAG.getCopyToReg(Chain, DL, RegsToPass[I].first,
722 RegsToPass[I].second, InGlue);
723 InGlue = Chain.getValue(1);
724 }
725
726 // If the callee is a GlobalAddress node (quite common, every direct call is)
727 // turn it into a TargetGlobalAddress node so that legalize doesn't hack it.
728 // Likewise ExternalSymbol -> TargetExternalSymbol.
729 uint8_t OpFlag = LanaiII::MO_NO_FLAG;
730 if (G) {
732 G->getGlobal(), DL, getPointerTy(DAG.getDataLayout()), 0, OpFlag);
733 } else if (ExternalSymbolSDNode *E = dyn_cast<ExternalSymbolSDNode>(Callee)) {
735 E->getSymbol(), getPointerTy(DAG.getDataLayout()), OpFlag);
736 }
737
738 // Returns a chain & a flag for retval copy to use.
739 SDVTList NodeTys = DAG.getVTList(MVT::Other, MVT::Glue);
741 Ops.push_back(Chain);
742 Ops.push_back(Callee);
743
744 // Add a register mask operand representing the call-preserved registers.
745 // TODO: Should return-twice functions be handled?
746 const uint32_t *Mask =
747 TRI->getCallPreservedMask(DAG.getMachineFunction(), CallConv);
748 assert(Mask && "Missing call preserved mask for calling convention");
749 Ops.push_back(DAG.getRegisterMask(Mask));
750
751 // Add argument registers to the end of the list so that they are
752 // known live into the call.
753 for (unsigned I = 0, E = RegsToPass.size(); I != E; ++I)
754 Ops.push_back(DAG.getRegister(RegsToPass[I].first,
755 RegsToPass[I].second.getValueType()));
756
757 if (InGlue.getNode())
758 Ops.push_back(InGlue);
759
760 Chain = DAG.getNode(LanaiISD::CALL, DL, NodeTys,
761 ArrayRef<SDValue>(&Ops[0], Ops.size()));
762 InGlue = Chain.getValue(1);
763
764 // Create the CALLSEQ_END node.
765 Chain = DAG.getCALLSEQ_END(Chain, NumBytes, 0, InGlue, DL);
766 InGlue = Chain.getValue(1);
767
768 // Handle result values, copying them out of physregs into vregs that we
769 // return.
770 return LowerCallResult(Chain, InGlue, CallConv, IsVarArg, Ins, DL, DAG,
771 InVals);
772}
773
774// LowerCallResult - Lower the result values of a call into the
775// appropriate copies out of appropriate physical registers.
776SDValue LanaiTargetLowering::LowerCallResult(
777 SDValue Chain, SDValue InGlue, CallingConv::ID CallConv, bool IsVarArg,
778 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL,
779 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
780 // Assign locations to each value returned by this call.
782 CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), RVLocs,
783 *DAG.getContext());
784
785 CCInfo.AnalyzeCallResult(Ins, RetCC_Lanai32);
786
787 // Copy all of the result registers out of their specified physreg.
788 for (unsigned I = 0; I != RVLocs.size(); ++I) {
789 Chain = DAG.getCopyFromReg(Chain, DL, RVLocs[I].getLocReg(),
790 RVLocs[I].getValVT(), InGlue)
791 .getValue(1);
792 InGlue = Chain.getValue(2);
793 InVals.push_back(Chain.getValue(0));
794 }
795
796 return Chain;
797}
798
799//===----------------------------------------------------------------------===//
800// Custom Lowerings
801//===----------------------------------------------------------------------===//
802
804 SDValue &RHS, SelectionDAG &DAG) {
805 ISD::CondCode SetCCOpcode = cast<CondCodeSDNode>(CC)->get();
806
807 // For integer, only the SETEQ, SETNE, SETLT, SETLE, SETGT, SETGE, SETULT,
808 // SETULE, SETUGT, and SETUGE opcodes are used (see CodeGen/ISDOpcodes.h)
809 // and Lanai only supports integer comparisons, so only provide definitions
810 // for them.
811 switch (SetCCOpcode) {
812 case ISD::SETEQ:
813 return LPCC::ICC_EQ;
814 case ISD::SETGT:
815 if (ConstantSDNode *RHSC = dyn_cast<ConstantSDNode>(RHS))
816 if (RHSC->getZExtValue() == 0xFFFFFFFF) {
817 // X > -1 -> X >= 0 -> is_plus(X)
818 RHS = DAG.getConstant(0, DL, RHS.getValueType());
819 return LPCC::ICC_PL;
820 }
821 return LPCC::ICC_GT;
822 case ISD::SETUGT:
823 return LPCC::ICC_UGT;
824 case ISD::SETLT:
825 if (ConstantSDNode *RHSC = dyn_cast<ConstantSDNode>(RHS))
826 if (RHSC->getZExtValue() == 0)
827 // X < 0 -> is_minus(X)
828 return LPCC::ICC_MI;
829 return LPCC::ICC_LT;
830 case ISD::SETULT:
831 return LPCC::ICC_ULT;
832 case ISD::SETLE:
833 if (ConstantSDNode *RHSC = dyn_cast<ConstantSDNode>(RHS))
834 if (RHSC->getZExtValue() == 0xFFFFFFFF) {
835 // X <= -1 -> X < 0 -> is_minus(X)
836 RHS = DAG.getConstant(0, DL, RHS.getValueType());
837 return LPCC::ICC_MI;
838 }
839 return LPCC::ICC_LE;
840 case ISD::SETULE:
841 return LPCC::ICC_ULE;
842 case ISD::SETGE:
843 if (ConstantSDNode *RHSC = dyn_cast<ConstantSDNode>(RHS))
844 if (RHSC->getZExtValue() == 0)
845 // X >= 0 -> is_plus(X)
846 return LPCC::ICC_PL;
847 return LPCC::ICC_GE;
848 case ISD::SETUGE:
849 return LPCC::ICC_UGE;
850 case ISD::SETNE:
851 return LPCC::ICC_NE;
852 case ISD::SETONE:
853 case ISD::SETUNE:
854 case ISD::SETOGE:
855 case ISD::SETOLE:
856 case ISD::SETOLT:
857 case ISD::SETOGT:
858 case ISD::SETOEQ:
859 case ISD::SETUEQ:
860 case ISD::SETO:
861 case ISD::SETUO:
862 llvm_unreachable("Unsupported comparison.");
863 default:
864 llvm_unreachable("Unknown integer condition code!");
865 }
866}
867
869 SDValue Chain = Op.getOperand(0);
870 SDValue Cond = Op.getOperand(1);
871 SDValue LHS = Op.getOperand(2);
872 SDValue RHS = Op.getOperand(3);
873 SDValue Dest = Op.getOperand(4);
874 SDLoc DL(Op);
875
877 SDValue TargetCC = DAG.getConstant(CC, DL, MVT::i32);
878 SDValue Glue =
879 DAG.getNode(LanaiISD::SET_FLAG, DL, MVT::Glue, LHS, RHS, TargetCC);
880
881 return DAG.getNode(LanaiISD::BR_CC, DL, Op.getValueType(), Chain, Dest,
882 TargetCC, Glue);
883}
884
886 EVT VT = Op->getValueType(0);
887 if (VT != MVT::i32)
888 return SDValue();
889
890 ConstantSDNode *C = dyn_cast<ConstantSDNode>(Op->getOperand(1));
891 if (!C)
892 return SDValue();
893
894 int64_t MulAmt = C->getSExtValue();
895 int32_t HighestOne = -1;
896 uint32_t NonzeroEntries = 0;
897 int SignedDigit[32] = {0};
898
899 // Convert to non-adjacent form (NAF) signed-digit representation.
900 // NAF is a signed-digit form where no adjacent digits are non-zero. It is the
901 // minimal Hamming weight representation of a number (on average 1/3 of the
902 // digits will be non-zero vs 1/2 for regular binary representation). And as
903 // the non-zero digits will be the only digits contributing to the instruction
904 // count, this is desirable. The next loop converts it to NAF (following the
905 // approach in 'Guide to Elliptic Curve Cryptography' [ISBN: 038795273X]) by
906 // choosing the non-zero coefficients such that the resulting quotient is
907 // divisible by 2 which will cause the next coefficient to be zero.
908 int64_t E = std::abs(MulAmt);
909 int S = (MulAmt < 0 ? -1 : 1);
910 int I = 0;
911 while (E > 0) {
912 int ZI = 0;
913 if (E % 2 == 1) {
914 ZI = 2 - (E % 4);
915 if (ZI != 0)
916 ++NonzeroEntries;
917 }
918 SignedDigit[I] = S * ZI;
919 if (SignedDigit[I] == 1)
920 HighestOne = I;
921 E = (E - ZI) / 2;
922 ++I;
923 }
924
925 // Compute number of instructions required. Due to differences in lowering
926 // between the different processors this count is not exact.
927 // Start by assuming a shift and a add/sub for every non-zero entry (hence
928 // every non-zero entry requires 1 shift and 1 add/sub except for the first
929 // entry).
930 int32_t InstrRequired = 2 * NonzeroEntries - 1;
931 // Correct possible over-adding due to shift by 0 (which is not emitted).
932 if (std::abs(MulAmt) % 2 == 1)
933 --InstrRequired;
934 // Return if the form generated would exceed the instruction threshold.
935 if (InstrRequired > LanaiLowerConstantMulThreshold)
936 return SDValue();
937
938 SDValue Res;
939 SDLoc DL(Op);
940 SDValue V = Op->getOperand(0);
941
942 // Initialize the running sum. Set the running sum to the maximal shifted
943 // positive value (i.e., largest i such that zi == 1 and MulAmt has V<<i as a
944 // term NAF).
945 if (HighestOne == -1)
946 Res = DAG.getConstant(0, DL, MVT::i32);
947 else {
948 Res = DAG.getNode(ISD::SHL, DL, VT, V,
949 DAG.getConstant(HighestOne, DL, MVT::i32));
950 SignedDigit[HighestOne] = 0;
951 }
952
953 // Assemble multiplication from shift, add, sub using NAF form and running
954 // sum.
955 for (unsigned int I = 0; I < std::size(SignedDigit); ++I) {
956 if (SignedDigit[I] == 0)
957 continue;
958
959 // Shifted multiplicand (v<<i).
960 SDValue Op =
961 DAG.getNode(ISD::SHL, DL, VT, V, DAG.getConstant(I, DL, MVT::i32));
962 if (SignedDigit[I] == 1)
963 Res = DAG.getNode(ISD::ADD, DL, VT, Res, Op);
964 else if (SignedDigit[I] == -1)
965 Res = DAG.getNode(ISD::SUB, DL, VT, Res, Op);
966 }
967 return Res;
968}
969
971 SDValue LHS = Op.getOperand(0);
972 SDValue RHS = Op.getOperand(1);
973 SDValue Cond = Op.getOperand(2);
974 SDLoc DL(Op);
975
977 SDValue TargetCC = DAG.getConstant(CC, DL, MVT::i32);
978 SDValue Glue =
979 DAG.getNode(LanaiISD::SET_FLAG, DL, MVT::Glue, LHS, RHS, TargetCC);
980
981 return DAG.getNode(LanaiISD::SETCC, DL, Op.getValueType(), TargetCC, Glue);
982}
983
985 SelectionDAG &DAG) const {
986 SDValue LHS = Op.getOperand(0);
987 SDValue RHS = Op.getOperand(1);
988 SDValue TrueV = Op.getOperand(2);
989 SDValue FalseV = Op.getOperand(3);
990 SDValue Cond = Op.getOperand(4);
991 SDLoc DL(Op);
992
994 SDValue TargetCC = DAG.getConstant(CC, DL, MVT::i32);
995 SDValue Glue =
996 DAG.getNode(LanaiISD::SET_FLAG, DL, MVT::Glue, LHS, RHS, TargetCC);
997
998 SDVTList VTs = DAG.getVTList(Op.getValueType(), MVT::Glue);
999 return DAG.getNode(LanaiISD::SELECT_CC, DL, VTs, TrueV, FalseV, TargetCC,
1000 Glue);
1001}
1002
1006
1007 SDLoc DL(Op);
1008 SDValue FI = DAG.getFrameIndex(FuncInfo->getVarArgsFrameIndex(),
1010
1011 // vastart just stores the address of the VarArgsFrameIndex slot into the
1012 // memory location argument.
1013 const Value *SV = cast<SrcValueSDNode>(Op.getOperand(2))->getValue();
1014 return DAG.getStore(Op.getOperand(0), DL, FI, Op.getOperand(1),
1015 MachinePointerInfo(SV));
1016}
1017
1019 SelectionDAG &DAG) const {
1020 SDValue Chain = Op.getOperand(0);
1021 SDValue Size = Op.getOperand(1);
1022 SDLoc DL(Op);
1023
1025
1026 // Get a reference to the stack pointer.
1027 SDValue StackPointer = DAG.getCopyFromReg(Chain, DL, SPReg, MVT::i32);
1028
1029 // Subtract the dynamic size from the actual stack size to
1030 // obtain the new stack size.
1031 SDValue Sub = DAG.getNode(ISD::SUB, DL, MVT::i32, StackPointer, Size);
1032
1033 // For Lanai, the outgoing memory arguments area should be on top of the
1034 // alloca area on the stack i.e., the outgoing memory arguments should be
1035 // at a lower address than the alloca area. Move the alloca area down the
1036 // stack by adding back the space reserved for outgoing arguments to SP
1037 // here.
1038 //
1039 // We do not know what the size of the outgoing args is at this point.
1040 // So, we add a pseudo instruction ADJDYNALLOC that will adjust the
1041 // stack pointer. We replace this instruction with on that has the correct,
1042 // known offset in emitPrologue().
1043 SDValue ArgAdjust = DAG.getNode(LanaiISD::ADJDYNALLOC, DL, MVT::i32, Sub);
1044
1045 // The Sub result contains the new stack start address, so it
1046 // must be placed in the stack pointer register.
1047 SDValue CopyChain = DAG.getCopyToReg(Chain, DL, SPReg, Sub);
1048
1049 SDValue Ops[2] = {ArgAdjust, CopyChain};
1050 return DAG.getMergeValues(Ops, DL);
1051}
1052
1054 SelectionDAG &DAG) const {
1056 MachineFrameInfo &MFI = MF.getFrameInfo();
1057 MFI.setReturnAddressIsTaken(true);
1058
1059 EVT VT = Op.getValueType();
1060 SDLoc DL(Op);
1061 unsigned Depth = Op.getConstantOperandVal(0);
1062 if (Depth) {
1063 SDValue FrameAddr = LowerFRAMEADDR(Op, DAG);
1064 const unsigned Offset = -4;
1065 SDValue Ptr = DAG.getNode(ISD::ADD, DL, VT, FrameAddr,
1067 return DAG.getLoad(VT, DL, DAG.getEntryNode(), Ptr, MachinePointerInfo());
1068 }
1069
1070 // Return the link register, which contains the return address.
1071 // Mark it an implicit live-in.
1072 Register Reg = MF.addLiveIn(TRI->getRARegister(), getRegClassFor(MVT::i32));
1073 return DAG.getCopyFromReg(DAG.getEntryNode(), DL, Reg, VT);
1074}
1075
1077 SelectionDAG &DAG) const {
1079 MFI.setFrameAddressIsTaken(true);
1080
1081 EVT VT = Op.getValueType();
1082 SDLoc DL(Op);
1083 SDValue FrameAddr = DAG.getCopyFromReg(DAG.getEntryNode(), DL, Lanai::FP, VT);
1084 unsigned Depth = Op.getConstantOperandVal(0);
1085 while (Depth--) {
1086 const unsigned Offset = -8;
1087 SDValue Ptr = DAG.getNode(ISD::ADD, DL, VT, FrameAddr,
1089 FrameAddr =
1090 DAG.getLoad(VT, DL, DAG.getEntryNode(), Ptr, MachinePointerInfo());
1091 }
1092 return FrameAddr;
1093}
1094
1095const char *LanaiTargetLowering::getTargetNodeName(unsigned Opcode) const {
1096 switch (Opcode) {
1098 return "LanaiISD::ADJDYNALLOC";
1099 case LanaiISD::RET_GLUE:
1100 return "LanaiISD::RET_GLUE";
1101 case LanaiISD::CALL:
1102 return "LanaiISD::CALL";
1104 return "LanaiISD::SELECT_CC";
1105 case LanaiISD::SETCC:
1106 return "LanaiISD::SETCC";
1107 case LanaiISD::SUBBF:
1108 return "LanaiISD::SUBBF";
1109 case LanaiISD::SET_FLAG:
1110 return "LanaiISD::SET_FLAG";
1111 case LanaiISD::BR_CC:
1112 return "LanaiISD::BR_CC";
1113 case LanaiISD::Wrapper:
1114 return "LanaiISD::Wrapper";
1115 case LanaiISD::HI:
1116 return "LanaiISD::HI";
1117 case LanaiISD::LO:
1118 return "LanaiISD::LO";
1119 case LanaiISD::SMALL:
1120 return "LanaiISD::SMALL";
1121 default:
1122 return nullptr;
1123 }
1124}
1125
1127 SelectionDAG &DAG) const {
1128 SDLoc DL(Op);
1129 ConstantPoolSDNode *N = cast<ConstantPoolSDNode>(Op);
1130 const Constant *C = N->getConstVal();
1131 const LanaiTargetObjectFile *TLOF =
1132 static_cast<const LanaiTargetObjectFile *>(
1134
1135 // If the code model is small or constant will be placed in the small section,
1136 // then assume address will fit in 21-bits.
1139 SDValue Small = DAG.getTargetConstantPool(
1140 C, MVT::i32, N->getAlign(), N->getOffset(), LanaiII::MO_NO_FLAG);
1141 return DAG.getNode(ISD::OR, DL, MVT::i32,
1142 DAG.getRegister(Lanai::R0, MVT::i32),
1143 DAG.getNode(LanaiISD::SMALL, DL, MVT::i32, Small));
1144 } else {
1145 uint8_t OpFlagHi = LanaiII::MO_ABS_HI;
1146 uint8_t OpFlagLo = LanaiII::MO_ABS_LO;
1147
1148 SDValue Hi = DAG.getTargetConstantPool(C, MVT::i32, N->getAlign(),
1149 N->getOffset(), OpFlagHi);
1150 SDValue Lo = DAG.getTargetConstantPool(C, MVT::i32, N->getAlign(),
1151 N->getOffset(), OpFlagLo);
1152 Hi = DAG.getNode(LanaiISD::HI, DL, MVT::i32, Hi);
1153 Lo = DAG.getNode(LanaiISD::LO, DL, MVT::i32, Lo);
1154 SDValue Result = DAG.getNode(ISD::OR, DL, MVT::i32, Hi, Lo);
1155 return Result;
1156 }
1157}
1158
1160 SelectionDAG &DAG) const {
1161 SDLoc DL(Op);
1162 const GlobalValue *GV = cast<GlobalAddressSDNode>(Op)->getGlobal();
1163 int64_t Offset = cast<GlobalAddressSDNode>(Op)->getOffset();
1164
1165 const LanaiTargetObjectFile *TLOF =
1166 static_cast<const LanaiTargetObjectFile *>(
1168
1169 // If the code model is small or global variable will be placed in the small
1170 // section, then assume address will fit in 21-bits.
1171 const GlobalObject *GO = GV->getAliaseeObject();
1172 if (TLOF->isGlobalInSmallSection(GO, getTargetMachine())) {
1173 SDValue Small = DAG.getTargetGlobalAddress(
1175 return DAG.getNode(ISD::OR, DL, MVT::i32,
1176 DAG.getRegister(Lanai::R0, MVT::i32),
1177 DAG.getNode(LanaiISD::SMALL, DL, MVT::i32, Small));
1178 } else {
1179 uint8_t OpFlagHi = LanaiII::MO_ABS_HI;
1180 uint8_t OpFlagLo = LanaiII::MO_ABS_LO;
1181
1182 // Create the TargetGlobalAddress node, folding in the constant offset.
1184 GV, DL, getPointerTy(DAG.getDataLayout()), Offset, OpFlagHi);
1186 GV, DL, getPointerTy(DAG.getDataLayout()), Offset, OpFlagLo);
1187 Hi = DAG.getNode(LanaiISD::HI, DL, MVT::i32, Hi);
1188 Lo = DAG.getNode(LanaiISD::LO, DL, MVT::i32, Lo);
1189 return DAG.getNode(ISD::OR, DL, MVT::i32, Hi, Lo);
1190 }
1191}
1192
1194 SelectionDAG &DAG) const {
1195 SDLoc DL(Op);
1196 const BlockAddress *BA = cast<BlockAddressSDNode>(Op)->getBlockAddress();
1197
1198 uint8_t OpFlagHi = LanaiII::MO_ABS_HI;
1199 uint8_t OpFlagLo = LanaiII::MO_ABS_LO;
1200
1201 SDValue Hi = DAG.getBlockAddress(BA, MVT::i32, true, OpFlagHi);
1202 SDValue Lo = DAG.getBlockAddress(BA, MVT::i32, true, OpFlagLo);
1203 Hi = DAG.getNode(LanaiISD::HI, DL, MVT::i32, Hi);
1204 Lo = DAG.getNode(LanaiISD::LO, DL, MVT::i32, Lo);
1205 SDValue Result = DAG.getNode(ISD::OR, DL, MVT::i32, Hi, Lo);
1206 return Result;
1207}
1208
1210 SelectionDAG &DAG) const {
1211 SDLoc DL(Op);
1212 JumpTableSDNode *JT = cast<JumpTableSDNode>(Op);
1213
1214 // If the code model is small assume address will fit in 21-bits.
1216 SDValue Small = DAG.getTargetJumpTable(
1217 JT->getIndex(), getPointerTy(DAG.getDataLayout()), LanaiII::MO_NO_FLAG);
1218 return DAG.getNode(ISD::OR, DL, MVT::i32,
1219 DAG.getRegister(Lanai::R0, MVT::i32),
1220 DAG.getNode(LanaiISD::SMALL, DL, MVT::i32, Small));
1221 } else {
1222 uint8_t OpFlagHi = LanaiII::MO_ABS_HI;
1223 uint8_t OpFlagLo = LanaiII::MO_ABS_LO;
1224
1226 JT->getIndex(), getPointerTy(DAG.getDataLayout()), OpFlagHi);
1228 JT->getIndex(), getPointerTy(DAG.getDataLayout()), OpFlagLo);
1229 Hi = DAG.getNode(LanaiISD::HI, DL, MVT::i32, Hi);
1230 Lo = DAG.getNode(LanaiISD::LO, DL, MVT::i32, Lo);
1231 SDValue Result = DAG.getNode(ISD::OR, DL, MVT::i32, Hi, Lo);
1232 return Result;
1233 }
1234}
1235
1237 SelectionDAG &DAG) const {
1238 EVT VT = Op.getValueType();
1239 unsigned VTBits = VT.getSizeInBits();
1240 SDLoc dl(Op);
1241 assert(Op.getNumOperands() == 3 && "Unexpected SHL!");
1242 SDValue ShOpLo = Op.getOperand(0);
1243 SDValue ShOpHi = Op.getOperand(1);
1244 SDValue ShAmt = Op.getOperand(2);
1245
1246 // Performs the following for (ShOpLo + (ShOpHi << 32)) << ShAmt:
1247 // LoBitsForHi = (ShAmt == 0) ? 0 : (ShOpLo >> (32-ShAmt))
1248 // HiBitsForHi = ShOpHi << ShAmt
1249 // Hi = (ShAmt >= 32) ? (ShOpLo << (ShAmt-32)) : (LoBitsForHi | HiBitsForHi)
1250 // Lo = (ShAmt >= 32) ? 0 : (ShOpLo << ShAmt)
1251 // return (Hi << 32) | Lo;
1252
1253 SDValue RevShAmt = DAG.getNode(ISD::SUB, dl, MVT::i32,
1254 DAG.getConstant(VTBits, dl, MVT::i32), ShAmt);
1255 SDValue LoBitsForHi = DAG.getNode(ISD::SRL, dl, VT, ShOpLo, RevShAmt);
1256
1257 // If ShAmt == 0, we just calculated "(SRL ShOpLo, 32)" which is "undef". We
1258 // wanted 0, so CSEL it directly.
1259 SDValue Zero = DAG.getConstant(0, dl, MVT::i32);
1260 SDValue SetCC = DAG.getSetCC(dl, MVT::i32, ShAmt, Zero, ISD::SETEQ);
1261 LoBitsForHi = DAG.getSelect(dl, MVT::i32, SetCC, Zero, LoBitsForHi);
1262
1263 SDValue ExtraShAmt = DAG.getNode(ISD::SUB, dl, MVT::i32, ShAmt,
1264 DAG.getConstant(VTBits, dl, MVT::i32));
1265 SDValue HiBitsForHi = DAG.getNode(ISD::SHL, dl, VT, ShOpHi, ShAmt);
1266 SDValue HiForNormalShift =
1267 DAG.getNode(ISD::OR, dl, VT, LoBitsForHi, HiBitsForHi);
1268
1269 SDValue HiForBigShift = DAG.getNode(ISD::SHL, dl, VT, ShOpLo, ExtraShAmt);
1270
1271 SetCC = DAG.getSetCC(dl, MVT::i32, ExtraShAmt, Zero, ISD::SETGE);
1272 SDValue Hi =
1273 DAG.getSelect(dl, MVT::i32, SetCC, HiForBigShift, HiForNormalShift);
1274
1275 // Lanai shifts of larger than register sizes are wrapped rather than
1276 // clamped, so we can't just emit "lo << b" if b is too big.
1277 SDValue LoForNormalShift = DAG.getNode(ISD::SHL, dl, VT, ShOpLo, ShAmt);
1278 SDValue Lo = DAG.getSelect(
1279 dl, MVT::i32, SetCC, DAG.getConstant(0, dl, MVT::i32), LoForNormalShift);
1280
1281 SDValue Ops[2] = {Lo, Hi};
1282 return DAG.getMergeValues(Ops, dl);
1283}
1284
1286 SelectionDAG &DAG) const {
1287 MVT VT = Op.getSimpleValueType();
1288 unsigned VTBits = VT.getSizeInBits();
1289 SDLoc dl(Op);
1290 SDValue ShOpLo = Op.getOperand(0);
1291 SDValue ShOpHi = Op.getOperand(1);
1292 SDValue ShAmt = Op.getOperand(2);
1293
1294 // Performs the following for a >> b:
1295 // unsigned r_high = a_high >> b;
1296 // r_high = (32 - b <= 0) ? 0 : r_high;
1297 //
1298 // unsigned r_low = a_low >> b;
1299 // r_low = (32 - b <= 0) ? r_high : r_low;
1300 // r_low = (b == 0) ? r_low : r_low | (a_high << (32 - b));
1301 // return (unsigned long long)r_high << 32 | r_low;
1302 // Note: This takes advantage of Lanai's shift behavior to avoid needing to
1303 // mask the shift amount.
1304
1305 SDValue Zero = DAG.getConstant(0, dl, MVT::i32);
1306 SDValue NegatedPlus32 = DAG.getNode(
1307 ISD::SUB, dl, MVT::i32, DAG.getConstant(VTBits, dl, MVT::i32), ShAmt);
1308 SDValue SetCC = DAG.getSetCC(dl, MVT::i32, NegatedPlus32, Zero, ISD::SETLE);
1309
1310 SDValue Hi = DAG.getNode(ISD::SRL, dl, MVT::i32, ShOpHi, ShAmt);
1311 Hi = DAG.getSelect(dl, MVT::i32, SetCC, Zero, Hi);
1312
1313 SDValue Lo = DAG.getNode(ISD::SRL, dl, MVT::i32, ShOpLo, ShAmt);
1314 Lo = DAG.getSelect(dl, MVT::i32, SetCC, Hi, Lo);
1315 SDValue CarryBits =
1316 DAG.getNode(ISD::SHL, dl, MVT::i32, ShOpHi, NegatedPlus32);
1317 SDValue ShiftIsZero = DAG.getSetCC(dl, MVT::i32, ShAmt, Zero, ISD::SETEQ);
1318 Lo = DAG.getSelect(dl, MVT::i32, ShiftIsZero, Lo,
1319 DAG.getNode(ISD::OR, dl, MVT::i32, Lo, CarryBits));
1320
1321 SDValue Ops[2] = {Lo, Hi};
1322 return DAG.getMergeValues(Ops, dl);
1323}
1324
1325// Helper function that checks if N is a null or all ones constant.
1326static inline bool isZeroOrAllOnes(SDValue N, bool AllOnes) {
1328}
1329
1330// Return true if N is conditionally 0 or all ones.
1331// Detects these expressions where cc is an i1 value:
1332//
1333// (select cc 0, y) [AllOnes=0]
1334// (select cc y, 0) [AllOnes=0]
1335// (zext cc) [AllOnes=0]
1336// (sext cc) [AllOnes=0/1]
1337// (select cc -1, y) [AllOnes=1]
1338// (select cc y, -1) [AllOnes=1]
1339//
1340// * AllOnes determines whether to check for an all zero (AllOnes false) or an
1341// all ones operand (AllOnes true).
1342// * Invert is set when N is the all zero/ones constant when CC is false.
1343// * OtherOp is set to the alternative value of N.
1344//
1345// For example, for (select cc X, Y) and AllOnes = 0 if:
1346// * X = 0, Invert = False and OtherOp = Y
1347// * Y = 0, Invert = True and OtherOp = X
1349 bool &Invert, SDValue &OtherOp,
1350 SelectionDAG &DAG) {
1351 switch (N->getOpcode()) {
1352 default:
1353 return false;
1354 case ISD::SELECT: {
1355 CC = N->getOperand(0);
1356 SDValue N1 = N->getOperand(1);
1357 SDValue N2 = N->getOperand(2);
1358 if (isZeroOrAllOnes(N1, AllOnes)) {
1359 Invert = false;
1360 OtherOp = N2;
1361 return true;
1362 }
1363 if (isZeroOrAllOnes(N2, AllOnes)) {
1364 Invert = true;
1365 OtherOp = N1;
1366 return true;
1367 }
1368 return false;
1369 }
1370 case ISD::ZERO_EXTEND: {
1371 // (zext cc) can never be the all ones value.
1372 if (AllOnes)
1373 return false;
1374 CC = N->getOperand(0);
1375 if (CC.getValueType() != MVT::i1)
1376 return false;
1377 SDLoc dl(N);
1378 EVT VT = N->getValueType(0);
1379 OtherOp = DAG.getConstant(1, dl, VT);
1380 Invert = true;
1381 return true;
1382 }
1383 case ISD::SIGN_EXTEND: {
1384 CC = N->getOperand(0);
1385 if (CC.getValueType() != MVT::i1)
1386 return false;
1387 SDLoc dl(N);
1388 EVT VT = N->getValueType(0);
1389 Invert = !AllOnes;
1390 if (AllOnes)
1391 // When looking for an AllOnes constant, N is an sext, and the 'other'
1392 // value is 0.
1393 OtherOp = DAG.getConstant(0, dl, VT);
1394 else
1395 OtherOp = DAG.getAllOnesConstant(dl, VT);
1396 return true;
1397 }
1398 }
1399}
1400
1401// Combine a constant select operand into its use:
1402//
1403// (add (select cc, 0, c), x) -> (select cc, x, (add, x, c))
1404// (sub x, (select cc, 0, c)) -> (select cc, x, (sub, x, c))
1405// (and (select cc, -1, c), x) -> (select cc, x, (and, x, c)) [AllOnes=1]
1406// (or (select cc, 0, c), x) -> (select cc, x, (or, x, c))
1407// (xor (select cc, 0, c), x) -> (select cc, x, (xor, x, c))
1408//
1409// The transform is rejected if the select doesn't have a constant operand that
1410// is null, or all ones when AllOnes is set.
1411//
1412// Also recognize sext/zext from i1:
1413//
1414// (add (zext cc), x) -> (select cc (add x, 1), x)
1415// (add (sext cc), x) -> (select cc (add x, -1), x)
1416//
1417// These transformations eventually create predicated instructions.
1420 bool AllOnes) {
1421 SelectionDAG &DAG = DCI.DAG;
1422 EVT VT = N->getValueType(0);
1423 SDValue NonConstantVal;
1424 SDValue CCOp;
1425 bool SwapSelectOps;
1426 if (!isConditionalZeroOrAllOnes(Slct.getNode(), AllOnes, CCOp, SwapSelectOps,
1427 NonConstantVal, DAG))
1428 return SDValue();
1429
1430 // Slct is now know to be the desired identity constant when CC is true.
1431 SDValue TrueVal = OtherOp;
1432 SDValue FalseVal =
1433 DAG.getNode(N->getOpcode(), SDLoc(N), VT, OtherOp, NonConstantVal);
1434 // Unless SwapSelectOps says CC should be false.
1435 if (SwapSelectOps)
1436 std::swap(TrueVal, FalseVal);
1437
1438 return DAG.getNode(ISD::SELECT, SDLoc(N), VT, CCOp, TrueVal, FalseVal);
1439}
1440
1441// Attempt combineSelectAndUse on each operand of a commutative operator N.
1442static SDValue
1444 bool AllOnes) {
1445 SDValue N0 = N->getOperand(0);
1446 SDValue N1 = N->getOperand(1);
1447 if (N0.getNode()->hasOneUse())
1448 if (SDValue Result = combineSelectAndUse(N, N0, N1, DCI, AllOnes))
1449 return Result;
1450 if (N1.getNode()->hasOneUse())
1451 if (SDValue Result = combineSelectAndUse(N, N1, N0, DCI, AllOnes))
1452 return Result;
1453 return SDValue();
1454}
1455
1456// PerformSUBCombine - Target-specific dag combine xforms for ISD::SUB.
1459 SDValue N0 = N->getOperand(0);
1460 SDValue N1 = N->getOperand(1);
1461
1462 // fold (sub x, (select cc, 0, c)) -> (select cc, x, (sub, x, c))
1463 if (N1.getNode()->hasOneUse())
1464 if (SDValue Result = combineSelectAndUse(N, N1, N0, DCI, /*AllOnes=*/false))
1465 return Result;
1466
1467 return SDValue();
1468}
1469
1471 DAGCombinerInfo &DCI) const {
1472 switch (N->getOpcode()) {
1473 default:
1474 break;
1475 case ISD::ADD:
1476 case ISD::OR:
1477 case ISD::XOR:
1478 return combineSelectAndUseCommutative(N, DCI, /*AllOnes=*/false);
1479 case ISD::AND:
1480 return combineSelectAndUseCommutative(N, DCI, /*AllOnes=*/true);
1481 case ISD::SUB:
1482 return PerformSUBCombine(N, DCI);
1483 }
1484
1485 return SDValue();
1486}
1487
1489 const SDValue Op, KnownBits &Known, const APInt &DemandedElts,
1490 const SelectionDAG &DAG, unsigned Depth) const {
1491 unsigned BitWidth = Known.getBitWidth();
1492 switch (Op.getOpcode()) {
1493 default:
1494 break;
1495 case LanaiISD::SETCC:
1496 Known = KnownBits(BitWidth);
1497 Known.Zero.setBits(1, BitWidth);
1498 break;
1500 KnownBits Known2;
1501 Known = DAG.computeKnownBits(Op->getOperand(0), Depth + 1);
1502 Known2 = DAG.computeKnownBits(Op->getOperand(1), Depth + 1);
1503 Known = Known.intersectWith(Known2);
1504 break;
1505 }
1506}
This file implements a class to represent arbitrary precision integral constant values and operations...
static bool isZeroOrAllOnes(SDValue N, bool AllOnes)
static SDValue PerformSUBCombine(SDNode *N, TargetLowering::DAGCombinerInfo &DCI, const ARMSubtarget *Subtarget)
PerformSUBCombine - Target-specific dag combine xforms for ISD::SUB.
static SDValue combineSelectAndUseCommutative(SDNode *N, bool AllOnes, TargetLowering::DAGCombinerInfo &DCI)
static bool isConditionalZeroOrAllOnes(SDNode *N, bool AllOnes, SDValue &CC, bool &Invert, SDValue &OtherOp, SelectionDAG &DAG)
static SDValue combineSelectAndUse(SDNode *N, SDValue Slct, SDValue OtherOp, TargetLowering::DAGCombinerInfo &DCI, bool AllOnes=false)
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Analysis containing CSE Info
Definition: CSEInfo.cpp:27
#define LLVM_DEBUG(X)
Definition: Debug.h:101
uint64_t Size
#define RegName(no)
static unsigned NumFixedArgs
static bool CC_Lanai32_VarArg(unsigned ValNo, MVT ValVT, MVT LocVT, CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State)
static LPCC::CondCode IntCondCCodeToICC(SDValue CC, const SDLoc &DL, SDValue &RHS, SelectionDAG &DAG)
static cl::opt< int > LanaiLowerConstantMulThreshold("lanai-constant-mul-threshold", cl::Hidden, cl::desc("Maximum number of instruction to generate when lowering constant " "multiplication instead of calling library function [default=14]"), cl::init(14))
#define I(x, y, z)
Definition: MD5.cpp:58
#define G(x, y, z)
Definition: MD5.cpp:56
unsigned const TargetRegisterInfo * TRI
static CodeModel::Model getCodeModel(const PPCSubtarget &S, const TargetMachine &TM, const MachineOperand &MO)
const SmallVectorImpl< MachineOperand > & Cond
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
This file defines the SmallVector class.
This file implements the StringSwitch template, which mimics a switch() statement whose cases are str...
Value * RHS
Value * LHS
Class for arbitrary precision integers.
Definition: APInt.h:78
void setBits(unsigned loBit, unsigned hiBit)
Set the bits from loBit (inclusive) to hiBit (exclusive) to 1.
Definition: APInt.h:1345
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition: ArrayRef.h:41
The address of a basic block.
Definition: Constants.h:890
CCState - This class holds information needed while lowering arguments and return values.
bool CheckReturn(const SmallVectorImpl< ISD::OutputArg > &Outs, CCAssignFn Fn)
CheckReturn - Analyze the return values of a function, returning true if the return can be performed ...
int64_t AllocateStack(unsigned Size, Align Alignment)
AllocateStack - Allocate a chunk of stack space with the specified size and alignment.
void addLoc(const CCValAssign &V)
CCValAssign - Represent assignment of one arg/retval to a location.
bool isRegLoc() const
Register getLocReg() const
LocInfo getLocInfo() const
static CCValAssign getMem(unsigned ValNo, MVT ValVT, int64_t Offset, MVT LocVT, LocInfo HTP, bool IsCustom=false)
bool isMemLoc() const
int64_t getLocMemOffset() const
This is an important base class in LLVM.
Definition: Constant.h:42
This class represents an Operation in the Expression.
unsigned getNumParams() const
Return the number of fixed parameters this function type requires.
Definition: DerivedTypes.h:142
FunctionType * getFunctionType() const
Returns the FunctionType for me.
Definition: Function.h:214
bool hasStructRetAttr() const
Determine if the function returns a structure through first or second pointer argument.
Definition: Function.h:686
const GlobalObject * getAliaseeObject() const
Definition: Globals.cpp:394
This is an important class for using LLVM in a threaded context.
Definition: LLVMContext.h:67
const LanaiRegisterInfo * getRegisterInfo() const override
const char * getTargetNodeName(unsigned Opcode) const override
This method returns the name of a target specific DAG node.
SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const
SDValue LowerJumpTable(SDValue Op, SelectionDAG &DAG) const
SDValue LowerRETURNADDR(SDValue Op, SelectionDAG &DAG) const
SDValue LowerSRL_PARTS(SDValue Op, SelectionDAG &DAG) const
SDValue LowerMUL(SDValue Op, SelectionDAG &DAG) const
void computeKnownBitsForTargetNode(const SDValue Op, KnownBits &Known, const APInt &DemandedElts, const SelectionDAG &DAG, unsigned Depth=0) const override
Determine which of the bits specified in Mask are known to be either zero or one and return them in t...
SDValue LowerSHL_PARTS(SDValue Op, SelectionDAG &DAG) const
SDValue LowerBR_CC(SDValue Op, SelectionDAG &DAG) const
LanaiTargetLowering(const TargetMachine &TM, const LanaiSubtarget &STI)
SDValue LowerVASTART(SDValue Op, SelectionDAG &DAG) const
SDValue LowerGlobalAddress(SDValue Op, SelectionDAG &DAG) const
Register getRegisterByName(const char *RegName, LLT VT, const MachineFunction &MF) const override
Return the register ID of the name passed in.
SDValue LowerSETCC(SDValue Op, SelectionDAG &DAG) const
SDValue LowerSELECT_CC(SDValue Op, SelectionDAG &DAG) const
SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const
SDValue LowerBlockAddress(SDValue Op, SelectionDAG &DAG) const
bool CanLowerReturn(CallingConv::ID CallConv, MachineFunction &MF, bool IsVarArg, const SmallVectorImpl< ISD::OutputArg > &Outs, LLVMContext &Context) const override
This hook should be implemented to check whether the return values described by the Outs array can fi...
ConstraintWeight getSingleConstraintMatchWeight(AsmOperandInfo &Info, const char *Constraint) const override
Examine constraint string and operand type and determine a weight value.
void LowerAsmOperandForConstraint(SDValue Op, StringRef Constraint, std::vector< SDValue > &Ops, SelectionDAG &DAG) const override
Lower the specified operand into the Ops vector.
SDValue LowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const
SDValue PerformDAGCombine(SDNode *N, DAGCombinerInfo &DCI) const override
This method will be invoked for all target nodes and for any target-independent nodes that the target...
std::pair< unsigned, const TargetRegisterClass * > getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const override
Given a physical register constraint (e.g.
SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override
This callback is invoked for operations that are unsupported by the target, which are registered to u...
bool isConstantInSmallSection(const DataLayout &DL, const Constant *CN) const
Return true if this constant should be placed into small data section.
Machine Value Type.
SimpleValueType SimpleTy
static auto integer_valuetypes()
TypeSize getSizeInBits() const
Returns the size of the specified MVT in bits.
The MachineFrameInfo class represents an abstract stack frame until prolog/epilog code is inserted.
int CreateFixedObject(uint64_t Size, int64_t SPOffset, bool IsImmutable, bool isAliased=false)
Create a new object at a fixed location on the stack.
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.
void setFrameAddressIsTaken(bool T)
void setReturnAddressIsTaken(bool s)
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
Register addLiveIn(MCRegister PReg, const TargetRegisterClass *RC)
addLiveIn - Add the specified physical register as a live-in value and create a corresponding virtual...
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
Register createVirtualRegister(const TargetRegisterClass *RegClass, StringRef Name="")
createVirtualRegister - Create and return a new virtual register in the function with the specified r...
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
Represents one node in the SelectionDAG.
bool hasOneUse() const
Return true if there is exactly one use of this node.
Unlike LLVM values, Selection DAG nodes may return multiple values as the result of a computation.
SDNode * getNode() const
get the SDNode which holds the desired result
SDValue getValue(unsigned R) const
This is used to represent a portion of an LLVM function in a low-level Data Dependence DAG representa...
Definition: SelectionDAG.h:226
SDValue getTargetGlobalAddress(const GlobalValue *GV, const SDLoc &DL, EVT VT, int64_t offset=0, unsigned TargetFlags=0)
Definition: SelectionDAG.h:736
SDValue getMergeValues(ArrayRef< SDValue > Ops, const SDLoc &dl)
Create a MERGE_VALUES node from the given operands.
SDVTList getVTList(EVT VT)
Return an SDVTList that represents the list of values specified.
SDValue getAllOnesConstant(const SDLoc &DL, EVT VT, bool IsTarget=false, bool IsOpaque=false)
SDValue getMemcpy(SDValue Chain, const SDLoc &dl, SDValue Dst, SDValue Src, SDValue Size, Align Alignment, bool isVol, bool AlwaysInline, const CallInst *CI, std::optional< bool > OverrideTailCall, MachinePointerInfo DstPtrInfo, MachinePointerInfo SrcPtrInfo, const AAMDNodes &AAInfo=AAMDNodes(), AAResults *AA=nullptr)
SDValue getSetCC(const SDLoc &DL, EVT VT, SDValue LHS, SDValue RHS, ISD::CondCode Cond, SDValue Chain=SDValue(), bool IsSignaling=false)
Helper function to make it easier to build SetCC's if you just have an ISD::CondCode instead of an SD...
SDValue 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 getTargetJumpTable(int JTI, EVT VT, unsigned TargetFlags=0)
Definition: SelectionDAG.h:746
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 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...
const DataLayout & getDataLayout() const
Definition: SelectionDAG.h:487
SDValue getConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isTarget=false, bool isOpaque=false)
Create a ConstantSDNode wrapping a constant value.
SDValue getStore(SDValue Chain, const SDLoc &dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, Align Alignment, MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes())
Helper function to build ISD::STORE nodes.
SDValue 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 ...
SDValue getRegister(unsigned Reg, EVT VT)
SDValue getCopyToReg(SDValue Chain, const SDLoc &dl, unsigned Reg, SDValue N)
Definition: SelectionDAG.h:787
SDValue getBlockAddress(const BlockAddress *BA, EVT VT, int64_t Offset=0, bool isTarget=false, unsigned TargetFlags=0)
SDValue getIntPtrConstant(uint64_t Val, const SDLoc &DL, bool isTarget=false)
SDValue getValueType(EVT)
SDValue getNode(unsigned Opcode, const SDLoc &DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
SDValue getTargetConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isOpaque=false)
Definition: SelectionDAG.h:690
MachineFunction & getMachineFunction() const
Definition: SelectionDAG.h:482
SDValue getCopyFromReg(SDValue Chain, const SDLoc &dl, unsigned Reg, EVT VT)
Definition: SelectionDAG.h:813
SDValue getFrameIndex(int FI, EVT VT, bool isTarget=false)
KnownBits computeKnownBits(SDValue Op, unsigned Depth=0) const
Determine which bits of Op are known to be either zero or one and return them in Known.
SDValue getRegisterMask(const uint32_t *RegMask)
LLVMContext * getContext() const
Definition: SelectionDAG.h:500
SDValue getTargetExternalSymbol(const char *Sym, EVT VT, unsigned TargetFlags=0)
SDValue getTargetConstantPool(const Constant *C, EVT VT, MaybeAlign Align=std::nullopt, int Offset=0, unsigned TargetFlags=0)
Definition: SelectionDAG.h:753
SDValue getEntryNode() const
Return the token chain corresponding to the entry of the function.
Definition: SelectionDAG.h:570
bool empty() const
Definition: SmallVector.h:94
size_t size() const
Definition: SmallVector.h:91
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
Definition: SmallVector.h:586
void push_back(const T &Elt)
Definition: SmallVector.h:426
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
Definition: SmallVector.h:1209
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:50
constexpr size_t size() const
size - Get the string size.
Definition: StringRef.h:137
A switch()-like statement whose cases are string literals.
Definition: StringSwitch.h:44
StringSwitch & Case(StringLiteral S, T Value)
Definition: StringSwitch.h:69
R Default(T Value)
Definition: StringSwitch.h:182
void setOperationAction(unsigned Op, MVT VT, LegalizeAction Action)
Indicate that the specified operation does not work with the specified type and indicate what to do a...
unsigned MaxStoresPerMemcpyOptSize
Likewise for functions with the OptSize attribute.
virtual const TargetRegisterClass * getRegClassFor(MVT VT, bool isDivergent=false) const
Return the register class that should be used for the specified value type.
const TargetMachine & getTargetMachine() const
void setLibcallCallingConv(RTLIB::Libcall Call, CallingConv::ID CC)
Set the CallingConv that should be used for the specified libcall.
void setMaxAtomicSizeInBitsSupported(unsigned SizeInBits)
Set the maximum atomic operation size supported by the backend.
Register getStackPointerRegisterToSaveRestore() const
If a physical register, this specifies the register that llvm.savestack/llvm.restorestack should save...
void setMinFunctionAlignment(Align Alignment)
Set the target's minimum function alignment.
unsigned MaxStoresPerMemsetOptSize
Likewise for functions with the OptSize attribute.
void setBooleanContents(BooleanContent Ty)
Specify how the target extends the result of integer and floating point boolean values from i1 to a w...
unsigned MaxStoresPerMemmove
Specify maximum number of store instructions per memmove call.
void computeRegisterProperties(const TargetRegisterInfo *TRI)
Once all of the register classes are added, this allows us to compute derived properties we expose.
unsigned MaxStoresPerMemmoveOptSize
Likewise for functions with the OptSize attribute.
void addRegisterClass(MVT VT, const TargetRegisterClass *RC)
Add the specified register class as an available regclass for the specified value type.
virtual MVT getPointerTy(const DataLayout &DL, uint32_t AS=0) const
Return the pointer type for the given address space, defaults to the pointer type from the data layou...
void setPrefFunctionAlignment(Align Alignment)
Set the target's preferred function alignment.
unsigned MaxStoresPerMemset
Specify maximum number of store instructions per memset call.
void setMinimumJumpTableEntries(unsigned Val)
Indicate the minimum number of blocks to generate jump tables.
void setStackPointerRegisterToSaveRestore(Register R)
If set to a physical register, this specifies the register that llvm.savestack/llvm....
void setTargetDAGCombine(ArrayRef< ISD::NodeType > NTs)
Targets should invoke this method for each target independent node that they want to provide a custom...
void setLoadExtAction(unsigned ExtType, MVT ValVT, MVT MemVT, LegalizeAction Action)
Indicate that the specified load with extension does not work with the specified type and indicate wh...
unsigned MaxStoresPerMemcpy
Specify maximum number of store instructions per memcpy call.
void setJumpIsExpensive(bool isExpensive=true)
Tells the code generator not to expand logic operations on comparison predicates into separate sequen...
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
virtual ConstraintWeight getSingleConstraintMatchWeight(AsmOperandInfo &info, const char *constraint) const
Examine constraint string and operand type and determine a weight value.
virtual std::pair< unsigned, const TargetRegisterClass * > getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const
Given a physical register constraint (e.g.
virtual void LowerAsmOperandForConstraint(SDValue Op, StringRef Constraint, std::vector< SDValue > &Ops, SelectionDAG &DAG) const
Lower the specified operand into the Ops vector.
Primary interface to the complete machine description for the target machine.
Definition: TargetMachine.h:77
virtual TargetLoweringObjectFile * getObjFileLowering() const
CodeModel::Model getCodeModel() const
Returns the code model.
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
LLVM Value Representation.
Definition: Value.h:74
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
Definition: BitmaskEnum.h:121
@ Fast
Attempts to make calls as fast as possible (e.g.
Definition: CallingConv.h:41
@ C
The default llvm calling convention, compatible with C.
Definition: CallingConv.h:34
@ SETCC
SetCC operator - This evaluates to a true value iff the condition is true.
Definition: ISDOpcodes.h:779
@ STACKRESTORE
STACKRESTORE has two operands, an input chain and a pointer to restore to it returns an output chain.
Definition: ISDOpcodes.h:1194
@ STACKSAVE
STACKSAVE - STACKSAVE has one operand, an input chain.
Definition: ISDOpcodes.h:1190
@ SMUL_LOHI
SMUL_LOHI/UMUL_LOHI - Multiply two integers of type iN, producing a signed/unsigned value of type i[2...
Definition: ISDOpcodes.h:257
@ BSWAP
Byte Swap and Counting operators.
Definition: ISDOpcodes.h:743
@ VAEND
VAEND, VASTART - VAEND and VASTART have three operands: an input chain, pointer, and a SRCVALUE.
Definition: ISDOpcodes.h:1223
@ ADD
Simple integer binary arithmetic operators.
Definition: ISDOpcodes.h:246
@ ANY_EXTEND
ANY_EXTEND - Used for integer types. The high bits are undefined.
Definition: ISDOpcodes.h:813
@ GlobalAddress
Definition: ISDOpcodes.h:78
@ SDIVREM
SDIVREM/UDIVREM - Divide two integers and produce both a quotient and remainder result.
Definition: ISDOpcodes.h:262
@ SIGN_EXTEND
Conversion operators.
Definition: ISDOpcodes.h:804
@ BR_CC
BR_CC - Conditional branch.
Definition: ISDOpcodes.h:1145
@ BR_JT
BR_JT - Jumptable branch.
Definition: ISDOpcodes.h:1124
@ SELECT
Select(COND, TRUEVAL, FALSEVAL).
Definition: ISDOpcodes.h:756
@ VACOPY
VACOPY - VACOPY has 5 operands: an input chain, a destination pointer, a source pointer,...
Definition: ISDOpcodes.h:1219
@ MULHU
MULHU/MULHS - Multiply high - Multiply two integers of type iN, producing an unsigned/signed value of...
Definition: ISDOpcodes.h:673
@ SHL
Shift and rotation operations.
Definition: ISDOpcodes.h:734
@ ZERO_EXTEND
ZERO_EXTEND - Used for integer types, zeroing the new bits.
Definition: ISDOpcodes.h:810
@ SELECT_CC
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
Definition: ISDOpcodes.h:771
@ DYNAMIC_STACKALLOC
DYNAMIC_STACKALLOC - Allocate some number of bytes on the stack aligned to a specified boundary.
Definition: ISDOpcodes.h:1109
@ ConstantPool
Definition: ISDOpcodes.h:82
@ SIGN_EXTEND_INREG
SIGN_EXTEND_INREG - This operator atomically performs a SHL/SRA pair to sign extend a small value in ...
Definition: ISDOpcodes.h:848
@ FRAMEADDR
FRAMEADDR, RETURNADDR - These nodes represent llvm.frameaddress and llvm.returnaddress on the DAG.
Definition: ISDOpcodes.h:100
@ AND
Bitwise operators - logical and, logical or, logical xor.
Definition: ISDOpcodes.h:708
@ TokenFactor
TokenFactor - This node takes multiple tokens as input and produces a single token result.
Definition: ISDOpcodes.h:52
@ TRUNCATE
TRUNCATE - Completely drop the high bits.
Definition: ISDOpcodes.h:816
@ VAARG
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
Definition: ISDOpcodes.h:1214
@ BRCOND
BRCOND - Conditional branch.
Definition: ISDOpcodes.h:1138
@ BlockAddress
Definition: ISDOpcodes.h:84
@ SHL_PARTS
SHL_PARTS/SRA_PARTS/SRL_PARTS - These operators are used for expanded integer shift operations.
Definition: ISDOpcodes.h:793
@ AssertSext
AssertSext, AssertZext - These nodes record if a register contains a value that has already been zero...
Definition: ISDOpcodes.h:61
@ AssertZext
Definition: ISDOpcodes.h:62
CondCode
ISD::CondCode enum - These are ordered carefully to make the bitfields below work out,...
Definition: ISDOpcodes.h:1603
Libcall
RTLIB::Libcall enum - This enum defines all of the runtime library calls the backend can emit.
Reg
All possible values of the reg field in the ModR/M byte.
initializer< Ty > init(const Ty &Val)
Definition: CommandLine.h:443
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
@ Offset
Definition: DWP.cpp:480
bool isNullConstant(SDValue V)
Returns true if V is a constant integer zero.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition: Debug.cpp:163
void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
Definition: Error.cpp:167
raw_fd_ostream & errs()
This returns a reference to a raw_ostream for standard error.
constexpr unsigned BitWidth
Definition: BitmaskEnum.h:191
bool isAllOnesConstant(SDValue V)
Returns true if V is an integer constant with all bits set.
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition: BitVector.h:860
#define N
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition: Alignment.h:39
Extended Value Type.
Definition: ValueTypes.h:35
TypeSize getSizeInBits() const
Return the size of the specified value type in bits.
Definition: ValueTypes.h:359
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
Definition: ValueTypes.h:307
unsigned getBitWidth() const
Get the bit width of this value.
Definition: KnownBits.h:40
KnownBits intersectWith(const KnownBits &RHS) const
Returns KnownBits information that is known to be true for both this and RHS.
Definition: KnownBits.h:300
unsigned getRARegister() const
const uint32_t * getCallPreservedMask(const MachineFunction &MF, CallingConv::ID) const override
This class contains a discriminated union of information about pointers in memory operands,...
static MachinePointerInfo getFixedStack(MachineFunction &MF, int FI, int64_t Offset=0)
Return a MachinePointerInfo record that refers to the specified FrameIndex.
This represents a list of ValueType's that has been intern'd by a SelectionDAG.
This contains information for each constraint that we are lowering.
This structure contains all information that is necessary for lowering calls.
SmallVector< ISD::InputArg, 32 > Ins
SmallVector< ISD::OutputArg, 32 > Outs
SmallVector< SDValue, 32 > OutVals