[ORC] Add std::tuple support to SimplePackedSerialization.
[llvm-project.git] / llvm / lib / Target / M68k / M68kFrameLowering.cpp
blob66ea6ae38f430fca840254c0c17e2945e3315f08
1 //===-- M68kFrameLowering.cpp - M68k Frame Information ------*- C++ -*-===//
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 /// \file
10 /// This file contains the M68k implementation of TargetFrameLowering class.
11 ///
12 //===----------------------------------------------------------------------===//
14 #include "M68kFrameLowering.h"
16 #include "M68kInstrBuilder.h"
17 #include "M68kInstrInfo.h"
18 #include "M68kMachineFunction.h"
19 #include "M68kSubtarget.h"
21 #include "llvm/ADT/SmallSet.h"
22 #include "llvm/CodeGen/MachineFrameInfo.h"
23 #include "llvm/CodeGen/MachineFunction.h"
24 #include "llvm/CodeGen/MachineInstrBuilder.h"
25 #include "llvm/CodeGen/MachineModuleInfo.h"
26 #include "llvm/CodeGen/MachineRegisterInfo.h"
27 #include "llvm/IR/DataLayout.h"
28 #include "llvm/IR/Function.h"
29 #include "llvm/Support/Alignment.h"
30 #include "llvm/Support/CommandLine.h"
31 #include "llvm/Target/TargetMachine.h"
32 #include "llvm/Target/TargetOptions.h"
34 using namespace llvm;
36 M68kFrameLowering::M68kFrameLowering(const M68kSubtarget &STI, Align Alignment)
37 : TargetFrameLowering(StackGrowsDown, Alignment, -4), STI(STI),
38 TII(*STI.getInstrInfo()), TRI(STI.getRegisterInfo()) {
39 SlotSize = STI.getSlotSize();
40 StackPtr = TRI->getStackRegister();
43 bool M68kFrameLowering::hasFP(const MachineFunction &MF) const {
44 const MachineFrameInfo &MFI = MF.getFrameInfo();
45 const TargetRegisterInfo *TRI = STI.getRegisterInfo();
47 return MF.getTarget().Options.DisableFramePointerElim(MF) ||
48 MFI.hasVarSizedObjects() || MFI.isFrameAddressTaken() ||
49 TRI->hasStackRealignment(MF);
52 // FIXME Make sure no other factors prevent us from reserving call frame
53 bool M68kFrameLowering::hasReservedCallFrame(const MachineFunction &MF) const {
54 return !MF.getFrameInfo().hasVarSizedObjects() &&
55 !MF.getInfo<M68kMachineFunctionInfo>()->getHasPushSequences();
58 bool M68kFrameLowering::canSimplifyCallFramePseudos(
59 const MachineFunction &MF) const {
60 return hasReservedCallFrame(MF) ||
61 (hasFP(MF) && !TRI->hasStackRealignment(MF)) ||
62 TRI->hasBasePointer(MF);
65 bool M68kFrameLowering::needsFrameIndexResolution(
66 const MachineFunction &MF) const {
67 return MF.getFrameInfo().hasStackObjects() ||
68 MF.getInfo<M68kMachineFunctionInfo>()->getHasPushSequences();
71 // NOTE: this only has a subset of the full frame index logic. In
72 // particular, the FI < 0 and AfterFPPop logic is handled in
73 // M68kRegisterInfo::eliminateFrameIndex, but not here. Possibly
74 // (probably?) it should be moved into here.
75 StackOffset
76 M68kFrameLowering::getFrameIndexReference(const MachineFunction &MF, int FI,
77 Register &FrameReg) const {
78 const MachineFrameInfo &MFI = MF.getFrameInfo();
80 // We can't calculate offset from frame pointer if the stack is realigned,
81 // so enforce usage of stack/base pointer. The base pointer is used when we
82 // have dynamic allocas in addition to dynamic realignment.
83 if (TRI->hasBasePointer(MF))
84 FrameReg = TRI->getBaseRegister();
85 else if (TRI->hasStackRealignment(MF))
86 FrameReg = TRI->getStackRegister();
87 else
88 FrameReg = TRI->getFrameRegister(MF);
90 // Offset will hold the offset from the stack pointer at function entry to the
91 // object.
92 // We need to factor in additional offsets applied during the prologue to the
93 // frame, base, and stack pointer depending on which is used.
94 int Offset = MFI.getObjectOffset(FI) - getOffsetOfLocalArea();
95 const M68kMachineFunctionInfo *MMFI = MF.getInfo<M68kMachineFunctionInfo>();
96 uint64_t StackSize = MFI.getStackSize();
97 bool HasFP = hasFP(MF);
99 // TODO: Support tail calls
100 if (TRI->hasBasePointer(MF)) {
101 assert(HasFP && "VLAs and dynamic stack realign, but no FP?!");
102 if (FI < 0) {
103 // Skip the saved FP.
104 return StackOffset::getFixed(Offset + SlotSize);
107 assert((-(Offset + StackSize)) % MFI.getObjectAlign(FI).value() == 0);
108 return StackOffset::getFixed(Offset + StackSize);
110 if (TRI->hasStackRealignment(MF)) {
111 if (FI < 0) {
112 // Skip the saved FP.
113 return StackOffset::getFixed(Offset + SlotSize);
116 assert((-(Offset + StackSize)) % MFI.getObjectAlign(FI).value() == 0);
117 return StackOffset::getFixed(Offset + StackSize);
120 if (!HasFP)
121 return StackOffset::getFixed(Offset + StackSize);
123 // Skip the saved FP.
124 Offset += SlotSize;
126 // Skip the RETADDR move area
127 int TailCallReturnAddrDelta = MMFI->getTCReturnAddrDelta();
128 if (TailCallReturnAddrDelta < 0)
129 Offset -= TailCallReturnAddrDelta;
131 return StackOffset::getFixed(Offset);
134 /// Return a caller-saved register that isn't live
135 /// when it reaches the "return" instruction. We can then pop a stack object
136 /// to this register without worry about clobbering it.
137 static unsigned findDeadCallerSavedReg(MachineBasicBlock &MBB,
138 MachineBasicBlock::iterator &MBBI,
139 const M68kRegisterInfo *TRI) {
140 const MachineFunction *MF = MBB.getParent();
141 if (MF->callsEHReturn())
142 return 0;
144 const TargetRegisterClass &AvailableRegs = *TRI->getRegsForTailCall(*MF);
146 if (MBBI == MBB.end())
147 return 0;
149 switch (MBBI->getOpcode()) {
150 default:
151 return 0;
152 case TargetOpcode::PATCHABLE_RET:
153 case M68k::RET: {
154 SmallSet<uint16_t, 8> Uses;
156 for (unsigned i = 0, e = MBBI->getNumOperands(); i != e; ++i) {
157 MachineOperand &MO = MBBI->getOperand(i);
158 if (!MO.isReg() || MO.isDef())
159 continue;
160 unsigned Reg = MO.getReg();
161 if (!Reg)
162 continue;
163 for (MCRegAliasIterator AI(Reg, TRI, true); AI.isValid(); ++AI)
164 Uses.insert(*AI);
167 for (auto CS : AvailableRegs)
168 if (!Uses.count(CS))
169 return CS;
173 return 0;
176 static bool isRegLiveIn(MachineBasicBlock &MBB, unsigned Reg) {
177 return llvm::any_of(MBB.liveins(),
178 [Reg](MachineBasicBlock::RegisterMaskPair RegMask) {
179 return RegMask.PhysReg == Reg;
183 uint64_t
184 M68kFrameLowering::calculateMaxStackAlign(const MachineFunction &MF) const {
185 const MachineFrameInfo &MFI = MF.getFrameInfo();
186 uint64_t MaxAlign = MFI.getMaxAlign().value(); // Desired stack alignment.
187 unsigned StackAlign = getStackAlignment(); // ABI alignment
188 if (MF.getFunction().hasFnAttribute("stackrealign")) {
189 if (MFI.hasCalls())
190 MaxAlign = (StackAlign > MaxAlign) ? StackAlign : MaxAlign;
191 else if (MaxAlign < SlotSize)
192 MaxAlign = SlotSize;
194 return MaxAlign;
197 void M68kFrameLowering::BuildStackAlignAND(MachineBasicBlock &MBB,
198 MachineBasicBlock::iterator MBBI,
199 const DebugLoc &DL, unsigned Reg,
200 uint64_t MaxAlign) const {
201 uint64_t Val = -MaxAlign;
202 unsigned AndOp = M68k::AND32di;
203 unsigned MovOp = M68k::MOV32rr;
205 // This function is normally used with SP which is Address Register, but AND,
206 // or any other logical instructions in M68k do not support ARs so we need
207 // to use a temp Data Register to perform the op.
208 unsigned Tmp = M68k::D0;
210 BuildMI(MBB, MBBI, DL, TII.get(MovOp), Tmp)
211 .addReg(Reg)
212 .setMIFlag(MachineInstr::FrameSetup);
214 MachineInstr *MI = BuildMI(MBB, MBBI, DL, TII.get(AndOp), Tmp)
215 .addReg(Tmp)
216 .addImm(Val)
217 .setMIFlag(MachineInstr::FrameSetup);
219 // The CCR implicit def is dead.
220 MI->getOperand(3).setIsDead();
222 BuildMI(MBB, MBBI, DL, TII.get(MovOp), Reg)
223 .addReg(Tmp)
224 .setMIFlag(MachineInstr::FrameSetup);
227 MachineBasicBlock::iterator M68kFrameLowering::eliminateCallFramePseudoInstr(
228 MachineFunction &MF, MachineBasicBlock &MBB,
229 MachineBasicBlock::iterator I) const {
230 bool ReserveCallFrame = hasReservedCallFrame(MF);
231 unsigned Opcode = I->getOpcode();
232 bool IsDestroy = Opcode == TII.getCallFrameDestroyOpcode();
233 DebugLoc DL = I->getDebugLoc();
234 uint64_t Amount = !ReserveCallFrame ? I->getOperand(0).getImm() : 0;
235 uint64_t InternalAmt = (IsDestroy && Amount) ? I->getOperand(1).getImm() : 0;
236 I = MBB.erase(I);
238 if (!ReserveCallFrame) {
239 // If the stack pointer can be changed after prologue, turn the
240 // adjcallstackup instruction into a 'sub %SP, <amt>' and the
241 // adjcallstackdown instruction into 'add %SP, <amt>'
243 // We need to keep the stack aligned properly. To do this, we round the
244 // amount of space needed for the outgoing arguments up to the next
245 // alignment boundary.
246 unsigned StackAlign = getStackAlignment();
247 Amount = alignTo(Amount, StackAlign);
249 MachineModuleInfo &MMI = MF.getMMI();
250 const auto &Fn = MF.getFunction();
251 bool DwarfCFI = MMI.hasDebugInfo() || Fn.needsUnwindTableEntry();
253 // If we have any exception handlers in this function, and we adjust
254 // the SP before calls, we may need to indicate this to the unwinder
255 // using GNU_ARGS_SIZE. Note that this may be necessary even when
256 // Amount == 0, because the preceding function may have set a non-0
257 // GNU_ARGS_SIZE.
258 // TODO: We don't need to reset this between subsequent functions,
259 // if it didn't change.
260 bool HasDwarfEHHandlers = !MF.getLandingPads().empty();
262 if (HasDwarfEHHandlers && !IsDestroy &&
263 MF.getInfo<M68kMachineFunctionInfo>()->getHasPushSequences()) {
264 BuildCFI(MBB, I, DL,
265 MCCFIInstruction::createGnuArgsSize(nullptr, Amount));
268 if (Amount == 0)
269 return I;
271 // Factor out the amount that gets handled inside the sequence
272 // (Pushes of argument for frame setup, callee pops for frame destroy)
273 Amount -= InternalAmt;
275 // TODO: This is needed only if we require precise CFA.
276 // If this is a callee-pop calling convention, emit a CFA adjust for
277 // the amount the callee popped.
278 if (IsDestroy && InternalAmt && DwarfCFI && !hasFP(MF))
279 BuildCFI(MBB, I, DL,
280 MCCFIInstruction::createAdjustCfaOffset(nullptr, -InternalAmt));
282 // Add Amount to SP to destroy a frame, or subtract to setup.
283 int64_t StackAdjustment = IsDestroy ? Amount : -Amount;
284 int64_t CfaAdjustment = -StackAdjustment;
286 if (StackAdjustment) {
287 // Merge with any previous or following adjustment instruction. Note: the
288 // instructions merged with here do not have CFI, so their stack
289 // adjustments do not feed into CfaAdjustment.
290 StackAdjustment += mergeSPUpdates(MBB, I, true);
291 StackAdjustment += mergeSPUpdates(MBB, I, false);
293 if (StackAdjustment) {
294 BuildStackAdjustment(MBB, I, DL, StackAdjustment, false);
298 if (DwarfCFI && !hasFP(MF)) {
299 // If we don't have FP, but need to generate unwind information,
300 // we need to set the correct CFA offset after the stack adjustment.
301 // How much we adjust the CFA offset depends on whether we're emitting
302 // CFI only for EH purposes or for debugging. EH only requires the CFA
303 // offset to be correct at each call site, while for debugging we want
304 // it to be more precise.
306 // TODO: When not using precise CFA, we also need to adjust for the
307 // InternalAmt here.
308 if (CfaAdjustment) {
309 BuildCFI(
310 MBB, I, DL,
311 MCCFIInstruction::createAdjustCfaOffset(nullptr, CfaAdjustment));
315 return I;
318 if (IsDestroy && InternalAmt) {
319 // If we are performing frame pointer elimination and if the callee pops
320 // something off the stack pointer, add it back. We do this until we have
321 // more advanced stack pointer tracking ability.
322 // We are not tracking the stack pointer adjustment by the callee, so make
323 // sure we restore the stack pointer immediately after the call, there may
324 // be spill code inserted between the CALL and ADJCALLSTACKUP instructions.
325 MachineBasicBlock::iterator CI = I;
326 MachineBasicBlock::iterator B = MBB.begin();
327 while (CI != B && !std::prev(CI)->isCall())
328 --CI;
329 BuildStackAdjustment(MBB, CI, DL, -InternalAmt, /*InEpilogue=*/false);
332 return I;
335 /// Emit a series of instructions to increment / decrement the stack pointer by
336 /// a constant value.
337 void M68kFrameLowering::emitSPUpdate(MachineBasicBlock &MBB,
338 MachineBasicBlock::iterator &MBBI,
339 int64_t NumBytes, bool InEpilogue) const {
340 bool IsSub = NumBytes < 0;
341 uint64_t Offset = IsSub ? -NumBytes : NumBytes;
343 uint64_t Chunk = (1LL << 31) - 1;
344 DebugLoc DL = MBB.findDebugLoc(MBBI);
346 while (Offset) {
347 if (Offset > Chunk) {
348 // Rather than emit a long series of instructions for large offsets,
349 // load the offset into a register and do one sub/add
350 Register Reg;
352 if (IsSub && !isRegLiveIn(MBB, M68k::D0))
353 Reg = M68k::D0;
354 else
355 Reg = findDeadCallerSavedReg(MBB, MBBI, TRI);
357 if (Reg) {
358 unsigned Opc = M68k::MOV32ri;
359 BuildMI(MBB, MBBI, DL, TII.get(Opc), Reg).addImm(Offset);
360 Opc = IsSub ? M68k::SUB32ar : M68k::ADD32ar;
361 MachineInstr *MI = BuildMI(MBB, MBBI, DL, TII.get(Opc), StackPtr)
362 .addReg(StackPtr)
363 .addReg(Reg);
364 // ??? still no CCR
365 MI->getOperand(3).setIsDead(); // The CCR implicit def is dead.
366 Offset = 0;
367 continue;
371 uint64_t ThisVal = std::min(Offset, Chunk);
373 MachineInstrBuilder MI = BuildStackAdjustment(
374 MBB, MBBI, DL, IsSub ? -ThisVal : ThisVal, InEpilogue);
375 if (IsSub)
376 MI.setMIFlag(MachineInstr::FrameSetup);
377 else
378 MI.setMIFlag(MachineInstr::FrameDestroy);
380 Offset -= ThisVal;
384 int M68kFrameLowering::mergeSPUpdates(MachineBasicBlock &MBB,
385 MachineBasicBlock::iterator &MBBI,
386 bool MergeWithPrevious) const {
387 if ((MergeWithPrevious && MBBI == MBB.begin()) ||
388 (!MergeWithPrevious && MBBI == MBB.end()))
389 return 0;
391 MachineBasicBlock::iterator PI = MergeWithPrevious ? std::prev(MBBI) : MBBI;
392 MachineBasicBlock::iterator NI =
393 MergeWithPrevious ? nullptr : std::next(MBBI);
394 unsigned Opc = PI->getOpcode();
395 int Offset = 0;
397 if (!MergeWithPrevious && NI != MBB.end() &&
398 NI->getOpcode() == TargetOpcode::CFI_INSTRUCTION) {
399 // Don't merge with the next instruction if it has CFI.
400 return Offset;
403 if (Opc == M68k::ADD32ai && PI->getOperand(0).getReg() == StackPtr) {
404 assert(PI->getOperand(1).getReg() == StackPtr);
405 Offset += PI->getOperand(2).getImm();
406 MBB.erase(PI);
407 if (!MergeWithPrevious)
408 MBBI = NI;
409 } else if (Opc == M68k::SUB32ai && PI->getOperand(0).getReg() == StackPtr) {
410 assert(PI->getOperand(1).getReg() == StackPtr);
411 Offset -= PI->getOperand(2).getImm();
412 MBB.erase(PI);
413 if (!MergeWithPrevious)
414 MBBI = NI;
417 return Offset;
420 MachineInstrBuilder M68kFrameLowering::BuildStackAdjustment(
421 MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
422 const DebugLoc &DL, int64_t Offset, bool InEpilogue) const {
423 assert(Offset != 0 && "zero offset stack adjustment requested");
425 // TODO can `lea` be used to adjust stack?
427 bool IsSub = Offset < 0;
428 uint64_t AbsOffset = IsSub ? -Offset : Offset;
429 unsigned Opc = IsSub ? M68k::SUB32ai : M68k::ADD32ai;
431 MachineInstrBuilder MI = BuildMI(MBB, MBBI, DL, TII.get(Opc), StackPtr)
432 .addReg(StackPtr)
433 .addImm(AbsOffset);
434 // FIXME Update CCR as well. For now we just
435 // conservatively say CCR implicit def is dead
436 MI->getOperand(3).setIsDead();
437 return MI;
440 void M68kFrameLowering::BuildCFI(MachineBasicBlock &MBB,
441 MachineBasicBlock::iterator MBBI,
442 const DebugLoc &DL,
443 const MCCFIInstruction &CFIInst) const {
444 MachineFunction &MF = *MBB.getParent();
445 unsigned CFIIndex = MF.addFrameInst(CFIInst);
446 BuildMI(MBB, MBBI, DL, TII.get(TargetOpcode::CFI_INSTRUCTION))
447 .addCFIIndex(CFIIndex);
450 void M68kFrameLowering::emitPrologueCalleeSavedFrameMoves(
451 MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
452 const DebugLoc &DL) const {
453 MachineFunction &MF = *MBB.getParent();
454 MachineFrameInfo &MFI = MF.getFrameInfo();
455 MachineModuleInfo &MMI = MF.getMMI();
456 const MCRegisterInfo *MRI = MMI.getContext().getRegisterInfo();
458 // Add callee saved registers to move list.
459 const auto &CSI = MFI.getCalleeSavedInfo();
460 if (CSI.empty())
461 return;
463 // Calculate offsets.
464 for (const auto &I : CSI) {
465 int64_t Offset = MFI.getObjectOffset(I.getFrameIdx());
466 unsigned Reg = I.getReg();
468 unsigned DwarfReg = MRI->getDwarfRegNum(Reg, true);
469 BuildCFI(MBB, MBBI, DL,
470 MCCFIInstruction::createOffset(nullptr, DwarfReg, Offset));
474 void M68kFrameLowering::emitPrologue(MachineFunction &MF,
475 MachineBasicBlock &MBB) const {
476 assert(&STI == &MF.getSubtarget<M68kSubtarget>() &&
477 "MF used frame lowering for wrong subtarget");
479 MachineBasicBlock::iterator MBBI = MBB.begin();
480 MachineFrameInfo &MFI = MF.getFrameInfo();
481 const auto &Fn = MF.getFunction();
482 MachineModuleInfo &MMI = MF.getMMI();
483 M68kMachineFunctionInfo *MMFI = MF.getInfo<M68kMachineFunctionInfo>();
484 uint64_t MaxAlign = calculateMaxStackAlign(MF); // Desired stack alignment.
485 uint64_t StackSize = MFI.getStackSize(); // Number of bytes to allocate.
486 bool HasFP = hasFP(MF);
487 bool NeedsDwarfCFI = MMI.hasDebugInfo() || Fn.needsUnwindTableEntry();
488 unsigned FramePtr = TRI->getFrameRegister(MF);
489 const unsigned MachineFramePtr = FramePtr;
490 unsigned BasePtr = TRI->getBaseRegister();
492 // Debug location must be unknown since the first debug location is used
493 // to determine the end of the prologue.
494 DebugLoc DL;
496 // Add RETADDR move area to callee saved frame size.
497 int TailCallReturnAddrDelta = MMFI->getTCReturnAddrDelta();
499 if (TailCallReturnAddrDelta < 0) {
500 MMFI->setCalleeSavedFrameSize(MMFI->getCalleeSavedFrameSize() -
501 TailCallReturnAddrDelta);
504 // Insert stack pointer adjustment for later moving of return addr. Only
505 // applies to tail call optimized functions where the callee argument stack
506 // size is bigger than the callers.
507 if (TailCallReturnAddrDelta < 0) {
508 BuildStackAdjustment(MBB, MBBI, DL, TailCallReturnAddrDelta,
509 /*InEpilogue=*/false)
510 .setMIFlag(MachineInstr::FrameSetup);
513 // Mapping for machine moves:
515 // DST: VirtualFP AND
516 // SRC: VirtualFP => DW_CFA_def_cfa_offset
517 // ELSE => DW_CFA_def_cfa
519 // SRC: VirtualFP AND
520 // DST: Register => DW_CFA_def_cfa_register
522 // ELSE
523 // OFFSET < 0 => DW_CFA_offset_extended_sf
524 // REG < 64 => DW_CFA_offset + Reg
525 // ELSE => DW_CFA_offset_extended
527 uint64_t NumBytes = 0;
528 int stackGrowth = -SlotSize;
530 if (HasFP) {
531 // Calculate required stack adjustment.
532 uint64_t FrameSize = StackSize - SlotSize;
533 // If required, include space for extra hidden slot for stashing base
534 // pointer.
535 if (MMFI->getRestoreBasePointer())
536 FrameSize += SlotSize;
538 NumBytes = FrameSize - MMFI->getCalleeSavedFrameSize();
540 // Callee-saved registers are pushed on stack before the stack is realigned.
541 if (TRI->hasStackRealignment(MF))
542 NumBytes = alignTo(NumBytes, MaxAlign);
544 // Get the offset of the stack slot for the FP register, which is
545 // guaranteed to be the last slot by processFunctionBeforeFrameFinalized.
546 // Update the frame offset adjustment.
547 MFI.setOffsetAdjustment(-NumBytes);
549 // Save FP into the appropriate stack slot.
550 BuildMI(MBB, MBBI, DL, TII.get(M68k::PUSH32r))
551 .addReg(MachineFramePtr, RegState::Kill)
552 .setMIFlag(MachineInstr::FrameSetup);
554 if (NeedsDwarfCFI) {
555 // Mark the place where FP was saved.
556 // Define the current CFA rule to use the provided offset.
557 assert(StackSize);
558 BuildCFI(MBB, MBBI, DL,
559 MCCFIInstruction::cfiDefCfaOffset(nullptr, 2 * stackGrowth));
561 // Change the rule for the FramePtr to be an "offset" rule.
562 int DwarfFramePtr = TRI->getDwarfRegNum(MachineFramePtr, true);
563 assert(DwarfFramePtr > 0);
564 BuildCFI(MBB, MBBI, DL,
565 MCCFIInstruction::createOffset(nullptr, DwarfFramePtr,
566 2 * stackGrowth));
569 // Update FP with the new base value.
570 BuildMI(MBB, MBBI, DL, TII.get(M68k::MOV32aa), FramePtr)
571 .addReg(StackPtr)
572 .setMIFlag(MachineInstr::FrameSetup);
574 if (NeedsDwarfCFI) {
575 // Mark effective beginning of when frame pointer becomes valid.
576 // Define the current CFA to use the FP register.
577 unsigned DwarfFramePtr = TRI->getDwarfRegNum(MachineFramePtr, true);
578 BuildCFI(MBB, MBBI, DL,
579 MCCFIInstruction::createDefCfaRegister(nullptr, DwarfFramePtr));
582 // Mark the FramePtr as live-in in every block. Don't do this again for
583 // funclet prologues.
584 for (MachineBasicBlock &EveryMBB : MF)
585 EveryMBB.addLiveIn(MachineFramePtr);
586 } else {
587 NumBytes = StackSize - MMFI->getCalleeSavedFrameSize();
590 // Skip the callee-saved push instructions.
591 bool PushedRegs = false;
592 int StackOffset = 2 * stackGrowth;
594 while (MBBI != MBB.end() && MBBI->getFlag(MachineInstr::FrameSetup) &&
595 MBBI->getOpcode() == M68k::PUSH32r) {
596 PushedRegs = true;
597 ++MBBI;
599 if (!HasFP && NeedsDwarfCFI) {
600 // Mark callee-saved push instruction.
601 // Define the current CFA rule to use the provided offset.
602 assert(StackSize);
603 BuildCFI(MBB, MBBI, DL,
604 MCCFIInstruction::cfiDefCfaOffset(nullptr, StackOffset));
605 StackOffset += stackGrowth;
609 // Realign stack after we pushed callee-saved registers (so that we'll be
610 // able to calculate their offsets from the frame pointer).
611 if (TRI->hasStackRealignment(MF)) {
612 assert(HasFP && "There should be a frame pointer if stack is realigned.");
613 BuildStackAlignAND(MBB, MBBI, DL, StackPtr, MaxAlign);
616 // If there is an SUB32ri of SP immediately before this instruction, merge
617 // the two. This can be the case when tail call elimination is enabled and
618 // the callee has more arguments then the caller.
619 NumBytes -= mergeSPUpdates(MBB, MBBI, true);
621 // Adjust stack pointer: ESP -= numbytes.
622 emitSPUpdate(MBB, MBBI, -(int64_t)NumBytes, /*InEpilogue=*/false);
624 unsigned SPOrEstablisher = StackPtr;
626 // If we need a base pointer, set it up here. It's whatever the value
627 // of the stack pointer is at this point. Any variable size objects
628 // will be allocated after this, so we can still use the base pointer
629 // to reference locals.
630 if (TRI->hasBasePointer(MF)) {
631 // Update the base pointer with the current stack pointer.
632 BuildMI(MBB, MBBI, DL, TII.get(M68k::MOV32aa), BasePtr)
633 .addReg(SPOrEstablisher)
634 .setMIFlag(MachineInstr::FrameSetup);
635 if (MMFI->getRestoreBasePointer()) {
636 // Stash value of base pointer. Saving SP instead of FP shortens
637 // dependence chain. Used by SjLj EH.
638 unsigned Opm = M68k::MOV32ja;
639 M68k::addRegIndirectWithDisp(BuildMI(MBB, MBBI, DL, TII.get(Opm)),
640 FramePtr, true,
641 MMFI->getRestoreBasePointerOffset())
642 .addReg(SPOrEstablisher)
643 .setMIFlag(MachineInstr::FrameSetup);
647 if (((!HasFP && NumBytes) || PushedRegs) && NeedsDwarfCFI) {
648 // Mark end of stack pointer adjustment.
649 if (!HasFP && NumBytes) {
650 // Define the current CFA rule to use the provided offset.
651 assert(StackSize);
652 BuildCFI(
653 MBB, MBBI, DL,
654 MCCFIInstruction::cfiDefCfaOffset(nullptr, -StackSize + stackGrowth));
657 // Emit DWARF info specifying the offsets of the callee-saved registers.
658 if (PushedRegs)
659 emitPrologueCalleeSavedFrameMoves(MBB, MBBI, DL);
662 // TODO Interrupt handlers
663 // M68k Interrupt handling function cannot assume anything about the
664 // direction flag (DF in CCR register). Clear this flag by creating "cld"
665 // instruction in each prologue of interrupt handler function. The "cld"
666 // instruction should only in these cases:
667 // 1. The interrupt handling function uses any of the "rep" instructions.
668 // 2. Interrupt handling function calls another function.
671 static bool isTailCallOpcode(unsigned Opc) {
672 return Opc == M68k::TCRETURNj || Opc == M68k::TCRETURNq;
675 void M68kFrameLowering::emitEpilogue(MachineFunction &MF,
676 MachineBasicBlock &MBB) const {
677 const MachineFrameInfo &MFI = MF.getFrameInfo();
678 M68kMachineFunctionInfo *MMFI = MF.getInfo<M68kMachineFunctionInfo>();
679 MachineBasicBlock::iterator MBBI = MBB.getFirstTerminator();
680 Optional<unsigned> RetOpcode;
681 if (MBBI != MBB.end())
682 RetOpcode = MBBI->getOpcode();
683 DebugLoc DL;
684 if (MBBI != MBB.end())
685 DL = MBBI->getDebugLoc();
686 unsigned FramePtr = TRI->getFrameRegister(MF);
687 unsigned MachineFramePtr = FramePtr;
689 // Get the number of bytes to allocate from the FrameInfo.
690 uint64_t StackSize = MFI.getStackSize();
691 uint64_t MaxAlign = calculateMaxStackAlign(MF);
692 unsigned CSSize = MMFI->getCalleeSavedFrameSize();
693 uint64_t NumBytes = 0;
695 if (hasFP(MF)) {
696 // Calculate required stack adjustment.
697 uint64_t FrameSize = StackSize - SlotSize;
698 NumBytes = FrameSize - CSSize;
700 // Callee-saved registers were pushed on stack before the stack was
701 // realigned.
702 if (TRI->hasStackRealignment(MF))
703 NumBytes = alignTo(FrameSize, MaxAlign);
705 // Pop FP.
706 BuildMI(MBB, MBBI, DL, TII.get(M68k::POP32r), MachineFramePtr)
707 .setMIFlag(MachineInstr::FrameDestroy);
708 } else {
709 NumBytes = StackSize - CSSize;
712 // Skip the callee-saved pop instructions.
713 while (MBBI != MBB.begin()) {
714 MachineBasicBlock::iterator PI = std::prev(MBBI);
715 unsigned Opc = PI->getOpcode();
717 if ((Opc != M68k::POP32r || !PI->getFlag(MachineInstr::FrameDestroy)) &&
718 Opc != M68k::DBG_VALUE && !PI->isTerminator())
719 break;
721 --MBBI;
723 MachineBasicBlock::iterator FirstCSPop = MBBI;
725 if (MBBI != MBB.end())
726 DL = MBBI->getDebugLoc();
728 // If there is an ADD32ri or SUB32ri of SP immediately before this
729 // instruction, merge the two instructions.
730 if (NumBytes || MFI.hasVarSizedObjects())
731 NumBytes += mergeSPUpdates(MBB, MBBI, true);
733 // If dynamic alloca is used, then reset SP to point to the last callee-saved
734 // slot before popping them off! Same applies for the case, when stack was
735 // realigned. Don't do this if this was a funclet epilogue, since the funclets
736 // will not do realignment or dynamic stack allocation.
737 if ((TRI->hasStackRealignment(MF) || MFI.hasVarSizedObjects())) {
738 if (TRI->hasStackRealignment(MF))
739 MBBI = FirstCSPop;
740 uint64_t LEAAmount = -CSSize;
742 // 'move %FramePtr, SP' will not be recognized as an epilogue sequence.
743 // However, we may use this sequence if we have a frame pointer because the
744 // effects of the prologue can safely be undone.
745 if (LEAAmount != 0) {
746 unsigned Opc = M68k::LEA32p;
747 M68k::addRegIndirectWithDisp(
748 BuildMI(MBB, MBBI, DL, TII.get(Opc), StackPtr), FramePtr, false,
749 LEAAmount);
750 --MBBI;
751 } else {
752 unsigned Opc = (M68k::MOV32rr);
753 BuildMI(MBB, MBBI, DL, TII.get(Opc), StackPtr).addReg(FramePtr);
754 --MBBI;
756 } else if (NumBytes) {
757 // Adjust stack pointer back: SP += numbytes.
758 emitSPUpdate(MBB, MBBI, NumBytes, /*InEpilogue=*/true);
759 --MBBI;
762 if (!RetOpcode || !isTailCallOpcode(*RetOpcode)) {
763 // Add the return addr area delta back since we are not tail calling.
764 int Offset = -1 * MMFI->getTCReturnAddrDelta();
765 assert(Offset >= 0 && "TCDelta should never be positive");
766 if (Offset) {
767 MBBI = MBB.getFirstTerminator();
769 // Check for possible merge with preceding ADD instruction.
770 Offset += mergeSPUpdates(MBB, MBBI, true);
771 emitSPUpdate(MBB, MBBI, Offset, /*InEpilogue=*/true);
776 void M68kFrameLowering::determineCalleeSaves(MachineFunction &MF,
777 BitVector &SavedRegs,
778 RegScavenger *RS) const {
779 TargetFrameLowering::determineCalleeSaves(MF, SavedRegs, RS);
781 MachineFrameInfo &MFI = MF.getFrameInfo();
783 M68kMachineFunctionInfo *M68kFI = MF.getInfo<M68kMachineFunctionInfo>();
784 int64_t TailCallReturnAddrDelta = M68kFI->getTCReturnAddrDelta();
786 if (TailCallReturnAddrDelta < 0) {
787 // create RETURNADDR area
788 // arg
789 // arg
790 // RETADDR
791 // { ...
792 // RETADDR area
793 // ...
794 // }
795 // [FP]
796 MFI.CreateFixedObject(-TailCallReturnAddrDelta,
797 TailCallReturnAddrDelta - SlotSize, true);
800 // Spill the BasePtr if it's used.
801 if (TRI->hasBasePointer(MF)) {
802 SavedRegs.set(TRI->getBaseRegister());
806 bool M68kFrameLowering::assignCalleeSavedSpillSlots(
807 MachineFunction &MF, const TargetRegisterInfo *TRI,
808 std::vector<CalleeSavedInfo> &CSI) const {
809 MachineFrameInfo &MFI = MF.getFrameInfo();
810 M68kMachineFunctionInfo *M68kFI = MF.getInfo<M68kMachineFunctionInfo>();
812 int SpillSlotOffset = getOffsetOfLocalArea() + M68kFI->getTCReturnAddrDelta();
814 if (hasFP(MF)) {
815 // emitPrologue always spills frame register the first thing.
816 SpillSlotOffset -= SlotSize;
817 MFI.CreateFixedSpillStackObject(SlotSize, SpillSlotOffset);
819 // Since emitPrologue and emitEpilogue will handle spilling and restoring of
820 // the frame register, we can delete it from CSI list and not have to worry
821 // about avoiding it later.
822 unsigned FPReg = TRI->getFrameRegister(MF);
823 for (unsigned i = 0, e = CSI.size(); i < e; ++i) {
824 if (TRI->regsOverlap(CSI[i].getReg(), FPReg)) {
825 CSI.erase(CSI.begin() + i);
826 break;
831 // The rest is fine
832 return false;
835 bool M68kFrameLowering::spillCalleeSavedRegisters(
836 MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
837 ArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const {
838 auto &MRI = *static_cast<const M68kRegisterInfo *>(TRI);
839 auto DL = MBB.findDebugLoc(MI);
841 int FI = 0;
842 unsigned Mask = 0;
843 for (const auto &Info : CSI) {
844 FI = std::max(FI, Info.getFrameIdx());
845 unsigned Reg = Info.getReg();
846 unsigned Shift = MRI.getSpillRegisterOrder(Reg);
847 Mask |= 1 << Shift;
850 auto I =
851 M68k::addFrameReference(BuildMI(MBB, MI, DL, TII.get(M68k::MOVM32pm)), FI)
852 .addImm(Mask)
853 .setMIFlag(MachineInstr::FrameSetup);
855 // Append implicit registers and mem locations
856 const MachineFunction &MF = *MBB.getParent();
857 const MachineRegisterInfo &RI = MF.getRegInfo();
858 for (const auto &Info : CSI) {
859 unsigned Reg = Info.getReg();
860 bool IsLiveIn = RI.isLiveIn(Reg);
861 if (!IsLiveIn)
862 MBB.addLiveIn(Reg);
863 I.addReg(Reg, IsLiveIn ? RegState::Implicit : RegState::ImplicitKill);
864 M68k::addMemOperand(I, Info.getFrameIdx(), 0);
867 return true;
870 bool M68kFrameLowering::restoreCalleeSavedRegisters(
871 MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
872 MutableArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const {
873 auto &MRI = *static_cast<const M68kRegisterInfo *>(TRI);
874 auto DL = MBB.findDebugLoc(MI);
876 int FI = 0;
877 unsigned Mask = 0;
878 for (const auto &Info : CSI) {
879 FI = std::max(FI, Info.getFrameIdx());
880 unsigned Reg = Info.getReg();
881 unsigned Shift = MRI.getSpillRegisterOrder(Reg);
882 Mask |= 1 << Shift;
885 auto I = M68k::addFrameReference(
886 BuildMI(MBB, MI, DL, TII.get(M68k::MOVM32mp)).addImm(Mask), FI)
887 .setMIFlag(MachineInstr::FrameDestroy);
889 // Append implicit registers and mem locations
890 for (const auto &Info : CSI) {
891 I.addReg(Info.getReg(), RegState::ImplicitDefine);
892 M68k::addMemOperand(I, Info.getFrameIdx(), 0);
895 return true;