LLVM 24.0.0git
MipsABIInfo.cpp
Go to the documentation of this file.
1//===---- MipsABIInfo.cpp - Information about MIPS ABI's ------------------===//
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#include "MipsABIInfo.h"
10#include "Mips.h"
11#include "llvm/ADT/StringRef.h"
13
14using namespace llvm;
15
16namespace {
17static constexpr MCPhysReg O32IntRegs[] = {Mips::R4, Mips::R5, Mips::R6,
18 Mips::R7};
19static constexpr MCPhysReg NABIIntRegs[] = {Mips::R4, Mips::R5, Mips::R6,
20 Mips::R7, Mips::R8, Mips::R9,
21 Mips::R10, Mips::R11};
22static constexpr MCPhysReg Mips64IntRegs[] = {
23 Mips::R4_64, Mips::R5_64, Mips::R6_64, Mips::R7_64,
24 Mips::R8_64, Mips::R9_64, Mips::R10_64, Mips::R11_64};
25
26struct GPR {
27 MCPhysReg Reg32;
28 MCPhysReg Reg64;
29};
30
31static constexpr GPR OABITempRegs[] = {
32 {Mips::R8, Mips::R8_64}, {Mips::R9, Mips::R9_64},
33 {Mips::R10, Mips::R10_64}, {Mips::R11, Mips::R11_64},
34 {Mips::R12, Mips::R12_64}, {Mips::R13, Mips::R13_64},
35 {Mips::R14, Mips::R14_64}, {Mips::R15, Mips::R15_64},
36 {Mips::R24, Mips::R24_64}, {Mips::R25, Mips::R25_64},
37};
38
39static constexpr GPR NABITempRegs[] = {
40 {Mips::R12, Mips::R12_64},
41 {Mips::R13, Mips::R13_64},
42 {Mips::R14, Mips::R14_64},
43 {Mips::R15, Mips::R15_64},
44 {Mips::NoRegister, Mips::NoRegister},
45 {Mips::NoRegister, Mips::NoRegister},
46 {Mips::NoRegister, Mips::NoRegister},
47 {Mips::NoRegister, Mips::NoRegister},
48 {Mips::R24, Mips::R24_64},
49 {Mips::R25, Mips::R25_64},
50};
51
52static constexpr GPR PABITempRegs[] = {
53 {Mips::R12, Mips::R12_64},
54 {Mips::R13, Mips::R13_64},
55 {Mips::R14, Mips::R14_64},
56 {Mips::R15, Mips::R15_64},
57 {Mips::R2, Mips::R2_64},
58 {Mips::R3, Mips::R3_64},
59 {Mips::NoRegister, Mips::NoRegister},
60 {Mips::NoRegister, Mips::NoRegister},
61 {Mips::R24, Mips::R24_64},
62 {Mips::R25, Mips::R25_64},
63};
64
65static constexpr GPR SavedRegs[] = {
66 {Mips::R16, Mips::R16_64}, {Mips::R17, Mips::R17_64},
67 {Mips::R18, Mips::R18_64}, {Mips::R19, Mips::R19_64},
68 {Mips::R20, Mips::R20_64}, {Mips::R21, Mips::R21_64},
69 {Mips::R22, Mips::R22_64}, {Mips::R23, Mips::R23_64},
70};
71
72static constexpr GPR ReturnRegs[] = {
73 {Mips::R2, Mips::R2_64},
74 {Mips::R3, Mips::R3_64},
75};
76
77MCRegister getReg(ArrayRef<GPR> Regs, unsigned I, bool Is64Bit) {
78 assert(I < Regs.size() && "Invalid ABI register index");
79 MCRegister Reg = Is64Bit ? Regs[I].Reg64 : Regs[I].Reg32;
80 assert(Reg && "Register name is not defined by this ABI");
81 return Reg;
82}
83} // namespace
84
86 assert(IsKnown() && "Unknown ABI");
87 if (Is64Bit)
88 return ArrayRef(Mips64IntRegs).take_front(IsO32() ? 4 : 8);
89 return IsO32() ? ArrayRef(O32IntRegs) : ArrayRef(NABIIntRegs);
90}
91
95
97 switch (ThisABI) {
98 case ABI::O32:
99 return Mips::OABIRegAltName;
100 case ABI::N32:
101 case ABI::N64:
102 return Mips::NABIRegAltName;
103 case ABI::Unknown:
104 llvm_unreachable("Unknown ABI");
105 }
106 llvm_unreachable("Unhandled ABI");
107}
108
109MCRegister MipsABIInfo::getArgReg(unsigned I, bool Is64Bit) const {
110 ArrayRef<MCPhysReg> Regs = getArgRegs(Is64Bit);
111 assert(I < Regs.size() && "Invalid argument register");
112 return Regs[I];
113}
114
115MCRegister MipsABIInfo::getTempReg(unsigned I, bool Is64Bit) const {
116 switch (getRegAltNameIndex()) {
117 case Mips::OABIRegAltName:
118 return getReg(OABITempRegs, I, Is64Bit);
119 case Mips::NABIRegAltName:
120 return getReg(NABITempRegs, I, Is64Bit);
121 case Mips::PABIRegAltName:
122 return getReg(PABITempRegs, I, Is64Bit);
123 default:
124 llvm_unreachable("Unknown register naming convention");
125 }
126}
127
128MCRegister MipsABIInfo::getSavedReg(unsigned I, bool Is64Bit) const {
129 assert(IsKnown() && "Unknown ABI");
130 return getReg(SavedRegs, I, Is64Bit);
131}
132
133MCRegister MipsABIInfo::getReturnReg(unsigned I, bool Is64Bit) const {
134 switch (ThisABI) {
135 case ABI::O32:
136 case ABI::N32:
137 case ABI::N64:
138 return getReg(ReturnRegs, I, Is64Bit);
139 case ABI::Unknown:
140 llvm_unreachable("Unknown ABI");
141 }
142 llvm_unreachable("Unhandled ABI");
143}
144
146 if (IsO32()) {
147 if (isGP64bit)
148 return ArrayRef(Mips64IntRegs);
149 else
150 return ArrayRef(O32IntRegs);
151 }
152 if (IsN32() || IsN64())
153 return ArrayRef(Mips64IntRegs);
154 llvm_unreachable("Unhandled ABI");
155}
156
158 if (IsO32())
159 return CC != CallingConv::Fast ? 16 : 0;
160 if (IsN32() || IsN64())
161 return 0;
162 llvm_unreachable("Unhandled ABI");
163}
164
166 if (ABIName.starts_with("o32"))
167 return MipsABIInfo::O32();
168 if (ABIName.starts_with("n32"))
169 return MipsABIInfo::N32();
170 if (ABIName.starts_with("n64"))
171 return MipsABIInfo::N64();
172 if (TT.isABIN32())
173 return MipsABIInfo::N32();
174 assert(ABIName.empty() && "Unknown ABI option for MIPS");
175
176 if (TT.isMIPS64())
177 return MipsABIInfo::N64();
178 return MipsABIInfo::O32();
179}
180
181unsigned MipsABIInfo::GetStackPtr() const {
182 return ArePtrs64bit() ? Mips::SP_64 : Mips::SP;
183}
184
185unsigned MipsABIInfo::GetFramePtr() const {
186 return ArePtrs64bit() ? Mips::FP_64 : Mips::FP;
187}
188
189unsigned MipsABIInfo::GetBasePtr() const { return getSavedRegPtr(7); }
190
192 return ArePtrs64bit() ? Mips::GP_64 : Mips::GP;
193}
194
195unsigned MipsABIInfo::GetNullPtr() const {
196 return ArePtrs64bit() ? Mips::R0_64 : Mips::R0;
197}
198
199unsigned MipsABIInfo::GetZeroReg() const {
200 return AreGprs64bit() ? Mips::R0_64 : Mips::R0;
201}
202
204 return ArePtrs64bit() ? Mips::DADDu : Mips::ADDu;
205}
206
208 return ArePtrs64bit() ? Mips::DADDiu : Mips::ADDiu;
209}
210
212 return ArePtrs64bit() ? Mips::DSUBu : Mips::SUBu;
213}
214
215unsigned MipsABIInfo::GetPtrAndOp() const {
216 return ArePtrs64bit() ? Mips::AND64 : Mips::AND;
217}
218
220 return ArePtrs64bit() ? Mips::OR64 : Mips::OR;
221}
222
223unsigned MipsABIInfo::GetEhDataReg(unsigned I) const {
224 assert(I < 4 && "Invalid EH data register");
225 return getArgRegPtr(I);
226}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
#define I(x, y, z)
Definition MD5.cpp:57
Register Reg
static MCRegister getReg(const MCDisassembler *D, unsigned RC, unsigned RegNo)
Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
size_t size() const
Get the array size.
Definition ArrayRef.h:141
Wrapper class representing physical registers. Should be passed by value.
Definition MCRegister.h:41
bool AreGprs64bit() const
bool IsN64() const
Definition MipsABIInfo.h:41
unsigned GetGlobalPtr() const
static MipsABIInfo O32()
Definition MipsABIInfo.h:33
MipsABIInfo(ABI ThisABI)
Definition MipsABIInfo.h:30
unsigned GetEhDataReg(unsigned I) const
bool ArePtrs64bit() const
unsigned GetGPRMoveOp() const
MCRegister getArgReg(unsigned I, bool Is64Bit) const
ABI register accessors default to the ABI's GPR width.
unsigned GetStackPtr() const
static MipsABIInfo N32()
Definition MipsABIInfo.h:34
unsigned GetZeroReg() const
unsigned GetCalleeAllocdArgSizeInBytes(CallingConv::ID CC) const
Obtain the size of the area allocated by the callee for arguments.
static MipsABIInfo N64()
Definition MipsABIInfo.h:35
unsigned GetPtrAddiuOp() const
unsigned GetPtrAndOp() const
unsigned GetFramePtr() const
unsigned getRegAltNameIndex() const
Register naming convention for this ABI.
static MipsABIInfo computeTargetABI(const Triple &TT, StringRef ABIName)
ArrayRef< MCPhysReg > GetByValArgRegs() const
The registers to use for byval arguments.
unsigned GetNullPtr() const
ArrayRef< MCPhysReg > getVarArgRegs(bool isGP64bit) const
The registers to use for the variable argument list.
unsigned GetPtrAdduOp() const
bool IsKnown() const
Definition MipsABIInfo.h:38
bool IsN32() const
Definition MipsABIInfo.h:40
MCRegister getReturnReg(unsigned I, bool Is64Bit) const
Integer return-value registers.
MCRegister getSavedReg(unsigned I, bool Is64Bit) const
unsigned GetBasePtr() const
unsigned GetPtrSubuOp() const
MCRegister getSavedRegPtr(unsigned I) const
Definition MipsABIInfo.h:72
bool IsO32() const
Definition MipsABIInfo.h:39
MCRegister getTempReg(unsigned I, bool Is64Bit) const
I is the suffix in tI (NABI has t0-t3 and t8-t9).
ArrayRef< MCPhysReg > getArgRegs(bool Is64Bit) const
Integer argument registers in calling-convention order.
MCRegister getArgRegPtr(unsigned I) const
Definition MipsABIInfo.h:57
Represent a constant reference to a string, i.e.
Definition StringRef.h:56
bool starts_with(StringRef Prefix) const
Check if this string starts with the given Prefix.
Definition StringRef.h:258
constexpr bool empty() const
Check if the string is empty.
Definition StringRef.h:141
Triple - Helper class for working with autoconf configuration names.
Definition Triple.h:48
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
Definition CallingConv.h:24
@ Fast
Attempts to make calls as fast as possible (e.g.
Definition CallingConv.h:41
constexpr MCPhysReg FP_64
constexpr MCPhysReg GP_64
constexpr MCPhysReg FP
constexpr MCPhysReg GP
constexpr MCPhysReg SP
constexpr MCPhysReg SP_64
This is an optimization pass for GlobalISel generic memory operations.
uint16_t MCPhysReg
An unsigned integer type large enough to represent all physical registers, but not necessarily virtua...
Definition MCRegister.h:21
ArrayRef(const T &OneElt) -> ArrayRef< T >