1 //===-- M68kInstrInfo.cpp - M68k Instruction 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 declaration of the TargetInstrInfo class.
11 ///
12 //===----------------------------------------------------------------------===//
13 
14 #include "M68kInstrInfo.h"
15 
16 #include "M68kInstrBuilder.h"
17 #include "M68kMachineFunction.h"
18 #include "M68kTargetMachine.h"
19 #include "MCTargetDesc/M68kMCCodeEmitter.h"
20 
21 #include "llvm/ADT/STLExtras.h"
22 #include "llvm/ADT/ScopeExit.h"
23 #include "llvm/CodeGen/LivePhysRegs.h"
24 #include "llvm/CodeGen/LiveVariables.h"
25 #include "llvm/CodeGen/MachineInstrBuilder.h"
26 #include "llvm/CodeGen/MachineRegisterInfo.h"
27 #include "llvm/MC/TargetRegistry.h"
28 #include "llvm/Support/ErrorHandling.h"
29 #include "llvm/Support/Regex.h"
30 
31 #include <functional>
32 
33 using namespace llvm;
34 
35 #define DEBUG_TYPE "M68k-instr-info"
36 
37 #define GET_INSTRINFO_CTOR_DTOR
38 #include "M68kGenInstrInfo.inc"
39 
40 // Pin the vtable to this file.
anchor()41 void M68kInstrInfo::anchor() {}
42 
M68kInstrInfo(const M68kSubtarget & STI)43 M68kInstrInfo::M68kInstrInfo(const M68kSubtarget &STI)
44     : M68kGenInstrInfo(M68k::ADJCALLSTACKDOWN, M68k::ADJCALLSTACKUP, 0,
45                        M68k::RET),
46       Subtarget(STI), RI(STI) {}
47 
getCondFromBranchOpc(unsigned BrOpc)48 static M68k::CondCode getCondFromBranchOpc(unsigned BrOpc) {
49   switch (BrOpc) {
50   default:
51     return M68k::COND_INVALID;
52   case M68k::Beq8:
53     return M68k::COND_EQ;
54   case M68k::Bne8:
55     return M68k::COND_NE;
56   case M68k::Blt8:
57     return M68k::COND_LT;
58   case M68k::Ble8:
59     return M68k::COND_LE;
60   case M68k::Bgt8:
61     return M68k::COND_GT;
62   case M68k::Bge8:
63     return M68k::COND_GE;
64   case M68k::Bcs8:
65     return M68k::COND_CS;
66   case M68k::Bls8:
67     return M68k::COND_LS;
68   case M68k::Bhi8:
69     return M68k::COND_HI;
70   case M68k::Bcc8:
71     return M68k::COND_CC;
72   case M68k::Bmi8:
73     return M68k::COND_MI;
74   case M68k::Bpl8:
75     return M68k::COND_PL;
76   case M68k::Bvs8:
77     return M68k::COND_VS;
78   case M68k::Bvc8:
79     return M68k::COND_VC;
80   }
81 }
82 
AnalyzeBranchImpl(MachineBasicBlock & MBB,MachineBasicBlock * & TBB,MachineBasicBlock * & FBB,SmallVectorImpl<MachineOperand> & Cond,bool AllowModify) const83 bool M68kInstrInfo::AnalyzeBranchImpl(MachineBasicBlock &MBB,
84                                       MachineBasicBlock *&TBB,
85                                       MachineBasicBlock *&FBB,
86                                       SmallVectorImpl<MachineOperand> &Cond,
87                                       bool AllowModify) const {
88 
89   auto UncondBranch =
90       std::pair<MachineBasicBlock::reverse_iterator, MachineBasicBlock *>{
91           MBB.rend(), nullptr};
92 
93   // Erase any instructions if allowed at the end of the scope.
94   std::vector<std::reference_wrapper<llvm::MachineInstr>> EraseList;
95   auto FinalizeOnReturn = llvm::make_scope_exit([&EraseList] {
96     std::for_each(EraseList.begin(), EraseList.end(),
97                   [](auto &ref) { ref.get().eraseFromParent(); });
98   });
99 
100   // Start from the bottom of the block and work up, examining the
101   // terminator instructions.
102   for (auto iter = MBB.rbegin(); iter != MBB.rend(); iter = std::next(iter)) {
103 
104     unsigned Opcode = iter->getOpcode();
105 
106     if (iter->isDebugInstr())
107       continue;
108 
109     // Working from the bottom, when we see a non-terminator instruction, we're
110     // done.
111     if (!isUnpredicatedTerminator(*iter))
112       break;
113 
114     // A terminator that isn't a branch can't easily be handled by this
115     // analysis.
116     if (!iter->isBranch())
117       return true;
118 
119     // Handle unconditional branches.
120     if (Opcode == M68k::BRA8 || Opcode == M68k::BRA16) {
121       if (!iter->getOperand(0).isMBB())
122         return true;
123       UncondBranch = {iter, iter->getOperand(0).getMBB()};
124 
125       // TBB is used to indicate the unconditional destination.
126       TBB = UncondBranch.second;
127 
128       if (!AllowModify)
129         continue;
130 
131       // If the block has any instructions after a JMP, erase them.
132       EraseList.insert(EraseList.begin(), MBB.rbegin(), iter);
133 
134       Cond.clear();
135       FBB = nullptr;
136 
137       // Erase the JMP if it's equivalent to a fall-through.
138       if (MBB.isLayoutSuccessor(UncondBranch.second)) {
139         TBB = nullptr;
140         EraseList.push_back(*iter);
141         UncondBranch = {MBB.rend(), nullptr};
142       }
143 
144       continue;
145     }
146 
147     // Handle conditional branches.
148     auto BranchCode = M68k::GetCondFromBranchOpc(Opcode);
149 
150     // Can't handle indirect branch.
151     if (BranchCode == M68k::COND_INVALID)
152       return true;
153 
154     // In practice we should never have an undef CCR operand, if we do
155     // abort here as we are not prepared to preserve the flag.
156     // ??? Is this required?
157     // if (iter->getOperand(1).isUndef())
158     //   return true;
159 
160     // Working from the bottom, handle the first conditional branch.
161     if (Cond.empty()) {
162       if (!iter->getOperand(0).isMBB())
163         return true;
164       MachineBasicBlock *CondBranchTarget = iter->getOperand(0).getMBB();
165 
166       // If we see something like this:
167       //
168       //     bcc l1
169       //     bra l2
170       //     ...
171       //   l1:
172       //     ...
173       //   l2:
174       if (UncondBranch.first != MBB.rend()) {
175 
176         assert(std::next(UncondBranch.first) == iter && "Wrong block layout.");
177 
178         // And we are allowed to modify the block and the target block of the
179         // conditional branch is the direct successor of this block:
180         //
181         //     bcc l1
182         //     bra l2
183         //   l1:
184         //     ...
185         //   l2:
186         //
187         // we change it to this if allowed:
188         //
189         //     bncc l2
190         //   l1:
191         //     ...
192         //   l2:
193         //
194         // Which is a bit more efficient.
195         if (AllowModify && MBB.isLayoutSuccessor(CondBranchTarget)) {
196 
197           BranchCode = GetOppositeBranchCondition(BranchCode);
198           unsigned BNCC = GetCondBranchFromCond(BranchCode);
199 
200           BuildMI(MBB, *UncondBranch.first, MBB.rfindDebugLoc(iter), get(BNCC))
201               .addMBB(UncondBranch.second);
202 
203           EraseList.push_back(*iter);
204           EraseList.push_back(*UncondBranch.first);
205 
206           TBB = UncondBranch.second;
207           FBB = nullptr;
208           Cond.push_back(MachineOperand::CreateImm(BranchCode));
209 
210           // Otherwise preserve TBB, FBB and Cond as requested
211         } else {
212           TBB = CondBranchTarget;
213           FBB = UncondBranch.second;
214           Cond.push_back(MachineOperand::CreateImm(BranchCode));
215         }
216 
217         UncondBranch = {MBB.rend(), nullptr};
218         continue;
219       }
220 
221       TBB = CondBranchTarget;
222       FBB = nullptr;
223       Cond.push_back(MachineOperand::CreateImm(BranchCode));
224 
225       continue;
226     }
227 
228     // Handle subsequent conditional branches. Only handle the case where all
229     // conditional branches branch to the same destination and their condition
230     // opcodes fit one of the special multi-branch idioms.
231     assert(Cond.size() == 1);
232     assert(TBB);
233 
234     // If the conditions are the same, we can leave them alone.
235     auto OldBranchCode = static_cast<M68k::CondCode>(Cond[0].getImm());
236     if (!iter->getOperand(0).isMBB())
237       return true;
238     auto NewTBB = iter->getOperand(0).getMBB();
239     if (OldBranchCode == BranchCode && TBB == NewTBB)
240       continue;
241 
242     // If they differ we cannot do much here.
243     return true;
244   }
245 
246   return false;
247 }
248 
analyzeBranch(MachineBasicBlock & MBB,MachineBasicBlock * & TBB,MachineBasicBlock * & FBB,SmallVectorImpl<MachineOperand> & Cond,bool AllowModify) const249 bool M68kInstrInfo::analyzeBranch(MachineBasicBlock &MBB,
250                                   MachineBasicBlock *&TBB,
251                                   MachineBasicBlock *&FBB,
252                                   SmallVectorImpl<MachineOperand> &Cond,
253                                   bool AllowModify) const {
254   return AnalyzeBranchImpl(MBB, TBB, FBB, Cond, AllowModify);
255 }
256 
removeBranch(MachineBasicBlock & MBB,int * BytesRemoved) const257 unsigned M68kInstrInfo::removeBranch(MachineBasicBlock &MBB,
258                                      int *BytesRemoved) const {
259   assert(!BytesRemoved && "code size not handled");
260 
261   MachineBasicBlock::iterator I = MBB.end();
262   unsigned Count = 0;
263 
264   while (I != MBB.begin()) {
265     --I;
266     if (I->isDebugValue())
267       continue;
268     if (I->getOpcode() != M68k::BRA8 &&
269         getCondFromBranchOpc(I->getOpcode()) == M68k::COND_INVALID)
270       break;
271     // Remove the branch.
272     I->eraseFromParent();
273     I = MBB.end();
274     ++Count;
275   }
276 
277   return Count;
278 }
279 
insertBranch(MachineBasicBlock & MBB,MachineBasicBlock * TBB,MachineBasicBlock * FBB,ArrayRef<MachineOperand> Cond,const DebugLoc & DL,int * BytesAdded) const280 unsigned M68kInstrInfo::insertBranch(
281     MachineBasicBlock &MBB, MachineBasicBlock *TBB, MachineBasicBlock *FBB,
282     ArrayRef<MachineOperand> Cond, const DebugLoc &DL, int *BytesAdded) const {
283   // Shouldn't be a fall through.
284   assert(TBB && "InsertBranch must not be told to insert a fallthrough");
285   assert((Cond.size() == 1 || Cond.size() == 0) &&
286          "M68k branch conditions have one component!");
287   assert(!BytesAdded && "code size not handled");
288 
289   if (Cond.empty()) {
290     // Unconditional branch?
291     assert(!FBB && "Unconditional branch with multiple successors!");
292     BuildMI(&MBB, DL, get(M68k::BRA8)).addMBB(TBB);
293     return 1;
294   }
295 
296   // If FBB is null, it is implied to be a fall-through block.
297   bool FallThru = FBB == nullptr;
298 
299   // Conditional branch.
300   unsigned Count = 0;
301   M68k::CondCode CC = (M68k::CondCode)Cond[0].getImm();
302   unsigned Opc = GetCondBranchFromCond(CC);
303   BuildMI(&MBB, DL, get(Opc)).addMBB(TBB);
304   ++Count;
305   if (!FallThru) {
306     // Two-way Conditional branch. Insert the second branch.
307     BuildMI(&MBB, DL, get(M68k::BRA8)).addMBB(FBB);
308     ++Count;
309   }
310   return Count;
311 }
312 
AddSExt(MachineBasicBlock & MBB,MachineBasicBlock::iterator I,DebugLoc DL,unsigned Reg,MVT From,MVT To) const313 void M68kInstrInfo::AddSExt(MachineBasicBlock &MBB,
314                             MachineBasicBlock::iterator I, DebugLoc DL,
315                             unsigned Reg, MVT From, MVT To) const {
316   if (From == MVT::i8) {
317     unsigned R = Reg;
318     // EXT16 requires i16 register
319     if (To == MVT::i32) {
320       R = RI.getSubReg(Reg, M68k::MxSubRegIndex16Lo);
321       assert(R && "No viable SUB register available");
322     }
323     BuildMI(MBB, I, DL, get(M68k::EXT16), R).addReg(R);
324   }
325 
326   if (To == MVT::i32)
327     BuildMI(MBB, I, DL, get(M68k::EXT32), Reg).addReg(Reg);
328 }
329 
AddZExt(MachineBasicBlock & MBB,MachineBasicBlock::iterator I,DebugLoc DL,unsigned Reg,MVT From,MVT To) const330 void M68kInstrInfo::AddZExt(MachineBasicBlock &MBB,
331                             MachineBasicBlock::iterator I, DebugLoc DL,
332                             unsigned Reg, MVT From, MVT To) const {
333 
334   unsigned Mask, And;
335   if (From == MVT::i8)
336     Mask = 0xFF;
337   else
338     Mask = 0xFFFF;
339 
340   if (To == MVT::i16)
341     And = M68k::AND16di;
342   else // i32
343     And = M68k::AND32di;
344 
345   // TODO use xor r,r to decrease size
346   BuildMI(MBB, I, DL, get(And), Reg).addReg(Reg).addImm(Mask);
347 }
348 
ExpandMOVX_RR(MachineInstrBuilder & MIB,MVT MVTDst,MVT MVTSrc) const349 bool M68kInstrInfo::ExpandMOVX_RR(MachineInstrBuilder &MIB, MVT MVTDst,
350                                   MVT MVTSrc) const {
351   unsigned Move = MVTDst == MVT::i16 ? M68k::MOV16rr : M68k::MOV32rr;
352   Register Dst = MIB->getOperand(0).getReg();
353   Register Src = MIB->getOperand(1).getReg();
354 
355   assert(Dst != Src && "You cannot use the same Regs with MOVX_RR");
356 
357   const auto &TRI = getRegisterInfo();
358 
359   const auto *RCDst = TRI.getMaximalPhysRegClass(Dst, MVTDst);
360   const auto *RCSrc = TRI.getMaximalPhysRegClass(Src, MVTSrc);
361 
362   assert(RCDst && RCSrc && "Wrong use of MOVX_RR");
363   assert(RCDst != RCSrc && "You cannot use the same Reg Classes with MOVX_RR");
364   (void)RCSrc;
365 
366   // We need to find the super source register that matches the size of Dst
367   unsigned SSrc = RI.getMatchingMegaReg(Src, RCDst);
368   assert(SSrc && "No viable MEGA register available");
369 
370   DebugLoc DL = MIB->getDebugLoc();
371 
372   // If it happens to that super source register is the destination register
373   // we do nothing
374   if (Dst == SSrc) {
375     LLVM_DEBUG(dbgs() << "Remove " << *MIB.getInstr() << '\n');
376     MIB->eraseFromParent();
377   } else { // otherwise we need to MOV
378     LLVM_DEBUG(dbgs() << "Expand " << *MIB.getInstr() << " to MOV\n");
379     MIB->setDesc(get(Move));
380     MIB->getOperand(1).setReg(SSrc);
381   }
382 
383   return true;
384 }
385 
386 /// Expand SExt MOVE pseudos into a MOV and a EXT if the operands are two
387 /// different registers or just EXT if it is the same register
ExpandMOVSZX_RR(MachineInstrBuilder & MIB,bool IsSigned,MVT MVTDst,MVT MVTSrc) const388 bool M68kInstrInfo::ExpandMOVSZX_RR(MachineInstrBuilder &MIB, bool IsSigned,
389                                     MVT MVTDst, MVT MVTSrc) const {
390   LLVM_DEBUG(dbgs() << "Expand " << *MIB.getInstr() << " to ");
391 
392   unsigned Move;
393 
394   if (MVTDst == MVT::i16)
395     Move = M68k::MOV16rr;
396   else // i32
397     Move = M68k::MOV32rr;
398 
399   Register Dst = MIB->getOperand(0).getReg();
400   Register Src = MIB->getOperand(1).getReg();
401 
402   assert(Dst != Src && "You cannot use the same Regs with MOVSX_RR");
403 
404   const auto &TRI = getRegisterInfo();
405 
406   const auto *RCDst = TRI.getMaximalPhysRegClass(Dst, MVTDst);
407   const auto *RCSrc = TRI.getMaximalPhysRegClass(Src, MVTSrc);
408 
409   assert(RCDst && RCSrc && "Wrong use of MOVSX_RR");
410   assert(RCDst != RCSrc && "You cannot use the same Reg Classes with MOVSX_RR");
411   (void)RCSrc;
412 
413   // We need to find the super source register that matches the size of Dst
414   unsigned SSrc = RI.getMatchingMegaReg(Src, RCDst);
415   assert(SSrc && "No viable MEGA register available");
416 
417   MachineBasicBlock &MBB = *MIB->getParent();
418   DebugLoc DL = MIB->getDebugLoc();
419 
420   if (Dst != SSrc) {
421     LLVM_DEBUG(dbgs() << "Move and " << '\n');
422     BuildMI(MBB, MIB.getInstr(), DL, get(Move), Dst).addReg(SSrc);
423   }
424 
425   if (IsSigned) {
426     LLVM_DEBUG(dbgs() << "Sign Extend" << '\n');
427     AddSExt(MBB, MIB.getInstr(), DL, Dst, MVTSrc, MVTDst);
428   } else {
429     LLVM_DEBUG(dbgs() << "Zero Extend" << '\n');
430     AddZExt(MBB, MIB.getInstr(), DL, Dst, MVTSrc, MVTDst);
431   }
432 
433   MIB->eraseFromParent();
434 
435   return true;
436 }
437 
ExpandMOVSZX_RM(MachineInstrBuilder & MIB,bool IsSigned,const MCInstrDesc & Desc,MVT MVTDst,MVT MVTSrc) const438 bool M68kInstrInfo::ExpandMOVSZX_RM(MachineInstrBuilder &MIB, bool IsSigned,
439                                     const MCInstrDesc &Desc, MVT MVTDst,
440                                     MVT MVTSrc) const {
441   LLVM_DEBUG(dbgs() << "Expand " << *MIB.getInstr() << " to LOAD and ");
442 
443   Register Dst = MIB->getOperand(0).getReg();
444 
445   // We need the subreg of Dst to make instruction verifier happy because the
446   // real machine instruction consumes and produces values of the same size and
447   // the registers the will be used here fall into different classes and this
448   // makes IV cry. We could use a bigger operation, but this will put some
449   // pressure on cache and memory, so no.
450   unsigned SubDst =
451       RI.getSubReg(Dst, MVTSrc == MVT::i8 ? M68k::MxSubRegIndex8Lo
452                                           : M68k::MxSubRegIndex16Lo);
453   assert(SubDst && "No viable SUB register available");
454 
455   // Make this a plain move
456   MIB->setDesc(Desc);
457   MIB->getOperand(0).setReg(SubDst);
458 
459   MachineBasicBlock::iterator I = MIB.getInstr();
460   I++;
461   MachineBasicBlock &MBB = *MIB->getParent();
462   DebugLoc DL = MIB->getDebugLoc();
463 
464   if (IsSigned) {
465     LLVM_DEBUG(dbgs() << "Sign Extend" << '\n');
466     AddSExt(MBB, I, DL, Dst, MVTSrc, MVTDst);
467   } else {
468     LLVM_DEBUG(dbgs() << "Zero Extend" << '\n');
469     AddZExt(MBB, I, DL, Dst, MVTSrc, MVTDst);
470   }
471 
472   return true;
473 }
474 
ExpandPUSH_POP(MachineInstrBuilder & MIB,const MCInstrDesc & Desc,bool IsPush) const475 bool M68kInstrInfo::ExpandPUSH_POP(MachineInstrBuilder &MIB,
476                                    const MCInstrDesc &Desc, bool IsPush) const {
477   MachineBasicBlock::iterator I = MIB.getInstr();
478   I++;
479   MachineBasicBlock &MBB = *MIB->getParent();
480   MachineOperand MO = MIB->getOperand(0);
481   DebugLoc DL = MIB->getDebugLoc();
482   if (IsPush)
483     BuildMI(MBB, I, DL, Desc).addReg(RI.getStackRegister()).add(MO);
484   else
485     BuildMI(MBB, I, DL, Desc, MO.getReg()).addReg(RI.getStackRegister());
486 
487   MIB->eraseFromParent();
488   return true;
489 }
490 
ExpandCCR(MachineInstrBuilder & MIB,bool IsToCCR) const491 bool M68kInstrInfo::ExpandCCR(MachineInstrBuilder &MIB, bool IsToCCR) const {
492 
493   // Replace the pseudo instruction with the real one
494   if (IsToCCR)
495     MIB->setDesc(get(M68k::MOV16cd));
496   else
497     // FIXME M68010 or later is required
498     MIB->setDesc(get(M68k::MOV16dc));
499 
500   // Promote used register to the next class
501   auto &Opd = MIB->getOperand(1);
502   Opd.setReg(getRegisterInfo().getMatchingSuperReg(
503       Opd.getReg(), M68k::MxSubRegIndex8Lo, &M68k::DR16RegClass));
504 
505   return true;
506 }
507 
ExpandMOVEM(MachineInstrBuilder & MIB,const MCInstrDesc & Desc,bool IsRM) const508 bool M68kInstrInfo::ExpandMOVEM(MachineInstrBuilder &MIB,
509                                 const MCInstrDesc &Desc, bool IsRM) const {
510   int Reg = 0, Offset = 0, Base = 0;
511   auto XR32 = RI.getRegClass(M68k::XR32RegClassID);
512   auto DL = MIB->getDebugLoc();
513   auto MI = MIB.getInstr();
514   auto &MBB = *MIB->getParent();
515 
516   if (IsRM) {
517     Reg = MIB->getOperand(0).getReg();
518     Offset = MIB->getOperand(1).getImm();
519     Base = MIB->getOperand(2).getReg();
520   } else {
521     Offset = MIB->getOperand(0).getImm();
522     Base = MIB->getOperand(1).getReg();
523     Reg = MIB->getOperand(2).getReg();
524   }
525 
526   // If the register is not in XR32 then it is smaller than 32 bit, we
527   // implicitly promote it to 32
528   if (!XR32->contains(Reg)) {
529     Reg = RI.getMatchingMegaReg(Reg, XR32);
530     assert(Reg && "Has not meaningful MEGA register");
531   }
532 
533   unsigned Mask = 1 << RI.getSpillRegisterOrder(Reg);
534   if (IsRM) {
535     BuildMI(MBB, MI, DL, Desc)
536         .addImm(Mask)
537         .addImm(Offset)
538         .addReg(Base)
539         .addReg(Reg, RegState::ImplicitDefine)
540         .copyImplicitOps(*MIB);
541   } else {
542     BuildMI(MBB, MI, DL, Desc)
543         .addImm(Offset)
544         .addReg(Base)
545         .addImm(Mask)
546         .addReg(Reg, RegState::Implicit)
547         .copyImplicitOps(*MIB);
548   }
549 
550   MIB->eraseFromParent();
551 
552   return true;
553 }
554 
555 /// Expand a single-def pseudo instruction to a two-addr
556 /// instruction with two undef reads of the register being defined.
557 /// This is used for mapping:
558 ///   %d0 = SETCS_C32d
559 /// to:
560 ///   %d0 = SUBX32dd %d0<undef>, %d0<undef>
561 ///
Expand2AddrUndef(MachineInstrBuilder & MIB,const MCInstrDesc & Desc)562 static bool Expand2AddrUndef(MachineInstrBuilder &MIB,
563                              const MCInstrDesc &Desc) {
564   assert(Desc.getNumOperands() == 3 && "Expected two-addr instruction.");
565   Register Reg = MIB->getOperand(0).getReg();
566   MIB->setDesc(Desc);
567 
568   // MachineInstr::addOperand() will insert explicit operands before any
569   // implicit operands.
570   MIB.addReg(Reg, RegState::Undef).addReg(Reg, RegState::Undef);
571   // But we don't trust that.
572   assert(MIB->getOperand(1).getReg() == Reg &&
573          MIB->getOperand(2).getReg() == Reg && "Misplaced operand");
574   return true;
575 }
576 
expandPostRAPseudo(MachineInstr & MI) const577 bool M68kInstrInfo::expandPostRAPseudo(MachineInstr &MI) const {
578   MachineInstrBuilder MIB(*MI.getParent()->getParent(), MI);
579   switch (MI.getOpcode()) {
580   case M68k::PUSH8d:
581     return ExpandPUSH_POP(MIB, get(M68k::MOV8ed), true);
582   case M68k::PUSH16d:
583     return ExpandPUSH_POP(MIB, get(M68k::MOV16er), true);
584   case M68k::PUSH32r:
585     return ExpandPUSH_POP(MIB, get(M68k::MOV32er), true);
586 
587   case M68k::POP8d:
588     return ExpandPUSH_POP(MIB, get(M68k::MOV8do), false);
589   case M68k::POP16d:
590     return ExpandPUSH_POP(MIB, get(M68k::MOV16ro), false);
591   case M68k::POP32r:
592     return ExpandPUSH_POP(MIB, get(M68k::MOV32ro), false);
593 
594   case M68k::SETCS_C8d:
595     return Expand2AddrUndef(MIB, get(M68k::SUBX8dd));
596   case M68k::SETCS_C16d:
597     return Expand2AddrUndef(MIB, get(M68k::SUBX16dd));
598   case M68k::SETCS_C32d:
599     return Expand2AddrUndef(MIB, get(M68k::SUBX32dd));
600   }
601   return false;
602 }
603 
isPCRelRegisterOperandLegal(const MachineOperand & MO) const604 bool M68kInstrInfo::isPCRelRegisterOperandLegal(
605     const MachineOperand &MO) const {
606   assert(MO.isReg());
607 
608   // Check whether this MO belongs to an instruction with addressing mode 'k',
609   // Refer to TargetInstrInfo.h for more information about this function.
610 
611   const MachineInstr *MI = MO.getParent();
612   const unsigned NameIndices = M68kInstrNameIndices[MI->getOpcode()];
613   StringRef InstrName(&M68kInstrNameData[NameIndices]);
614   const unsigned OperandNo = MO.getOperandNo();
615 
616   // If this machine operand is the 2nd operand, then check
617   // whether the instruction has destination addressing mode 'k'.
618   if (OperandNo == 1)
619     return Regex("[A-Z]+(8|16|32)k[a-z](_TC)?$").match(InstrName);
620 
621   // If this machine operand is the last one, then check
622   // whether the instruction has source addressing mode 'k'.
623   if (OperandNo == MI->getNumExplicitOperands() - 1)
624     return Regex("[A-Z]+(8|16|32)[a-z]k(_TC)?$").match(InstrName);
625 
626   return false;
627 }
628 
copyPhysReg(MachineBasicBlock & MBB,MachineBasicBlock::iterator MI,const DebugLoc & DL,MCRegister DstReg,MCRegister SrcReg,bool KillSrc) const629 void M68kInstrInfo::copyPhysReg(MachineBasicBlock &MBB,
630                                 MachineBasicBlock::iterator MI,
631                                 const DebugLoc &DL, MCRegister DstReg,
632                                 MCRegister SrcReg, bool KillSrc) const {
633   unsigned Opc = 0;
634 
635   // First deal with the normal symmetric copies.
636   if (M68k::XR32RegClass.contains(DstReg, SrcReg))
637     Opc = M68k::MOV32rr;
638   else if (M68k::XR16RegClass.contains(DstReg, SrcReg))
639     Opc = M68k::MOV16rr;
640   else if (M68k::DR8RegClass.contains(DstReg, SrcReg))
641     Opc = M68k::MOV8dd;
642 
643   if (Opc) {
644     BuildMI(MBB, MI, DL, get(Opc), DstReg)
645         .addReg(SrcReg, getKillRegState(KillSrc));
646     return;
647   }
648 
649   // Now deal with asymmetrically sized copies. The cases that follow are upcast
650   // moves.
651   //
652   // NOTE
653   // These moves are not aware of type nature of these values and thus
654   // won't do any SExt or ZExt and upper bits will basically contain garbage.
655   MachineInstrBuilder MIB(*MBB.getParent(), MI);
656   if (M68k::DR8RegClass.contains(SrcReg)) {
657     if (M68k::XR16RegClass.contains(DstReg))
658       Opc = M68k::MOVXd16d8;
659     else if (M68k::XR32RegClass.contains(DstReg))
660       Opc = M68k::MOVXd32d8;
661   } else if (M68k::XR16RegClass.contains(SrcReg) &&
662              M68k::XR32RegClass.contains(DstReg))
663     Opc = M68k::MOVXd32d16;
664 
665   if (Opc) {
666     BuildMI(MBB, MI, DL, get(Opc), DstReg)
667         .addReg(SrcReg, getKillRegState(KillSrc));
668     return;
669   }
670 
671   bool FromCCR = SrcReg == M68k::CCR;
672   bool FromSR = SrcReg == M68k::SR;
673   bool ToCCR = DstReg == M68k::CCR;
674   bool ToSR = DstReg == M68k::SR;
675 
676   if (FromCCR) {
677     assert(M68k::DR8RegClass.contains(DstReg) &&
678            "Need DR8 register to copy CCR");
679     Opc = M68k::MOV8dc;
680   } else if (ToCCR) {
681     assert(M68k::DR8RegClass.contains(SrcReg) &&
682            "Need DR8 register to copy CCR");
683     Opc = M68k::MOV8cd;
684   } else if (FromSR || ToSR)
685     llvm_unreachable("Cannot emit SR copy instruction");
686 
687   if (Opc) {
688     BuildMI(MBB, MI, DL, get(Opc), DstReg)
689         .addReg(SrcReg, getKillRegState(KillSrc));
690     return;
691   }
692 
693   LLVM_DEBUG(dbgs() << "Cannot copy " << RI.getName(SrcReg) << " to "
694                     << RI.getName(DstReg) << '\n');
695   llvm_unreachable("Cannot emit physreg copy instruction");
696 }
697 
698 namespace {
getLoadStoreRegOpcode(unsigned Reg,const TargetRegisterClass * RC,const TargetRegisterInfo * TRI,const M68kSubtarget & STI,bool load)699 unsigned getLoadStoreRegOpcode(unsigned Reg, const TargetRegisterClass *RC,
700                                const TargetRegisterInfo *TRI,
701                                const M68kSubtarget &STI, bool load) {
702   switch (TRI->getRegSizeInBits(*RC)) {
703   default:
704     llvm_unreachable("Unknown spill size");
705   case 8:
706     if (M68k::DR8RegClass.hasSubClassEq(RC))
707       return load ? M68k::MOV8dp : M68k::MOV8pd;
708     if (M68k::CCRCRegClass.hasSubClassEq(RC))
709       return load ? M68k::MOV16cp : M68k::MOV16pc;
710 
711     llvm_unreachable("Unknown 1-byte regclass");
712   case 16:
713     assert(M68k::XR16RegClass.hasSubClassEq(RC) && "Unknown 2-byte regclass");
714     return load ? M68k::MOVM16mp_P : M68k::MOVM16pm_P;
715   case 32:
716     assert(M68k::XR32RegClass.hasSubClassEq(RC) && "Unknown 4-byte regclass");
717     return load ? M68k::MOVM32mp_P : M68k::MOVM32pm_P;
718   }
719 }
720 
getStoreRegOpcode(unsigned SrcReg,const TargetRegisterClass * RC,const TargetRegisterInfo * TRI,const M68kSubtarget & STI)721 unsigned getStoreRegOpcode(unsigned SrcReg, const TargetRegisterClass *RC,
722                            const TargetRegisterInfo *TRI,
723                            const M68kSubtarget &STI) {
724   return getLoadStoreRegOpcode(SrcReg, RC, TRI, STI, false);
725 }
726 
getLoadRegOpcode(unsigned DstReg,const TargetRegisterClass * RC,const TargetRegisterInfo * TRI,const M68kSubtarget & STI)727 unsigned getLoadRegOpcode(unsigned DstReg, const TargetRegisterClass *RC,
728                           const TargetRegisterInfo *TRI,
729                           const M68kSubtarget &STI) {
730   return getLoadStoreRegOpcode(DstReg, RC, TRI, STI, true);
731 }
732 } // end anonymous namespace
733 
getStackSlotRange(const TargetRegisterClass * RC,unsigned SubIdx,unsigned & Size,unsigned & Offset,const MachineFunction & MF) const734 bool M68kInstrInfo::getStackSlotRange(const TargetRegisterClass *RC,
735                                       unsigned SubIdx, unsigned &Size,
736                                       unsigned &Offset,
737                                       const MachineFunction &MF) const {
738   // The slot size must be the maximum size so we can easily use MOVEM.L
739   Size = 4;
740   Offset = 0;
741   return true;
742 }
743 
storeRegToStackSlot(MachineBasicBlock & MBB,MachineBasicBlock::iterator MI,Register SrcReg,bool IsKill,int FrameIndex,const TargetRegisterClass * RC,const TargetRegisterInfo * TRI,Register VReg) const744 void M68kInstrInfo::storeRegToStackSlot(
745     MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, Register SrcReg,
746     bool IsKill, int FrameIndex, const TargetRegisterClass *RC,
747     const TargetRegisterInfo *TRI, Register VReg) const {
748   const MachineFrameInfo &MFI = MBB.getParent()->getFrameInfo();
749   assert(MFI.getObjectSize(FrameIndex) >= TRI->getSpillSize(*RC) &&
750          "Stack slot is too small to store");
751   (void)MFI;
752 
753   unsigned Opc = getStoreRegOpcode(SrcReg, RC, TRI, Subtarget);
754   DebugLoc DL = MBB.findDebugLoc(MI);
755   // (0,FrameIndex) <- $reg
756   M68k::addFrameReference(BuildMI(MBB, MI, DL, get(Opc)), FrameIndex)
757       .addReg(SrcReg, getKillRegState(IsKill));
758 }
759 
loadRegFromStackSlot(MachineBasicBlock & MBB,MachineBasicBlock::iterator MI,Register DstReg,int FrameIndex,const TargetRegisterClass * RC,const TargetRegisterInfo * TRI,Register VReg) const760 void M68kInstrInfo::loadRegFromStackSlot(MachineBasicBlock &MBB,
761                                          MachineBasicBlock::iterator MI,
762                                          Register DstReg, int FrameIndex,
763                                          const TargetRegisterClass *RC,
764                                          const TargetRegisterInfo *TRI,
765                                          Register VReg) const {
766   const MachineFrameInfo &MFI = MBB.getParent()->getFrameInfo();
767   assert(MFI.getObjectSize(FrameIndex) >= TRI->getSpillSize(*RC) &&
768          "Stack slot is too small to load");
769   (void)MFI;
770 
771   unsigned Opc = getLoadRegOpcode(DstReg, RC, TRI, Subtarget);
772   DebugLoc DL = MBB.findDebugLoc(MI);
773   M68k::addFrameReference(BuildMI(MBB, MI, DL, get(Opc), DstReg), FrameIndex);
774 }
775 
776 /// Return a virtual register initialized with the global base register
777 /// value. Output instructions required to initialize the register in the
778 /// function entry block, if necessary.
779 ///
780 /// TODO Move this function to M68kMachineFunctionInfo.
getGlobalBaseReg(MachineFunction * MF) const781 unsigned M68kInstrInfo::getGlobalBaseReg(MachineFunction *MF) const {
782   M68kMachineFunctionInfo *MxFI = MF->getInfo<M68kMachineFunctionInfo>();
783   unsigned GlobalBaseReg = MxFI->getGlobalBaseReg();
784   if (GlobalBaseReg != 0)
785     return GlobalBaseReg;
786 
787   // Create the register. The code to initialize it is inserted later,
788   // by the M68kGlobalBaseReg pass (below).
789   //
790   // NOTE
791   // Normally M68k uses A5 register as global base pointer but this will
792   // create unnecessary spill if we use less then 4 registers in code; since A5
793   // is callee-save anyway we could try to allocate caller-save first and if
794   // lucky get one, otherwise it does not really matter which callee-save to
795   // use.
796   MachineRegisterInfo &RegInfo = MF->getRegInfo();
797   GlobalBaseReg = RegInfo.createVirtualRegister(&M68k::AR32_NOSPRegClass);
798   MxFI->setGlobalBaseReg(GlobalBaseReg);
799   return GlobalBaseReg;
800 }
801 
802 std::pair<unsigned, unsigned>
decomposeMachineOperandsTargetFlags(unsigned TF) const803 M68kInstrInfo::decomposeMachineOperandsTargetFlags(unsigned TF) const {
804   return std::make_pair(TF, 0u);
805 }
806 
807 ArrayRef<std::pair<unsigned, const char *>>
getSerializableDirectMachineOperandTargetFlags() const808 M68kInstrInfo::getSerializableDirectMachineOperandTargetFlags() const {
809   using namespace M68kII;
810   static const std::pair<unsigned, const char *> TargetFlags[] = {
811       {MO_ABSOLUTE_ADDRESS, "m68k-absolute"},
812       {MO_PC_RELATIVE_ADDRESS, "m68k-pcrel"},
813       {MO_GOT, "m68k-got"},
814       {MO_GOTOFF, "m68k-gotoff"},
815       {MO_GOTPCREL, "m68k-gotpcrel"},
816       {MO_PLT, "m68k-plt"},
817       {MO_TLSGD, "m68k-tlsgd"},
818       {MO_TLSLD, "m68k-tlsld"},
819       {MO_TLSLDM, "m68k-tlsldm"},
820       {MO_TLSIE, "m68k-tlsie"},
821       {MO_TLSLE, "m68k-tlsle"}};
822   return ArrayRef(TargetFlags);
823 }
824 
825 #undef DEBUG_TYPE
826 #define DEBUG_TYPE "m68k-create-global-base-reg"
827 
828 #define PASS_NAME "M68k PIC Global Base Reg Initialization"
829 
830 namespace {
831 /// This initializes the PIC global base register
832 struct M68kGlobalBaseReg : public MachineFunctionPass {
833   static char ID;
M68kGlobalBaseReg__anone426ef450411::M68kGlobalBaseReg834   M68kGlobalBaseReg() : MachineFunctionPass(ID) {}
835 
runOnMachineFunction__anone426ef450411::M68kGlobalBaseReg836   bool runOnMachineFunction(MachineFunction &MF) override {
837     const M68kSubtarget &STI = MF.getSubtarget<M68kSubtarget>();
838     M68kMachineFunctionInfo *MxFI = MF.getInfo<M68kMachineFunctionInfo>();
839 
840     unsigned GlobalBaseReg = MxFI->getGlobalBaseReg();
841 
842     // If we didn't need a GlobalBaseReg, don't insert code.
843     if (GlobalBaseReg == 0)
844       return false;
845 
846     // Insert the set of GlobalBaseReg into the first MBB of the function
847     MachineBasicBlock &FirstMBB = MF.front();
848     MachineBasicBlock::iterator MBBI = FirstMBB.begin();
849     DebugLoc DL = FirstMBB.findDebugLoc(MBBI);
850     const M68kInstrInfo *TII = STI.getInstrInfo();
851 
852     // Generate lea (__GLOBAL_OFFSET_TABLE_,%PC), %A5
853     BuildMI(FirstMBB, MBBI, DL, TII->get(M68k::LEA32q), GlobalBaseReg)
854         .addExternalSymbol("_GLOBAL_OFFSET_TABLE_", M68kII::MO_GOTPCREL);
855 
856     return true;
857   }
858 
getAnalysisUsage__anone426ef450411::M68kGlobalBaseReg859   void getAnalysisUsage(AnalysisUsage &AU) const override {
860     AU.setPreservesCFG();
861     MachineFunctionPass::getAnalysisUsage(AU);
862   }
863 };
864 char M68kGlobalBaseReg::ID = 0;
865 } // namespace
866 
INITIALIZE_PASS(M68kGlobalBaseReg,DEBUG_TYPE,PASS_NAME,false,false)867 INITIALIZE_PASS(M68kGlobalBaseReg, DEBUG_TYPE, PASS_NAME, false, false)
868 
869 FunctionPass *llvm::createM68kGlobalBaseRegPass() {
870   return new M68kGlobalBaseReg();
871 }
872