LLVM  14.0.0git
LanaiRegisterInfo.cpp
Go to the documentation of this file.
1 //===-- LanaiRegisterInfo.cpp - Lanai Register 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 // This file contains the Lanai implementation of the TargetRegisterInfo class.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #include "LanaiRegisterInfo.h"
14 #include "LanaiAluCode.h"
15 #include "LanaiCondCode.h"
16 #include "LanaiFrameLowering.h"
17 #include "LanaiInstrInfo.h"
18 #include "llvm/ADT/BitVector.h"
19 #include "llvm/ADT/STLExtras.h"
26 #include "llvm/IR/Function.h"
27 #include "llvm/IR/Type.h"
29 
30 #define GET_REGINFO_TARGET_DESC
31 #include "LanaiGenRegisterInfo.inc"
32 
33 using namespace llvm;
34 
36 
37 const uint16_t *
39  return CSR_SaveList;
40 }
41 
43  BitVector Reserved(getNumRegs());
44 
45  Reserved.set(Lanai::R0);
46  Reserved.set(Lanai::R1);
47  Reserved.set(Lanai::PC);
48  Reserved.set(Lanai::R2);
49  Reserved.set(Lanai::SP);
50  Reserved.set(Lanai::R4);
51  Reserved.set(Lanai::FP);
52  Reserved.set(Lanai::R5);
53  Reserved.set(Lanai::RR1);
54  Reserved.set(Lanai::R10);
55  Reserved.set(Lanai::RR2);
56  Reserved.set(Lanai::R11);
57  Reserved.set(Lanai::RCA);
58  Reserved.set(Lanai::R15);
59  if (hasBasePointer(MF))
61  return Reserved;
62 }
63 
65  const MachineFunction & /*MF*/) const {
66  return true;
67 }
68 
69 static bool isALUArithLoOpcode(unsigned Opcode) {
70  switch (Opcode) {
71  case Lanai::ADD_I_LO:
72  case Lanai::SUB_I_LO:
73  case Lanai::ADD_F_I_LO:
74  case Lanai::SUB_F_I_LO:
75  case Lanai::ADDC_I_LO:
76  case Lanai::SUBB_I_LO:
77  case Lanai::ADDC_F_I_LO:
78  case Lanai::SUBB_F_I_LO:
79  return true;
80  default:
81  return false;
82  }
83 }
84 
85 static unsigned getOppositeALULoOpcode(unsigned Opcode) {
86  switch (Opcode) {
87  case Lanai::ADD_I_LO:
88  return Lanai::SUB_I_LO;
89  case Lanai::SUB_I_LO:
90  return Lanai::ADD_I_LO;
91  case Lanai::ADD_F_I_LO:
92  return Lanai::SUB_F_I_LO;
93  case Lanai::SUB_F_I_LO:
94  return Lanai::ADD_F_I_LO;
95  case Lanai::ADDC_I_LO:
96  return Lanai::SUBB_I_LO;
97  case Lanai::SUBB_I_LO:
98  return Lanai::ADDC_I_LO;
99  case Lanai::ADDC_F_I_LO:
100  return Lanai::SUBB_F_I_LO;
101  case Lanai::SUBB_F_I_LO:
102  return Lanai::ADDC_F_I_LO;
103  default:
104  llvm_unreachable("Invalid ALU lo opcode");
105  }
106 }
107 
108 static unsigned getRRMOpcodeVariant(unsigned Opcode) {
109  switch (Opcode) {
110  case Lanai::LDBs_RI:
111  return Lanai::LDBs_RR;
112  case Lanai::LDBz_RI:
113  return Lanai::LDBz_RR;
114  case Lanai::LDHs_RI:
115  return Lanai::LDHs_RR;
116  case Lanai::LDHz_RI:
117  return Lanai::LDHz_RR;
118  case Lanai::LDW_RI:
119  return Lanai::LDW_RR;
120  case Lanai::STB_RI:
121  return Lanai::STB_RR;
122  case Lanai::STH_RI:
123  return Lanai::STH_RR;
124  case Lanai::SW_RI:
125  return Lanai::SW_RR;
126  default:
127  llvm_unreachable("Opcode has no RRM variant");
128  }
129 }
130 
132  int SPAdj, unsigned FIOperandNum,
133  RegScavenger *RS) const {
134  assert(SPAdj == 0 && "Unexpected");
135 
136  MachineInstr &MI = *II;
137  MachineFunction &MF = *MI.getParent()->getParent();
140  bool HasFP = TFI->hasFP(MF);
141  DebugLoc DL = MI.getDebugLoc();
142 
143  int FrameIndex = MI.getOperand(FIOperandNum).getIndex();
144 
146  MI.getOperand(FIOperandNum + 1).getImm();
147 
148  // Addressable stack objects are addressed using neg. offsets from fp
149  // or pos. offsets from sp/basepointer
150  if (!HasFP || (hasStackRealignment(MF) && FrameIndex >= 0))
151  Offset += MF.getFrameInfo().getStackSize();
152 
153  Register FrameReg = getFrameRegister(MF);
154  if (FrameIndex >= 0) {
155  if (hasBasePointer(MF))
156  FrameReg = getBaseRegister();
157  else if (hasStackRealignment(MF))
158  FrameReg = Lanai::SP;
159  }
160 
161  // Replace frame index with a frame pointer reference.
162  // If the offset is small enough to fit in the immediate field, directly
163  // encode it.
164  // Otherwise scavenge a register and encode it into a MOVHI, OR_I_LO sequence.
165  if ((isSPLSOpcode(MI.getOpcode()) && !isInt<10>(Offset)) ||
166  !isInt<16>(Offset)) {
167  assert(RS && "Register scavenging must be on");
168  unsigned Reg = RS->FindUnusedReg(&Lanai::GPRRegClass);
169  if (!Reg)
170  Reg = RS->scavengeRegister(&Lanai::GPRRegClass, II, SPAdj);
171  assert(Reg && "Register scavenger failed");
172 
173  bool HasNegOffset = false;
174  // ALU ops have unsigned immediate values. If the Offset is negative, we
175  // negate it here and reverse the opcode later.
176  if (Offset < 0) {
177  HasNegOffset = true;
178  Offset = -Offset;
179  }
180 
181  if (!isInt<16>(Offset)) {
182  // Reg = hi(offset) | lo(offset)
183  BuildMI(*MI.getParent(), II, DL, TII->get(Lanai::MOVHI), Reg)
184  .addImm(static_cast<uint32_t>(Offset) >> 16);
185  BuildMI(*MI.getParent(), II, DL, TII->get(Lanai::OR_I_LO), Reg)
186  .addReg(Reg)
187  .addImm(Offset & 0xffffU);
188  } else {
189  // Reg = mov(offset)
190  BuildMI(*MI.getParent(), II, DL, TII->get(Lanai::ADD_I_LO), Reg)
191  .addImm(0)
192  .addImm(Offset);
193  }
194  // Reg = FrameReg OP Reg
195  if (MI.getOpcode() == Lanai::ADD_I_LO) {
196  BuildMI(*MI.getParent(), II, DL,
197  HasNegOffset ? TII->get(Lanai::SUB_R) : TII->get(Lanai::ADD_R),
198  MI.getOperand(0).getReg())
199  .addReg(FrameReg)
200  .addReg(Reg)
202  MI.eraseFromParent();
203  return;
204  }
205  if (isSPLSOpcode(MI.getOpcode()) || isRMOpcode(MI.getOpcode())) {
206  MI.setDesc(TII->get(getRRMOpcodeVariant(MI.getOpcode())));
207  if (HasNegOffset) {
208  // Change the ALU op (operand 3) from LPAC::ADD (the default) to
209  // LPAC::SUB with the already negated offset.
210  assert((MI.getOperand(3).getImm() == LPAC::ADD) &&
211  "Unexpected ALU op in RRM instruction");
212  MI.getOperand(3).setImm(LPAC::SUB);
213  }
214  } else
215  llvm_unreachable("Unexpected opcode in frame index operation");
216 
217  MI.getOperand(FIOperandNum).ChangeToRegister(FrameReg, /*isDef=*/false);
218  MI.getOperand(FIOperandNum + 1)
219  .ChangeToRegister(Reg, /*isDef=*/false, /*isImp=*/false,
220  /*isKill=*/true);
221  return;
222  }
223 
224  // ALU arithmetic ops take unsigned immediates. If the offset is negative,
225  // we replace the instruction with one that inverts the opcode and negates
226  // the immediate.
227  if ((Offset < 0) && isALUArithLoOpcode(MI.getOpcode())) {
228  unsigned NewOpcode = getOppositeALULoOpcode(MI.getOpcode());
229  // We know this is an ALU op, so we know the operands are as follows:
230  // 0: destination register
231  // 1: source register (frame register)
232  // 2: immediate
233  BuildMI(*MI.getParent(), II, DL, TII->get(NewOpcode),
234  MI.getOperand(0).getReg())
235  .addReg(FrameReg)
236  .addImm(-Offset);
237  MI.eraseFromParent();
238  } else {
239  MI.getOperand(FIOperandNum).ChangeToRegister(FrameReg, /*isDef=*/false);
240  MI.getOperand(FIOperandNum + 1).ChangeToImmediate(Offset);
241  }
242 }
243 
245  const MachineFrameInfo &MFI = MF.getFrameInfo();
246  // When we need stack realignment and there are dynamic allocas, we can't
247  // reference off of the stack pointer, so we reserve a base pointer.
248  if (hasStackRealignment(MF) && MFI.hasVarSizedObjects())
249  return true;
250 
251  return false;
252 }
253 
254 unsigned LanaiRegisterInfo::getRARegister() const { return Lanai::RCA; }
255 
256 Register
258  return Lanai::FP;
259 }
260 
261 Register LanaiRegisterInfo::getBaseRegister() const { return Lanai::R14; }
262 
263 const uint32_t *
265  CallingConv::ID /*CC*/) const {
266  return CSR_RegMask;
267 }
llvm::MachineFrameInfo::hasVarSizedObjects
bool hasVarSizedObjects() const
This method may be called any time after instruction selection is complete to determine if the stack ...
Definition: MachineFrameInfo.h:351
llvm::LPAC::ADD
@ ADD
Definition: LanaiAluCode.h:23
LanaiAluCode.h
MI
IRTranslator LLVM IR MI
Definition: IRTranslator.cpp:102
llvm::MachineInstrBuilder::addImm
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
Definition: MachineInstrBuilder.h:131
llvm
---------------------— PointerInfo ------------------------------------—
Definition: AllocatorList.h:23
Reg
unsigned Reg
Definition: MachineSink.cpp:1566
TargetFrameLowering.h
llvm::LanaiRegisterInfo::LanaiRegisterInfo
LanaiRegisterInfo()
Definition: LanaiRegisterInfo.cpp:35
llvm::TargetFrameLowering
Information about stack frame layout on the target.
Definition: TargetFrameLowering.h:43
llvm::TargetSubtargetInfo::getInstrInfo
virtual const TargetInstrInfo * getInstrInfo() const
Definition: TargetSubtargetInfo.h:92
llvm::LanaiRegisterInfo::getCallPreservedMask
const uint32_t * getCallPreservedMask(const MachineFunction &MF, CallingConv::ID) const override
Definition: LanaiRegisterInfo.cpp:264
llvm::LanaiRegisterInfo::requiresRegisterScavenging
bool requiresRegisterScavenging(const MachineFunction &MF) const override
Definition: LanaiRegisterInfo.cpp:64
ErrorHandling.h
R4
#define R4(n)
TargetInstrInfo.h
Offset
uint64_t Offset
Definition: ELFObjHandler.cpp:81
LanaiGenRegisterInfo
getOppositeALULoOpcode
static unsigned getOppositeALULoOpcode(unsigned Opcode)
Definition: LanaiRegisterInfo.cpp:85
STLExtras.h
getRRMOpcodeVariant
static unsigned getRRMOpcodeVariant(unsigned Opcode)
Definition: LanaiRegisterInfo.cpp:108
llvm::RegScavenger::FindUnusedReg
Register FindUnusedReg(const TargetRegisterClass *RC) const
Find an unused register of the specified register class.
Definition: RegisterScavenging.cpp:268
LanaiRegisterInfo.h
R2
#define R2(n)
LanaiFrameLowering.h
llvm::TargetInstrInfo
TargetInstrInfo - Interface to description of machine instruction set.
Definition: TargetInstrInfo.h:97
llvm::RegScavenger::scavengeRegister
Register scavengeRegister(const TargetRegisterClass *RC, MachineBasicBlock::iterator I, int SPAdj, bool AllowSpill=true)
Make a register of the specific register class available and do the appropriate bookkeeping.
Definition: RegisterScavenging.cpp:521
llvm::LanaiRegisterInfo::getCalleeSavedRegs
const uint16_t * getCalleeSavedRegs(const MachineFunction *MF=nullptr) const override
Definition: LanaiRegisterInfo.cpp:38
LanaiCondCode.h
TII
const HexagonInstrInfo * TII
Definition: HexagonCopyToCombine.cpp:129
llvm::TargetFrameLowering::hasFP
virtual bool hasFP(const MachineFunction &MF) const =0
hasFP - Return true if the specified function should have a dedicated frame pointer register.
BitVector.h
llvm::MachineFrameInfo::getStackSize
uint64_t getStackSize() const
Return the number of bytes that must be allocated to hold all of the fixed size frame objects.
Definition: MachineFrameInfo.h:551
llvm::MachineFrameInfo::getObjectOffset
int64_t getObjectOffset(int ObjectIdx) const
Return the assigned stack offset of the specified object from the incoming stack pointer.
Definition: MachineFrameInfo.h:492
llvm::BitVector
Definition: BitVector.h:74
llvm::LanaiRegisterInfo::hasBasePointer
bool hasBasePointer(const MachineFunction &MF) const
Definition: LanaiRegisterInfo.cpp:244
llvm::isRMOpcode
static bool isRMOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:160
llvm::CallingConv::ID
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition: CallingConv.h:24
Type.h
llvm::isSPLSOpcode
static bool isSPLSOpcode(unsigned Opcode)
Definition: LanaiInstrInfo.h:146
llvm::MachineFunction::getSubtarget
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
Definition: MachineFunction.h:622
llvm::LPAC::SUB
@ SUB
Definition: LanaiAluCode.h:25
llvm::MachineInstr
Representation of each machine instruction.
Definition: MachineInstr.h:64
llvm::LanaiRegisterInfo::eliminateFrameIndex
void eliminateFrameIndex(MachineBasicBlock::iterator II, int SPAdj, unsigned FIOperandNum, RegScavenger *RS=nullptr) const override
Definition: LanaiRegisterInfo.cpp:131
llvm::RegScavenger
Definition: RegisterScavenging.h:34
assert
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
llvm::MachineFunction::getFrameInfo
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
Definition: MachineFunction.h:638
llvm::LanaiRegisterInfo::getReservedRegs
BitVector getReservedRegs(const MachineFunction &MF) const override
Definition: LanaiRegisterInfo.cpp:42
llvm::MachineInstrBuilder::addReg
const MachineInstrBuilder & addReg(Register RegNo, unsigned flags=0, unsigned SubReg=0) const
Add a new virtual register operand.
Definition: MachineInstrBuilder.h:97
llvm::LanaiRegisterInfo::getBaseRegister
Register getBaseRegister() const
Definition: LanaiRegisterInfo.cpp:261
llvm::MachineFunction
Definition: MachineFunction.h:230
llvm_unreachable
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
Definition: ErrorHandling.h:136
uint32_t
llvm::LanaiRegisterInfo::getFrameRegister
Register getFrameRegister(const MachineFunction &MF) const override
Definition: LanaiRegisterInfo.cpp:257
DL
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
Definition: AArch64SLSHardening.cpp:76
llvm::Register
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
llvm::ISD::FrameIndex
@ FrameIndex
Definition: ISDOpcodes.h:80
llvm::isInt< 16 >
constexpr bool isInt< 16 >(int64_t x)
Definition: MathExtras.h:370
llvm::TargetSubtargetInfo::getFrameLowering
virtual const TargetFrameLowering * getFrameLowering() const
Definition: TargetSubtargetInfo.h:93
uint16_t
MachineFrameInfo.h
Function.h
llvm::MachineFrameInfo
The MachineFrameInfo class represents an abstract stack frame until prolog/epilog code is inserted.
Definition: MachineFrameInfo.h:107
MachineInstrBuilder.h
llvm::BuildMI
MachineInstrBuilder BuildMI(MachineFunction &MF, const DebugLoc &DL, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
Definition: MachineInstrBuilder.h:328
llvm::PseudoProbeAttributes::Reserved
@ Reserved
isALUArithLoOpcode
static bool isALUArithLoOpcode(unsigned Opcode)
Definition: LanaiRegisterInfo.cpp:69
llvm::LanaiRegisterInfo::getRARegister
unsigned getRARegister() const
Definition: LanaiRegisterInfo.cpp:254
llvm::DebugLoc
A debug info location.
Definition: DebugLoc.h:33
LanaiInstrInfo.h
RegisterScavenging.h
llvm::LPCC::ICC_T
@ ICC_T
Definition: LanaiCondCode.h:11
MachineFunction.h
llvm::MachineInstrBundleIterator< MachineInstr >