Lines Matching +full:hi +full:- +full:fi

1 //===-- M68kISelLowering.cpp - M68k DAG Lowering Impl -----------*- C++ -*-===//
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //===----------------------------------------------------------------------===//
13 //===----------------------------------------------------------------------===//
42 #define DEBUG_TYPE "M68k-isel"
55 setStackPointerRegisterToSaveRestore(RegInfo->getStackRegister());
159 // We lower the `atomic-compare-and-swap` to `__sync_val_compare_and_swap`
167 // M68k does not have native read-modify-write support, so expand all of them
313 cast<VTSDNode>(TruncInput.getOperand(1))->getVT() ==
322 int FI = INT_MAX;
324 Register VR = cast<RegisterSDNode>(Arg.getOperand(1))->getReg();
327 MachineInstr *Def = MRI->getVRegDef(VR);
331 if (!TII->isLoadFromStackSlot(*Def, FI))
334 unsigned Opcode = Def->getOpcode();
336 Def->getOperand(1).isFI()) {
337 FI = Def->getOperand(1).getIndex();
350 SDValue Ptr = Ld->getBasePtr();
354 FI = FINode->getIndex();
357 FI = FINode->getIndex();
362 assert(FI != INT_MAX);
363 if (!MFI.isFixedObjectIndex(FI))
366 if (Offset != MFI.getObjectOffset(FI))
372 if (Flags.isZExt() != MFI.isObjectZExt(FI) ||
373 Flags.isSExt() != MFI.isObjectSExt(FI)) {
378 return Bytes == MFI.getObjectSize(FI);
385 int ReturnAddrIndex = FuncInfo->getRAIndex();
391 SlotSize, -(int64_t)SlotSize, false);
392 FuncInfo->setRAIndex(ReturnAddrIndex);
419 SlotSize, (int64_t)FPDiff - SlotSize, false);
457 // Calculate SP offset of interrupt parameter, re-arrange the slot normally
471 Bytes = 1; // Don't create zero-sized stack objects.
472 int FI = MFI.CreateFixedObject(Bytes, Offset, IsImmutable);
475 return DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
477 int FI =
482 MFI.setObjectZExt(FI, true);
484 MFI.setObjectSExt(FI, true);
490 SDValue FIN = DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
493 MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FI));
516 //===----------------------------------------------------------------------===//
518 //===----------------------------------------------------------------------===//
542 auto Attr = MF.getFunction().getFnAttribute("disable-tail-calls");
548 bool IsMustTail = CLI.CB && CLI.CB->isMustTailCall();
595 // Lower arguments at fp - stackoffset + fpdiff.
596 unsigned NumBytesCallerPushed = MFI->getBytesToPopOnReturn();
598 FPDiff = NumBytesCallerPushed - NumBytes;
602 if (FPDiff < MFI->getTCReturnAddrDelta())
603 MFI->setTCReturnAddrDelta(FPDiff);
624 NumBytes - NumBytesToPush, DL);
671 int FI = cast<FrameIndexSDNode>(SpillSlot)->getIndex();
674 MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FI));
685 StackPtr = DAG.getCopyFromReg(Chain, DL, RegInfo->getStackRegister(),
697 // The only time GOT is really needed is for Medium-PIC static data
698 // otherwise we are happy with pc-rel or static references
701 const auto &Forwards = MFI->getForwardedMustTailRegParms();
722 int FI = 0;
736 FI = MF.getFrameInfo().CreateFixedObject(OpSize, Offset, true);
737 FIN = DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
743 StackPtr = DAG.getCopyFromReg(Chain, DL, RegInfo->getStackRegister(),
755 MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FI)));
768 // Build a sequence of copy-to-reg nodes chained together with token chain
777 if (Callee->getOpcode() == ISD::GlobalAddress) {
784 // non-JIT mode.
785 const GlobalValue *GV = G->getGlobal();
786 if (!GV->hasDLLImportStorageClass()) {
790 GV, DL, getPointerTy(DAG.getDataLayout()), G->getOffset(), OpFlags);
810 S->getSymbol(), getPointerTy(DAG.getDataLayout()), OpFlags);
834 // Add a register mask operand representing the call-preserved registers.
835 const uint32_t *Mask = RegInfo->getCallPreservedMask(MF, CallConv);
857 // If this is a call to a struct-return function, the callee
914 //===----------------------------------------------------------------------===//
916 //===----------------------------------------------------------------------===//
957 // If this is an 8 or 16-bit value, it is really passed promoted to 32
978 // If value is passed via pointer - do a load.
997 unsigned Reg = MMFI->getSRetReturnReg();
1001 MMFI->setSRetReturnReg(Reg);
1018 MMFI->setVarArgsFrameIndex(MFI.CreateFixedObject(1, StackSize, true));
1030 MMFI->getForwardedMustTailRegParms();
1045 MMFI->setBytesToPopOnReturn(StackSize); // Callee pops everything.
1047 MMFI->setBytesToPopOnReturn(0); // Callee pops nothing.
1050 MMFI->setBytesToPopOnReturn(4);
1053 MMFI->setArgumentStackSize(StackSize);
1058 //===----------------------------------------------------------------------===//
1060 //===----------------------------------------------------------------------===//
1089 DAG.getTargetConstant(MFI->getBytesToPopOnReturn(), DL, MVT::i32));
1126 // either case MFI->setSRetReturnReg() will have been called.
1127 if (unsigned SRetReg = MFI->getSRetReturnReg()) {
1170 //===----------------------------------------------------------------------===//
1172 //===----------------------------------------------------------------------===//
1180 // On M68k_64 architecture with GOT-style position independent code only
1184 // linkers need this - darwin's dyld for example) If a tail called function
1200 /// Make the stack size align e.g 16n + 12 aligned for a 16-byte align
1207 uint64_t AlignMask = StackAlignment - 1;
1210 if ((Offset & AlignMask) <= (StackAlignment - SlotSize)) {
1212 Offset += ((StackAlignment - SlotSize) - (Offset & AlignMask));
1216 ((~AlignMask) & Offset) + StackAlignment + (StackAlignment - SlotSize);
1232 // If -tailcallopt is specified, make fastcc functions tail-callable.
1248 // Can't do sibcall if stack needs to be dynamically re-aligned. PEI needs to
1251 if (RegInfo->hasStackRealignment(MF))
1280 const uint32_t *CallerPreserved = TRI->getCallPreservedMask(MF, CallerCC);
1282 const uint32_t *CalleePreserved = TRI->getCallPreservedMask(MF, CalleeCC);
1283 if (!TRI->regmaskSubsetEqual(CallerPreserved, CalleePreserved))
1324 // callee-saved registers are restored. These happen to be the same
1360 MF.getInfo<M68kMachineFunctionInfo>()->getBytesToPopOnReturn()) {
1373 //===----------------------------------------------------------------------===//
1375 //===----------------------------------------------------------------------===//
1449 GA->getGlobal(), GA, GA->getValueType(0), GA->getOffset(), TargetFlags);
1476 DAG.getTargetGlobalAddress(GA->getGlobal(), GA, GA->getValueType(0),
1477 GA->getOffset(), M68kII::MO_TLSLD);
1486 DAG.getTargetGlobalAddress(GA->getGlobal(), GA, GA->getValueType(0),
1487 GA->getOffset(), M68kII::MO_TLSIE);
1500 DAG.getTargetGlobalAddress(GA->getGlobal(), GA, GA->getValueType(0),
1501 GA->getOffset(), M68kII::MO_TLSLE);
1510 TLSModel::Model AccessModel = DAG.getTarget().getTLSModel(GA->getGlobal());
1529 // up to 32 bits, but mul only has 16-bit variant. So it's almost
1530 // certainly beneficial to lower 8/16/32-bit mul to their
1531 // add / shifts counterparts. But for 64-bits mul, it might be
1554 EVT VT = N->getValueType(0);
1555 SDValue LHS = N->getOperand(0);
1556 SDValue RHS = N->getOperand(1);
1561 // We don't have 8-bit multiplications, so promote i8 version of U/SMULO
1622 CCR = DAG.getConstant(0, DL, N->getValueType(1));
1644 Overflow = DAG.getNode(M68kISD::SETCC, DL, N->getValueType(1),
1648 return DAG.getNode(ISD::MERGE_VALUES, DL, N->getVTList(), Result, Overflow);
1651 /// Create a BTST (Bit Test) node - Test bit \p BitNo in \p Src and set
1652 /// condition according to equal/not-equal condition code \p CC.
1656 // instruction. Since the shift amount is in-range-or-undefined, we know
1695 if (Known.countMinLeadingZeros() < BitWidth - AndBitWidth)
1702 uint64_t AndRHSVal = AndRHS->getZExtValue();
1750 /// Do a one-to-one translation of a ISD::CondCode to the M68k-specific
1758 if (SetCCOpcode == ISD::SETGT && RHSC->isAllOnes()) {
1759 // X > -1 -> X == 0, jump !sign.
1763 if (SetCCOpcode == ISD::SETLT && RHSC->isZero()) {
1764 // X < 0 -> X == 0, jump on sign.
1767 if (SetCCOpcode == ISD::SETLT && RHSC->getZExtValue() == 1) {
1768 // X < 1 -> X <= 0
1804 llvm_unreachable("Condcode should be pre-legalized away");
1850 for (SDNode::use_iterator UI = Op->use_begin(), UE = Op->use_end(); UI != UE;
1854 if (User->getOpcode() == ISD::TRUNCATE && User->hasOneUse()) {
1856 UOpNo = User->use_begin().getOperandNo();
1857 User = *User->use_begin();
1860 if (User->getOpcode() != ISD::BRCOND && User->getOpcode() != ISD::SETCC &&
1861 !(User->getOpcode() == ISD::SELECT && UOpNo == 0))
1892 switch (Op->getOpcode()) {
1897 if (Op.getNode()->getFlags().hasNoSignedWrap())
1921 // of the arithmetic instruction and use a reduced bit-width instruction.
1924 if (Op->getOpcode() == ISD::TRUNCATE && Op->hasOneUse()) {
1925 SDValue Arith = Op->getOperand(0);
1927 if (Arith->hasOneUse())
1944 // non-casted variable when we check for possible users.
1956 Op->hasOneUse() && isa<ConstantSDNode>(Op->getOperand(1)) &&
1960 unsigned ShAmt = Op->getConstantOperandVal(1);
1964 ? APInt::getHighBitsSet(BitWidth, BitWidth - ShAmt)
1965 : APInt::getLowBitsSet(BitWidth, BitWidth - ShAmt);
1968 Op = DAG.getNode(ISD::AND, DL, VT, Op->getOperand(0),
1977 SDValue Op0 = ArithOp->getOperand(0);
1978 SDValue Op1 = ArithOp->getOperand(1);
1993 // likely to be selected as part of a load-modify-store instruction.
1994 for (const auto *U : Op.getNode()->uses())
1995 if (U->getOpcode() == ISD::STORE)
1998 // Otherwise use a regular CCR-setting instruction.
2033 SDValue WideVal = Op->getOperand(0);
2075 SmallVector<SDValue, 4> Ops(Op->op_begin(), Op->op_begin() + NumOperands);
2144 assert(VT == MVT::i8 && "SetCC type must be 8-bit integer");
2149 ISD::CondCode CC = cast<CondCodeSDNode>(Op.getOperand(2))->get();
2217 M68k::CondCode CC = TranslateIntegerM68kCC(cast<CondCodeSDNode>(Cond)->get());
2234 unsigned Opc = Op.getNode()->getOpcode();
2257 APInt::getHighBitsSet(InBits, InBits - Bits));
2273 // (select (x == 0), -1, y) -> (sign_bit (x - 1)) | y
2274 // (select (x == 0), y, -1) -> ~(sign_bit (x - 1)) | y
2275 // (select (x != 0), y, -1) -> (sign_bit (x - 1)) | y
2276 // (select (x != 0), -1, y) -> ~(sign_bit (x - 1)) | y
2290 // (select (x != 0), -1, 0) -> neg & sbb
2291 // (select (x == 0), 0, -1) -> neg & sbb
2310 SDValue Res = // Res = 0 or -1.
2374 // a < b ? -1 : 0 -> RES = ~setcc_carry
2375 // a < b ? 0 : -1 -> RES = setcc_carry
2376 // a >= b ? -1 : 0 -> RES = setcc_carry
2377 // a >= b ? 0 : -1 -> RES = ~setcc_carry
2379 unsigned CondCode = CC->getAsZExtVal();
2413 const APInt &C = Const->getAPIntValue();
2461 if (cast<CondCodeSDNode>(Cond.getOperand(2))->get() == ISD::SETEQ &&
2495 switch (CC->getAsZExtVal()) {
2502 Cond = Cond.getNode()->getOperand(1);
2539 // have a fall-through edge, because this requires an explicit
2542 Op.getNode()->hasOneUse()) {
2547 SDNode *User = *Op.getNode()->use_begin();
2551 if (User->getOpcode() == ISD::BR) {
2552 SDValue FalseBB = User->getOperand(1);
2554 DAG.UpdateNodeOperands(User, User->getOperand(0), Dest);
2609 MVT VT = Op.getNode()->getSimpleValueType(0);
2665 CP->getConstVal(), PtrVT, CP->getAlign(), CP->getOffset(), OpFlag);
2682 const char *Sym = cast<ExternalSymbolSDNode>(Op)->getSymbol();
2720 const BlockAddress *BA = cast<BlockAddressSDNode>(Op)->getBlockAddress();
2721 int64_t Offset = cast<BlockAddressSDNode>(Op)->getOffset();
2779 // If there was a non-zero offset that we didn't fold, create an explicit
2791 const GlobalValue *GV = cast<GlobalAddressSDNode>(Op)->getGlobal();
2792 int64_t Offset = cast<GlobalAddressSDNode>(Op)->getOffset();
2796 //===----------------------------------------------------------------------===//
2798 //===----------------------------------------------------------------------===//
2814 SDValue Result = DAG.getTargetJumpTable(JT->getIndex(), PtrVT, OpFlag);
2835 return MCSymbolRefExpr::create(MBB->getSymbol(), MCSymbolRefExpr::VK_GOTOFF,
2852 return MCSymbolRefExpr::create(MF->getJTISymbol(JTI, Ctx), Ctx);
2914 int64_t Val = C->getSExtValue();
2920 case 'J': // constant signed 16-bit integer
2924 case 'K': // constant that is NOT in the range of [-0x80, 0x80)
2925 if (Val < -0x80 || Val >= 0x80)
2928 case 'L': // constant integer in the range [-8,-1]
2929 if (Val < 0 && Val >= -8)
2932 case 'M': // constant that is NOT in the range of [-0x100, 0x100]
2933 if (Val < -0x100 || Val >= 0x100)
2972 int64_t Val = C->getSExtValue();
2981 if (!isInt<16>(C->getSExtValue()))
3051 // Return true if it is OK for this CMOV pseudo-opcode to be cascaded
3052 // together with other CMOV pseudo-opcodes into a single basic-block with
3076 for (MachineBasicBlock::iterator miE = BB->end(); miI != miE; ++miI) {
3081 break; // Should have kill-flag - update below.
3086 if (miI == BB->end())
3087 for (const auto *SBB : BB->successors())
3088 if (SBB->isLiveIn(M68k::CCR))
3093 SelectItr->addRegisterKilled(M68k::CCR, TRI);
3104 // diamond control-flow pattern. The incoming instruction knows the
3107 const BasicBlock *BB = MBB->getBasicBlock();
3108 MachineFunction::iterator It = ++MBB->getIterator();
3115 // fallthrough --> Copy0MBB
3117 MachineFunction *F = MBB->getParent();
3119 // This code lowers all pseudo-CMOV instructions. Generally it lowers these
3168 while (NextMIIt != MBB->end() && isCMOVPseudo(*NextMIIt) &&
3169 (NextMIIt->getOperand(3).getImm() == CC ||
3170 NextMIIt->getOperand(3).getImm() == OppCC)) {
3178 if (LastCMOV == &MI && NextMIIt != MBB->end() &&
3179 NextMIIt->getOpcode() == MI.getOpcode() &&
3180 NextMIIt->getOperand(2).getReg() == MI.getOperand(2).getReg() &&
3181 NextMIIt->getOperand(1).getReg() == MI.getOperand(0).getReg() &&
3182 NextMIIt->getOperand(1).isKill()) {
3191 Jcc1MBB = F->CreateMachineBasicBlock(BB);
3192 F->insert(It, Jcc1MBB);
3193 Jcc1MBB->addLiveIn(M68k::CCR);
3196 MachineBasicBlock *Copy0MBB = F->CreateMachineBasicBlock(BB);
3197 MachineBasicBlock *SinkMBB = F->CreateMachineBasicBlock(BB);
3198 F->insert(It, Copy0MBB);
3199 F->insert(It, SinkMBB);
3202 unsigned CallFrameSize = TII->getCallFrameSizeAt(MI);
3203 Copy0MBB->setCallFrameSize(CallFrameSize);
3204 SinkMBB->setCallFrameSize(CallFrameSize);
3211 if (!LastCCRSUser->killsRegister(M68k::CCR, /*TRI=*/nullptr) &&
3213 Copy0MBB->addLiveIn(M68k::CCR);
3214 SinkMBB->addLiveIn(M68k::CCR);
3218 SinkMBB->splice(SinkMBB->begin(), MBB,
3219 std::next(MachineBasicBlock::iterator(LastCMOV)), MBB->end());
3220 SinkMBB->transferSuccessorsAndUpdatePHIs(MBB);
3225 MBB->addSuccessor(Jcc1MBB);
3229 Jcc1MBB->addSuccessor(Copy0MBB);
3230 Jcc1MBB->addSuccessor(SinkMBB);
3232 MBB->addSuccessor(Copy0MBB);
3236 MBB->addSuccessor(SinkMBB);
3240 BuildMI(MBB, DL, TII->get(Opc)).addMBB(SinkMBB);
3244 (M68k::CondCode)CascadedCMOV->getOperand(3).getImm());
3245 BuildMI(Jcc1MBB, DL, TII->get(Opc2)).addMBB(SinkMBB);
3251 Copy0MBB->addSuccessor(SinkMBB);
3259 MachineBasicBlock::iterator SinkInsertionPoint = SinkMBB->begin();
3271 Register DestReg = MIIt->getOperand(0).getReg();
3272 Register Op1Reg = MIIt->getOperand(1).getReg();
3273 Register Op2Reg = MIIt->getOperand(2).getReg();
3278 if (MIIt->getOperand(3).getImm() == OppCC)
3288 BuildMI(*SinkMBB, SinkInsertionPoint, DL, TII->get(M68k::PHI), DestReg)
3304 DL, TII->get(TargetOpcode::COPY),
3305 CascadedCMOV->getOperand(0).getReg())
3307 CascadedCMOV->eraseFromParent();
3312 (MIIt++)->eraseFromParent();
3320 llvm_unreachable("Cannot lower Segmented Stack Alloca with stack-split on");
3343 const Value *SV = cast<SrcValueSDNode>(Op.getOperand(2))->getValue();
3348 SDValue FR = DAG.getFrameIndex(FuncInfo->getVarArgsFrameIndex(), PtrVT);
3392 EVT VT = Node->getValueType(0);
3420 DAG.getConstant(-(uint64_t)Align, DL, VT));
3434 SDValue Hi = Op.getOperand(1);
3438 // if Shamt - register size < 0: // Shamt < register size
3440 // Hi = (Hi << Shamt) | ((Lo >>u 1) >>u (register size - 1 ^ Shamt))
3443 // Hi = Lo << (Shamt - register size)
3447 SDValue MinusRegisterSize = DAG.getConstant(-32, DL, VT);
3448 SDValue RegisterSizeMinus1 = DAG.getConstant(32 - 1, DL, VT);
3458 SDValue ShiftLeftHi = DAG.getNode(ISD::SHL, DL, VT, Hi, Shamt);
3466 Hi = DAG.getNode(ISD::SELECT, DL, VT, CC, HiTrue, HiFalse);
3468 return DAG.getMergeValues({Lo, Hi}, DL);
3475 SDValue Hi = Op.getOperand(1);
3480 // if Shamt - register size < 0: // Shamt < register size
3481 // Lo = (Lo >>u Shamt) | ((Hi << 1) << (register size - 1 ^ Shamt))
3482 // Hi = Hi >>s Shamt
3484 // Lo = Hi >>s (Shamt - register size);
3485 // Hi = Hi >>s (register size - 1)
3488 // if Shamt - register size < 0: // Shamt < register size
3489 // Lo = (Lo >>u Shamt) | ((Hi << 1) << (register size - 1 ^ Shamt))
3490 // Hi = Hi >>u Shamt
3492 // Lo = Hi >>u (Shamt - register size);
3493 // Hi = 0;
3499 SDValue MinusRegisterSize = DAG.getConstant(-32, DL, VT);
3500 SDValue RegisterSizeMinus1 = DAG.getConstant(32 - 1, DL, VT);
3507 SDValue ShiftLeftHi1 = DAG.getNode(ISD::SHL, DL, VT, Hi, One);
3511 SDValue HiTrue = DAG.getNode(ShiftRightOp, DL, VT, Hi, Shamt);
3513 DAG.getNode(ShiftRightOp, DL, VT, Hi, ShamtMinusRegisterSize);
3515 IsSRA ? DAG.getNode(ISD::SRA, DL, VT, Hi, RegisterSizeMinus1) : Zero;
3521 Hi = DAG.getNode(ISD::SELECT, DL, VT, CC, HiTrue, HiFalse);
3523 return DAG.getMergeValues({Lo, Hi}, DL);
3526 //===----------------------------------------------------------------------===//
3528 //===----------------------------------------------------------------------===//
3535 // When legalizing carry, we create carries via add X, -1
3577 M68k::CondCode CC = M68k::CondCode(N->getConstantOperandVal(0));
3578 SDValue CCR = N->getOperand(1);
3589 M68k::CondCode CC = M68k::CondCode(N->getConstantOperandVal(2));
3590 SDValue CCR = N->getOperand(3);
3597 return DAG.getNode(M68kISD::BRCOND, DL, N->getVTList(), N->getOperand(0),
3598 N->getOperand(1), Cond, Flags);
3605 if (SDValue Flags = combineCarryThroughADD(N->getOperand(2))) {
3606 MVT VT = N->getSimpleValueType(0);
3608 return DAG.getNode(M68kISD::SUBX, SDLoc(N), VTs, N->getOperand(0),
3609 N->getOperand(1), Flags);
3618 if (SDValue Flags = combineCarryThroughADD(N->getOperand(2))) {
3619 MVT VT = N->getSimpleValueType(0);
3621 return DAG.getNode(M68kISD::ADDX, SDLoc(N), VTs, N->getOperand(0),
3622 N->getOperand(1), Flags);
3631 switch (N->getOpcode()) {
3645 //===----------------------------------------------------------------------===//
3647 //===----------------------------------------------------------------------===//