NVPTXInstrInfo.cpp 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206
  1. //===- NVPTXInstrInfo.cpp - NVPTX Instruction Information -----------------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. // This file contains the NVPTX implementation of the TargetInstrInfo class.
  10. //
  11. //===----------------------------------------------------------------------===//
  12. #include "NVPTXInstrInfo.h"
  13. #include "NVPTX.h"
  14. #include "NVPTXTargetMachine.h"
  15. #include "llvm/ADT/STLExtras.h"
  16. #include "llvm/CodeGen/MachineFunction.h"
  17. #include "llvm/CodeGen/MachineInstrBuilder.h"
  18. #include "llvm/CodeGen/MachineRegisterInfo.h"
  19. #include "llvm/IR/Function.h"
  20. using namespace llvm;
  21. #define GET_INSTRINFO_CTOR_DTOR
  22. #include "NVPTXGenInstrInfo.inc"
  23. // Pin the vtable to this file.
  24. void NVPTXInstrInfo::anchor() {}
  25. NVPTXInstrInfo::NVPTXInstrInfo() : NVPTXGenInstrInfo(), RegInfo() {}
  26. void NVPTXInstrInfo::copyPhysReg(MachineBasicBlock &MBB,
  27. MachineBasicBlock::iterator I,
  28. const DebugLoc &DL, MCRegister DestReg,
  29. MCRegister SrcReg, bool KillSrc) const {
  30. const MachineRegisterInfo &MRI = MBB.getParent()->getRegInfo();
  31. const TargetRegisterClass *DestRC = MRI.getRegClass(DestReg);
  32. const TargetRegisterClass *SrcRC = MRI.getRegClass(SrcReg);
  33. if (RegInfo.getRegSizeInBits(*DestRC) != RegInfo.getRegSizeInBits(*SrcRC))
  34. report_fatal_error("Copy one register into another with a different width");
  35. unsigned Op;
  36. if (DestRC == &NVPTX::Int1RegsRegClass) {
  37. Op = NVPTX::IMOV1rr;
  38. } else if (DestRC == &NVPTX::Int16RegsRegClass) {
  39. Op = NVPTX::IMOV16rr;
  40. } else if (DestRC == &NVPTX::Int32RegsRegClass) {
  41. Op = (SrcRC == &NVPTX::Int32RegsRegClass ? NVPTX::IMOV32rr
  42. : NVPTX::BITCONVERT_32_F2I);
  43. } else if (DestRC == &NVPTX::Int64RegsRegClass) {
  44. Op = (SrcRC == &NVPTX::Int64RegsRegClass ? NVPTX::IMOV64rr
  45. : NVPTX::BITCONVERT_64_F2I);
  46. } else if (DestRC == &NVPTX::Float16RegsRegClass) {
  47. Op = (SrcRC == &NVPTX::Float16RegsRegClass ? NVPTX::FMOV16rr
  48. : NVPTX::BITCONVERT_16_I2F);
  49. } else if (DestRC == &NVPTX::Float16x2RegsRegClass) {
  50. Op = NVPTX::IMOV32rr;
  51. } else if (DestRC == &NVPTX::Float32RegsRegClass) {
  52. Op = (SrcRC == &NVPTX::Float32RegsRegClass ? NVPTX::FMOV32rr
  53. : NVPTX::BITCONVERT_32_I2F);
  54. } else if (DestRC == &NVPTX::Float64RegsRegClass) {
  55. Op = (SrcRC == &NVPTX::Float64RegsRegClass ? NVPTX::FMOV64rr
  56. : NVPTX::BITCONVERT_64_I2F);
  57. } else {
  58. llvm_unreachable("Bad register copy");
  59. }
  60. BuildMI(MBB, I, DL, get(Op), DestReg)
  61. .addReg(SrcReg, getKillRegState(KillSrc));
  62. }
  63. /// analyzeBranch - Analyze the branching code at the end of MBB, returning
  64. /// true if it cannot be understood (e.g. it's a switch dispatch or isn't
  65. /// implemented for a target). Upon success, this returns false and returns
  66. /// with the following information in various cases:
  67. ///
  68. /// 1. If this block ends with no branches (it just falls through to its succ)
  69. /// just return false, leaving TBB/FBB null.
  70. /// 2. If this block ends with only an unconditional branch, it sets TBB to be
  71. /// the destination block.
  72. /// 3. If this block ends with an conditional branch and it falls through to
  73. /// an successor block, it sets TBB to be the branch destination block and a
  74. /// list of operands that evaluate the condition. These
  75. /// operands can be passed to other TargetInstrInfo methods to create new
  76. /// branches.
  77. /// 4. If this block ends with an conditional branch and an unconditional
  78. /// block, it returns the 'true' destination in TBB, the 'false' destination
  79. /// in FBB, and a list of operands that evaluate the condition. These
  80. /// operands can be passed to other TargetInstrInfo methods to create new
  81. /// branches.
  82. ///
  83. /// Note that removeBranch and insertBranch must be implemented to support
  84. /// cases where this method returns success.
  85. ///
  86. bool NVPTXInstrInfo::analyzeBranch(MachineBasicBlock &MBB,
  87. MachineBasicBlock *&TBB,
  88. MachineBasicBlock *&FBB,
  89. SmallVectorImpl<MachineOperand> &Cond,
  90. bool AllowModify) const {
  91. // If the block has no terminators, it just falls into the block after it.
  92. MachineBasicBlock::iterator I = MBB.end();
  93. if (I == MBB.begin() || !isUnpredicatedTerminator(*--I))
  94. return false;
  95. // Get the last instruction in the block.
  96. MachineInstr &LastInst = *I;
  97. // If there is only one terminator instruction, process it.
  98. if (I == MBB.begin() || !isUnpredicatedTerminator(*--I)) {
  99. if (LastInst.getOpcode() == NVPTX::GOTO) {
  100. TBB = LastInst.getOperand(0).getMBB();
  101. return false;
  102. } else if (LastInst.getOpcode() == NVPTX::CBranch) {
  103. // Block ends with fall-through condbranch.
  104. TBB = LastInst.getOperand(1).getMBB();
  105. Cond.push_back(LastInst.getOperand(0));
  106. return false;
  107. }
  108. // Otherwise, don't know what this is.
  109. return true;
  110. }
  111. // Get the instruction before it if it's a terminator.
  112. MachineInstr &SecondLastInst = *I;
  113. // If there are three terminators, we don't know what sort of block this is.
  114. if (I != MBB.begin() && isUnpredicatedTerminator(*--I))
  115. return true;
  116. // If the block ends with NVPTX::GOTO and NVPTX:CBranch, handle it.
  117. if (SecondLastInst.getOpcode() == NVPTX::CBranch &&
  118. LastInst.getOpcode() == NVPTX::GOTO) {
  119. TBB = SecondLastInst.getOperand(1).getMBB();
  120. Cond.push_back(SecondLastInst.getOperand(0));
  121. FBB = LastInst.getOperand(0).getMBB();
  122. return false;
  123. }
  124. // If the block ends with two NVPTX:GOTOs, handle it. The second one is not
  125. // executed, so remove it.
  126. if (SecondLastInst.getOpcode() == NVPTX::GOTO &&
  127. LastInst.getOpcode() == NVPTX::GOTO) {
  128. TBB = SecondLastInst.getOperand(0).getMBB();
  129. I = LastInst;
  130. if (AllowModify)
  131. I->eraseFromParent();
  132. return false;
  133. }
  134. // Otherwise, can't handle this.
  135. return true;
  136. }
  137. unsigned NVPTXInstrInfo::removeBranch(MachineBasicBlock &MBB,
  138. int *BytesRemoved) const {
  139. assert(!BytesRemoved && "code size not handled");
  140. MachineBasicBlock::iterator I = MBB.end();
  141. if (I == MBB.begin())
  142. return 0;
  143. --I;
  144. if (I->getOpcode() != NVPTX::GOTO && I->getOpcode() != NVPTX::CBranch)
  145. return 0;
  146. // Remove the branch.
  147. I->eraseFromParent();
  148. I = MBB.end();
  149. if (I == MBB.begin())
  150. return 1;
  151. --I;
  152. if (I->getOpcode() != NVPTX::CBranch)
  153. return 1;
  154. // Remove the branch.
  155. I->eraseFromParent();
  156. return 2;
  157. }
  158. unsigned NVPTXInstrInfo::insertBranch(MachineBasicBlock &MBB,
  159. MachineBasicBlock *TBB,
  160. MachineBasicBlock *FBB,
  161. ArrayRef<MachineOperand> Cond,
  162. const DebugLoc &DL,
  163. int *BytesAdded) const {
  164. assert(!BytesAdded && "code size not handled");
  165. // Shouldn't be a fall through.
  166. assert(TBB && "insertBranch must not be told to insert a fallthrough");
  167. assert((Cond.size() == 1 || Cond.size() == 0) &&
  168. "NVPTX branch conditions have two components!");
  169. // One-way branch.
  170. if (!FBB) {
  171. if (Cond.empty()) // Unconditional branch
  172. BuildMI(&MBB, DL, get(NVPTX::GOTO)).addMBB(TBB);
  173. else // Conditional branch
  174. BuildMI(&MBB, DL, get(NVPTX::CBranch)).add(Cond[0]).addMBB(TBB);
  175. return 1;
  176. }
  177. // Two-way Conditional Branch.
  178. BuildMI(&MBB, DL, get(NVPTX::CBranch)).add(Cond[0]).addMBB(TBB);
  179. BuildMI(&MBB, DL, get(NVPTX::GOTO)).addMBB(FBB);
  180. return 2;
  181. }