1 /* 2 * Copyright (c) 2023 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef MAPLEBE_INCLUDE_CG_X64_X64_REG_INFO_H 17 #define MAPLEBE_INCLUDE_CG_X64_X64_REG_INFO_H 18 #include "reg_info.h" 19 #include "x64_abi.h" 20 #include "x64_cg.h" 21 22 namespace maplebe { 23 class X64CallConvImpl; 24 static const std::map<regno_t, uint32> x64IntParamsRegIdx = {{x64::RAX, 0}, {x64::RDI, 1}, {x64::RSI, 2}, {x64::RDX, 3}, 25 {x64::RCX, 4}, {x64::R8, 5}, {x64::R9, 6}}; 26 27 class X64RegInfo : public RegisterInfo { 28 public: X64RegInfo(MapleAllocator & mallocator,CallConvKind callConv)29 X64RegInfo(MapleAllocator &mallocator, CallConvKind callConv) : RegisterInfo(mallocator), callConv(callConv) {} 30 31 ~X64RegInfo() override = default; 32 33 void Init() override; 34 void Fini() override; 35 void SaveCalleeSavedReg(MapleSet<regno_t> savedRegs) override; 36 bool IsSpecialReg(regno_t regno) const override; 37 bool IsCalleeSavedReg(regno_t regno) const override; 38 bool IsYieldPointReg(regno_t regNO) const override; 39 bool IsUnconcernedReg(regno_t regNO) const override; 40 bool IsUnconcernedReg(const RegOperand ®Opnd) const override; 41 RegOperand *GetOrCreatePhyRegOperand(regno_t regNO, uint32 size, RegType kind, uint32 flag) override; 42 ListOperand *CreateListOperand() override; 43 Insn *BuildMovInstruction(Operand &opnd0, Operand &opnd1) override; 44 Insn *BuildStrInsn(uint32 regSize, PrimType stype, RegOperand &phyOpnd, MemOperand &memOpnd) override; 45 Insn *BuildLdrInsn(uint32 regSize, PrimType stype, RegOperand &phyOpnd, MemOperand &memOpnd) override; 46 Insn *BuildCommentInsn(const std::string &comment) override; 47 void FreeSpillRegMem(regno_t vrNum) override; 48 MemOperand *GetOrCreatSpillMem(regno_t vrNum, uint32 bitSize) override; 49 MemOperand *AdjustMemOperandIfOffsetOutOfRange(MemOperand *memOpnd, regno_t vrNum, bool isDest, Insn &insn, 50 regno_t regNum, bool &isOutOfRange) override; IsGPRegister(regno_t regNO)51 bool IsGPRegister(regno_t regNO) const override 52 { 53 return x64::IsGPRegister(static_cast<X64reg>(regNO)); 54 } 55 /* Those registers can not be overwrite. */ IsUntouchableReg(regno_t regNO)56 bool IsUntouchableReg(regno_t regNO) const override 57 { 58 return false; 59 } 60 /* Refactor later: Integrate parameters and return Reg */ GetIntRegsParmsNum()61 uint32 GetIntRegsParmsNum() override 62 { 63 /*Parms: rdi, rsi, rdx, rcx, r8, r9; Ret: rax, rdx */ 64 return X64CallConvImpl::GetCallConvInfo(callConv).GetIntParamRegsNum() + 1; 65 } GetIntRetRegsNum()66 uint32 GetIntRetRegsNum() override 67 { 68 return X64CallConvImpl::GetCallConvInfo(callConv).GetIntReturnRegsNum(); 69 } GetFpRetRegsNum()70 uint32 GetFpRetRegsNum() override 71 { 72 return X64CallConvImpl::GetCallConvInfo(callConv).GetFloatReturnRegsNum(); 73 } GetLastParamsIntReg()74 regno_t GetLastParamsIntReg() override 75 { 76 return static_cast<regno_t>(X64CallConvImpl::GetCallConvInfo(callConv).GetIntParamRegs().back()); 77 } GetNormalUseOperandNum()78 uint32 GetNormalUseOperandNum() override 79 { 80 return 0; 81 } GetIntRetReg(uint32 idx)82 regno_t GetIntRetReg(uint32 idx) override 83 { 84 CHECK_FATAL(idx <= GetIntRetRegsNum(), "index out of range in IntRetReg"); 85 return static_cast<regno_t>(X64CallConvImpl::GetCallConvInfo(callConv).GetIntReturnRegs()[idx]); 86 } GetFpRetReg(uint32 idx)87 regno_t GetFpRetReg(uint32 idx) override 88 { 89 CHECK_FATAL(idx <= GetFpRetRegsNum(), "index out of range in IntRetReg"); 90 return static_cast<regno_t>(X64CallConvImpl::GetCallConvInfo(callConv).GetFloatReturnRegs()[idx]); 91 } 92 /* phys reg which can be pre-Assignment: 93 * INT param regs -- rdi, rsi, rdx, rcx, r8, r9 94 * INT return regs -- rdx, rax 95 * FP param regs -- xmm0 ~ xmm7 96 * FP return regs -- xmm0 ~ xmm1 97 */ IsPreAssignedReg(regno_t regNO)98 bool IsPreAssignedReg(regno_t regNO) const override 99 { 100 return x64::IsParamReg(static_cast<X64reg>(regNO)) || regNO == x64::RAX || regNO == x64::RDX; 101 } GetIntParamRegIdx(regno_t regNO)102 uint32 GetIntParamRegIdx(regno_t regNO) const override 103 { 104 CHECK_FATAL(GetIntRegs().size(), "should be init before"); 105 return static_cast<uint32>(regNO - *GetIntRegs().begin()); 106 } GetFpParamRegIdx(regno_t regNO)107 uint32 GetFpParamRegIdx(regno_t regNO) const override 108 { 109 CHECK_FATAL(GetFpRegs().size(), "should be init before"); 110 return static_cast<uint32>(regNO - *GetFpRegs().begin()); 111 } GetLastParamsFpReg()112 regno_t GetLastParamsFpReg() override 113 { 114 return x64::kRinvalid; 115 } GetFloatRegsParmsNum()116 uint32 GetFloatRegsParmsNum() override 117 { 118 return X64CallConvImpl::GetCallConvInfo(callConv).GetFloatParamRegsNum(); 119 } GetFloatRegsRetsNum()120 uint32 GetFloatRegsRetsNum() 121 { 122 return X64CallConvImpl::GetCallConvInfo(callConv).GetFloatReturnRegsNum(); 123 } GetAllRegNum()124 uint32 GetAllRegNum() override 125 { 126 return x64::kAllRegNum; 127 } GetInvalidReg()128 regno_t GetInvalidReg() override 129 { 130 return x64::kRinvalid; 131 } IsAvailableReg(regno_t regNO)132 bool IsAvailableReg(regno_t regNO) const override 133 { 134 return x64::IsAvailableReg(static_cast<X64reg>(regNO)); 135 } IsVirtualRegister(const RegOperand & regOpnd)136 bool IsVirtualRegister(const RegOperand ®Opnd) override 137 { 138 return regOpnd.GetRegisterNumber() > kAllRegNum; 139 } IsVirtualRegister(regno_t regno)140 bool IsVirtualRegister(regno_t regno) override 141 { 142 return regno > kAllRegNum; 143 } GetReservedSpillReg()144 uint32 GetReservedSpillReg() override 145 { 146 return x64::kRinvalid; 147 } GetSecondReservedSpillReg()148 uint32 GetSecondReservedSpillReg() override 149 { 150 return x64::kRinvalid; 151 } IsSpillRegInRA(regno_t regNO,bool has3RegOpnd)152 bool IsSpillRegInRA(regno_t regNO, bool has3RegOpnd) override 153 { 154 return x64::IsSpillRegInRA(static_cast<X64reg>(regNO), has3RegOpnd); 155 } 156 157 private: 158 CallConvKind callConv; 159 }; 160 } /* namespace maplebe */ 161 162 #endif /* MAPLEBE_INCLUDE_CG_X64_X64_REG_INFO_H */ 163