1//===-- VERegisterInfo.cpp - VE Register 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 VE implementation of the TargetRegisterInfo class.
10//
11//===----------------------------------------------------------------------===//
12
13#include "VERegisterInfo.h"
14#include "VE.h"
15#include "VESubtarget.h"
16#include "llvm/ADT/BitVector.h"
17#include "llvm/ADT/STLExtras.h"
18#include "llvm/CodeGen/MachineFrameInfo.h"
19#include "llvm/CodeGen/MachineFunction.h"
20#include "llvm/CodeGen/MachineInstrBuilder.h"
21#include "llvm/CodeGen/MachineRegisterInfo.h"
22#include "llvm/CodeGen/TargetInstrInfo.h"
23#include "llvm/IR/Type.h"
24#include "llvm/Support/CommandLine.h"
25#include "llvm/Support/ErrorHandling.h"
26
27using namespace llvm;
28
29#define GET_REGINFO_TARGET_DESC
30#include "VEGenRegisterInfo.inc"
31
32// VE uses %s10 == %lp to keep return address
33VERegisterInfo::VERegisterInfo() : VEGenRegisterInfo(VE::SX10) {}
34
35const MCPhysReg *
36VERegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
37  return CSR_SaveList;
38}
39
40const uint32_t *VERegisterInfo::getCallPreservedMask(const MachineFunction &MF,
41                                                     CallingConv::ID CC) const {
42  return CSR_RegMask;
43}
44
45const uint32_t *VERegisterInfo::getNoPreservedMask() const {
46  return CSR_NoRegs_RegMask;
47}
48
49BitVector VERegisterInfo::getReservedRegs(const MachineFunction &MF) const {
50  BitVector Reserved(getNumRegs());
51  Reserved.set(VE::SX8);  // stack limit
52  Reserved.set(VE::SX9);  // frame pointer
53  Reserved.set(VE::SX10); // link register (return address)
54  Reserved.set(VE::SX11); // stack pointer
55
56  Reserved.set(VE::SX12); // outer register
57  Reserved.set(VE::SX13); // id register for dynamic linker
58
59  Reserved.set(VE::SX14); // thread pointer
60  Reserved.set(VE::SX15); // global offset table register
61  Reserved.set(VE::SX16); // procedure linkage table register
62  Reserved.set(VE::SX17); // linkage-area register
63
64  // sx18-sx33 are callee-saved registers
65  // sx34-sx63 are temporary registers
66
67  return Reserved;
68}
69
70bool VERegisterInfo::isConstantPhysReg(unsigned PhysReg) const { return false; }
71
72const TargetRegisterClass *
73VERegisterInfo::getPointerRegClass(const MachineFunction &MF,
74                                   unsigned Kind) const {
75  return &VE::I64RegClass;
76}
77
78static void replaceFI(MachineFunction &MF, MachineBasicBlock::iterator II,
79                      MachineInstr &MI, const DebugLoc &dl,
80                      unsigned FIOperandNum, int Offset, unsigned FramePtr) {
81  // Replace frame index with a frame pointer reference directly.
82  // VE has 32 bit offset field, so no need to expand a target instruction.
83  // Directly encode it.
84  MI.getOperand(FIOperandNum).ChangeToRegister(FramePtr, false);
85  MI.getOperand(FIOperandNum + 1).ChangeToImmediate(Offset);
86}
87
88void VERegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator II,
89                                         int SPAdj, unsigned FIOperandNum,
90                                         RegScavenger *RS) const {
91  assert(SPAdj == 0 && "Unexpected");
92
93  MachineInstr &MI = *II;
94  DebugLoc dl = MI.getDebugLoc();
95  int FrameIndex = MI.getOperand(FIOperandNum).getIndex();
96  MachineFunction &MF = *MI.getParent()->getParent();
97  const VEFrameLowering *TFI = getFrameLowering(MF);
98
99  unsigned FrameReg;
100  int Offset;
101  Offset = TFI->getFrameIndexReference(MF, FrameIndex, FrameReg);
102
103  Offset += MI.getOperand(FIOperandNum + 1).getImm();
104
105  replaceFI(MF, II, MI, dl, FIOperandNum, Offset, FrameReg);
106}
107
108Register VERegisterInfo::getFrameRegister(const MachineFunction &MF) const {
109  return VE::SX9;
110}
111
112// VE has no architectural need for stack realignment support,
113// except that LLVM unfortunately currently implements overaligned
114// stack objects by depending upon stack realignment support.
115// If that ever changes, this can probably be deleted.
116bool VERegisterInfo::canRealignStack(const MachineFunction &MF) const {
117  if (!TargetRegisterInfo::canRealignStack(MF))
118    return false;
119
120  // VE always has a fixed frame pointer register, so don't need to
121  // worry about needing to reserve it. [even if we don't have a frame
122  // pointer for our frame, it still cannot be used for other things,
123  // or register window traps will be SADNESS.]
124
125  // If there's a reserved call frame, we can use VE to access locals.
126  if (getFrameLowering(MF)->hasReservedCallFrame(MF))
127    return true;
128
129  // Otherwise, we'd need a base pointer, but those aren't implemented
130  // for VE at the moment.
131
132  return false;
133}
134