/3rd_party/llvm/lib/Target/Sparc/SparcFrameLowering.cpp

https://code.google.com/p/softart/ · C++ · 252 lines · 174 code · 44 blank · 34 comment · 32 complexity · 157a73f17dd2f3c4c2ab5b1f181e62b2 MD5 · raw file

  1. //===-- SparcFrameLowering.cpp - Sparc Frame Information ------------------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. //
  10. // This file contains the Sparc implementation of TargetFrameLowering class.
  11. //
  12. //===----------------------------------------------------------------------===//
  13. #include "SparcFrameLowering.h"
  14. #include "SparcInstrInfo.h"
  15. #include "SparcMachineFunctionInfo.h"
  16. #include "llvm/CodeGen/MachineFrameInfo.h"
  17. #include "llvm/CodeGen/MachineFunction.h"
  18. #include "llvm/CodeGen/MachineInstrBuilder.h"
  19. #include "llvm/CodeGen/MachineModuleInfo.h"
  20. #include "llvm/CodeGen/MachineRegisterInfo.h"
  21. #include "llvm/IR/DataLayout.h"
  22. #include "llvm/IR/Function.h"
  23. #include "llvm/Support/CommandLine.h"
  24. #include "llvm/Target/TargetOptions.h"
  25. using namespace llvm;
  26. static cl::opt<bool>
  27. DisableLeafProc("disable-sparc-leaf-proc",
  28. cl::init(false),
  29. cl::desc("Disable Sparc leaf procedure optimization."),
  30. cl::Hidden);
  31. void SparcFrameLowering::emitSPAdjustment(MachineFunction &MF,
  32. MachineBasicBlock &MBB,
  33. MachineBasicBlock::iterator MBBI,
  34. int NumBytes,
  35. unsigned ADDrr,
  36. unsigned ADDri) const {
  37. DebugLoc dl = (MBBI != MBB.end()) ? MBBI->getDebugLoc() : DebugLoc();
  38. const SparcInstrInfo &TII =
  39. *static_cast<const SparcInstrInfo*>(MF.getTarget().getInstrInfo());
  40. if (NumBytes >= -4096 && NumBytes < 4096) {
  41. BuildMI(MBB, MBBI, dl, TII.get(ADDri), SP::O6)
  42. .addReg(SP::O6).addImm(NumBytes);
  43. return;
  44. }
  45. // Emit this the hard way. This clobbers G1 which we always know is
  46. // available here.
  47. if (NumBytes >= 0) {
  48. // Emit nonnegative numbers with sethi + or.
  49. // sethi %hi(NumBytes), %g1
  50. // or %g1, %lo(NumBytes), %g1
  51. // add %sp, %g1, %sp
  52. BuildMI(MBB, MBBI, dl, TII.get(SP::SETHIi), SP::G1)
  53. .addImm(HI22(NumBytes));
  54. BuildMI(MBB, MBBI, dl, TII.get(SP::ORri), SP::G1)
  55. .addReg(SP::G1).addImm(LO10(NumBytes));
  56. BuildMI(MBB, MBBI, dl, TII.get(ADDrr), SP::O6)
  57. .addReg(SP::O6).addReg(SP::G1);
  58. return ;
  59. }
  60. // Emit negative numbers with sethi + xor.
  61. // sethi %hix(NumBytes), %g1
  62. // xor %g1, %lox(NumBytes), %g1
  63. // add %sp, %g1, %sp
  64. BuildMI(MBB, MBBI, dl, TII.get(SP::SETHIi), SP::G1)
  65. .addImm(HIX22(NumBytes));
  66. BuildMI(MBB, MBBI, dl, TII.get(SP::XORri), SP::G1)
  67. .addReg(SP::G1).addImm(LOX10(NumBytes));
  68. BuildMI(MBB, MBBI, dl, TII.get(ADDrr), SP::O6)
  69. .addReg(SP::O6).addReg(SP::G1);
  70. }
  71. void SparcFrameLowering::emitPrologue(MachineFunction &MF) const {
  72. SparcMachineFunctionInfo *FuncInfo = MF.getInfo<SparcMachineFunctionInfo>();
  73. MachineBasicBlock &MBB = MF.front();
  74. MachineFrameInfo *MFI = MF.getFrameInfo();
  75. const SparcInstrInfo &TII =
  76. *static_cast<const SparcInstrInfo*>(MF.getTarget().getInstrInfo());
  77. MachineBasicBlock::iterator MBBI = MBB.begin();
  78. DebugLoc dl = MBBI != MBB.end() ? MBBI->getDebugLoc() : DebugLoc();
  79. // Get the number of bytes to allocate from the FrameInfo
  80. int NumBytes = (int) MFI->getStackSize();
  81. unsigned SAVEri = SP::SAVEri;
  82. unsigned SAVErr = SP::SAVErr;
  83. if (FuncInfo->isLeafProc()) {
  84. if (NumBytes == 0)
  85. return;
  86. SAVEri = SP::ADDri;
  87. SAVErr = SP::ADDrr;
  88. }
  89. NumBytes = - SubTarget.getAdjustedFrameSize(NumBytes);
  90. emitSPAdjustment(MF, MBB, MBBI, NumBytes, SAVErr, SAVEri);
  91. MachineModuleInfo &MMI = MF.getMMI();
  92. const MCRegisterInfo *MRI = MMI.getContext().getRegisterInfo();
  93. MCSymbol *FrameLabel = MMI.getContext().CreateTempSymbol();
  94. BuildMI(MBB, MBBI, dl, TII.get(SP::PROLOG_LABEL)).addSym(FrameLabel);
  95. unsigned regFP = MRI->getDwarfRegNum(SP::I6, true);
  96. // Emit ".cfi_def_cfa_register 30".
  97. MMI.addFrameInst(MCCFIInstruction::createDefCfaRegister(FrameLabel,
  98. regFP));
  99. // Emit ".cfi_window_save".
  100. MMI.addFrameInst(MCCFIInstruction::createWindowSave(FrameLabel));
  101. unsigned regInRA = MRI->getDwarfRegNum(SP::I7, true);
  102. unsigned regOutRA = MRI->getDwarfRegNum(SP::O7, true);
  103. // Emit ".cfi_register 15, 31".
  104. MMI.addFrameInst(MCCFIInstruction::createRegister(FrameLabel,
  105. regOutRA,
  106. regInRA));
  107. }
  108. void SparcFrameLowering::
  109. eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB,
  110. MachineBasicBlock::iterator I) const {
  111. if (!hasReservedCallFrame(MF)) {
  112. MachineInstr &MI = *I;
  113. int Size = MI.getOperand(0).getImm();
  114. if (MI.getOpcode() == SP::ADJCALLSTACKDOWN)
  115. Size = -Size;
  116. if (Size)
  117. emitSPAdjustment(MF, MBB, I, Size, SP::ADDrr, SP::ADDri);
  118. }
  119. MBB.erase(I);
  120. }
  121. void SparcFrameLowering::emitEpilogue(MachineFunction &MF,
  122. MachineBasicBlock &MBB) const {
  123. SparcMachineFunctionInfo *FuncInfo = MF.getInfo<SparcMachineFunctionInfo>();
  124. MachineBasicBlock::iterator MBBI = MBB.getLastNonDebugInstr();
  125. const SparcInstrInfo &TII =
  126. *static_cast<const SparcInstrInfo*>(MF.getTarget().getInstrInfo());
  127. DebugLoc dl = MBBI->getDebugLoc();
  128. assert(MBBI->getOpcode() == SP::RETL &&
  129. "Can only put epilog before 'retl' instruction!");
  130. if (!FuncInfo->isLeafProc()) {
  131. BuildMI(MBB, MBBI, dl, TII.get(SP::RESTORErr), SP::G0).addReg(SP::G0)
  132. .addReg(SP::G0);
  133. return;
  134. }
  135. MachineFrameInfo *MFI = MF.getFrameInfo();
  136. int NumBytes = (int) MFI->getStackSize();
  137. if (NumBytes == 0)
  138. return;
  139. NumBytes = SubTarget.getAdjustedFrameSize(NumBytes);
  140. emitSPAdjustment(MF, MBB, MBBI, NumBytes, SP::ADDrr, SP::ADDri);
  141. }
  142. bool SparcFrameLowering::hasReservedCallFrame(const MachineFunction &MF) const {
  143. // Reserve call frame if there are no variable sized objects on the stack.
  144. return !MF.getFrameInfo()->hasVarSizedObjects();
  145. }
  146. // hasFP - Return true if the specified function should have a dedicated frame
  147. // pointer register. This is true if the function has variable sized allocas or
  148. // if frame pointer elimination is disabled.
  149. bool SparcFrameLowering::hasFP(const MachineFunction &MF) const {
  150. const MachineFrameInfo *MFI = MF.getFrameInfo();
  151. return MF.getTarget().Options.DisableFramePointerElim(MF) ||
  152. MFI->hasVarSizedObjects() || MFI->isFrameAddressTaken();
  153. }
  154. static bool LLVM_ATTRIBUTE_UNUSED verifyLeafProcRegUse(MachineRegisterInfo *MRI)
  155. {
  156. for (unsigned reg = SP::I0; reg <= SP::I7; ++reg)
  157. if (MRI->isPhysRegUsed(reg))
  158. return false;
  159. for (unsigned reg = SP::L0; reg <= SP::L7; ++reg)
  160. if (MRI->isPhysRegUsed(reg))
  161. return false;
  162. return true;
  163. }
  164. bool SparcFrameLowering::isLeafProc(MachineFunction &MF) const
  165. {
  166. MachineRegisterInfo &MRI = MF.getRegInfo();
  167. MachineFrameInfo *MFI = MF.getFrameInfo();
  168. return !(MFI->hasCalls() // has calls
  169. || MRI.isPhysRegUsed(SP::L0) // Too many registers needed
  170. || MRI.isPhysRegUsed(SP::O6) // %SP is used
  171. || hasFP(MF)); // need %FP
  172. }
  173. void SparcFrameLowering::remapRegsForLeafProc(MachineFunction &MF) const {
  174. MachineRegisterInfo &MRI = MF.getRegInfo();
  175. // Remap %i[0-7] to %o[0-7].
  176. for (unsigned reg = SP::I0; reg <= SP::I7; ++reg) {
  177. if (!MRI.isPhysRegUsed(reg))
  178. continue;
  179. unsigned mapped_reg = (reg - SP::I0 + SP::O0);
  180. assert(!MRI.isPhysRegUsed(mapped_reg));
  181. // Replace I register with O register.
  182. MRI.replaceRegWith(reg, mapped_reg);
  183. // Mark the reg unused.
  184. MRI.setPhysRegUnused(reg);
  185. }
  186. // Rewrite MBB's Live-ins.
  187. for (MachineFunction::iterator MBB = MF.begin(), E = MF.end();
  188. MBB != E; ++MBB) {
  189. for (unsigned reg = SP::I0; reg <= SP::I7; ++reg) {
  190. if (!MBB->isLiveIn(reg))
  191. continue;
  192. MBB->removeLiveIn(reg);
  193. MBB->addLiveIn(reg - SP::I0 + SP::O0);
  194. }
  195. }
  196. assert(verifyLeafProcRegUse(&MRI));
  197. #ifdef XDEBUG
  198. MF.verify(0, "After LeafProc Remapping");
  199. #endif
  200. }
  201. void SparcFrameLowering::processFunctionBeforeCalleeSavedScan
  202. (MachineFunction &MF, RegScavenger *RS) const {
  203. if (!DisableLeafProc && isLeafProc(MF)) {
  204. SparcMachineFunctionInfo *MFI = MF.getInfo<SparcMachineFunctionInfo>();
  205. MFI->setLeafProc(true);
  206. remapRegsForLeafProc(MF);
  207. }
  208. }