175 lines · c
1//===-- RISCVRegisterInfo.h - RISC-V Register Information Impl --*- 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-exception6//7//===----------------------------------------------------------------------===//8//9// This file contains the RISC-V implementation of the TargetRegisterInfo class.10//11//===----------------------------------------------------------------------===//12 13#ifndef LLVM_LIB_TARGET_RISCV_RISCVREGISTERINFO_H14#define LLVM_LIB_TARGET_RISCV_RISCVREGISTERINFO_H15 16#include "llvm/CodeGen/TargetRegisterInfo.h"17#include "llvm/TargetParser/RISCVTargetParser.h"18 19#define GET_REGINFO_HEADER20#include "RISCVGenRegisterInfo.inc"21 22namespace llvm {23 24namespace RISCVRI {25enum : uint8_t {26 // The IsVRegClass value of this RegisterClass.27 IsVRegClassShift = 0,28 IsVRegClassShiftMask = 0b1 << IsVRegClassShift,29 // The VLMul value of this RegisterClass. This value is valid iff IsVRegClass30 // is true.31 VLMulShift = IsVRegClassShift + 1,32 VLMulShiftMask = 0b11 << VLMulShift,33 34 // The NF value of this RegisterClass. This value is valid iff IsVRegClass is35 // true.36 NFShift = VLMulShift + 2,37 NFShiftMask = 0b111 << NFShift,38};39 40/// Register allocation hints for Zilsd register pairs41enum {42 // Used for Zilsd LD/SD register pairs43 RegPairOdd = 1,44 RegPairEven = 2,45};46 47/// \returns the IsVRegClass for the register class.48static inline bool isVRegClass(uint8_t TSFlags) {49 return (TSFlags & IsVRegClassShiftMask) >> IsVRegClassShift;50}51 52/// \returns the LMUL for the register class.53static inline RISCVVType::VLMUL getLMul(uint8_t TSFlags) {54 return static_cast<RISCVVType::VLMUL>((TSFlags & VLMulShiftMask) >>55 VLMulShift);56}57 58/// \returns the NF for the register class.59static inline unsigned getNF(uint8_t TSFlags) {60 return static_cast<unsigned>((TSFlags & NFShiftMask) >> NFShift) + 1;61}62} // namespace RISCVRI63 64struct RISCVRegisterInfo : public RISCVGenRegisterInfo {65 66 RISCVRegisterInfo(unsigned HwMode);67 68 const uint32_t *getCallPreservedMask(const MachineFunction &MF,69 CallingConv::ID) const override;70 71 unsigned getCSRFirstUseCost() const override {72 // The cost will be compared against BlockFrequency where entry has the73 // value of 1 << 14. A value of 5 will choose to spill or split cold74 // path instead of using a callee-saved register.75 return 5;76 }77 78 const MCPhysReg *getCalleeSavedRegs(const MachineFunction *MF) const override;79 80 const MCPhysReg *getIPRACSRegs(const MachineFunction *MF) const override;81 82 BitVector getReservedRegs(const MachineFunction &MF) const override;83 bool isAsmClobberable(const MachineFunction &MF,84 MCRegister PhysReg) const override;85 86 const uint32_t *getNoPreservedMask() const override;87 88 // Update DestReg to have the value SrcReg plus an offset. This is89 // used during frame layout, and we may need to ensure that if we90 // split the offset internally that the DestReg is always aligned,91 // assuming that source reg was.92 void adjustReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator II,93 const DebugLoc &DL, Register DestReg, Register SrcReg,94 StackOffset Offset, MachineInstr::MIFlag Flag,95 MaybeAlign RequiredAlign) const;96 97 bool eliminateFrameIndex(MachineBasicBlock::iterator MI, int SPAdj,98 unsigned FIOperandNum,99 RegScavenger *RS = nullptr) const override;100 101 bool requiresVirtualBaseRegisters(const MachineFunction &MF) const override;102 103 bool needsFrameBaseReg(MachineInstr *MI, int64_t Offset) const override;104 105 bool isFrameOffsetLegal(const MachineInstr *MI, Register BaseReg,106 int64_t Offset) const override;107 108 Register materializeFrameBaseRegister(MachineBasicBlock *MBB, int FrameIdx,109 int64_t Offset) const override;110 111 void resolveFrameIndex(MachineInstr &MI, Register BaseReg,112 int64_t Offset) const override;113 114 int64_t getFrameIndexInstrOffset(const MachineInstr *MI,115 int Idx) const override;116 117 void lowerSegmentSpillReload(MachineBasicBlock::iterator II,118 bool IsSpill) const;119 120 Register getFrameRegister(const MachineFunction &MF) const override;121 122 StringRef getRegAsmName(MCRegister Reg) const override;123 124 bool requiresRegisterScavenging(const MachineFunction &MF) const override {125 return true;126 }127 128 bool requiresFrameIndexScavenging(const MachineFunction &MF) const override {129 return true;130 }131 132 const TargetRegisterClass *133 getPointerRegClass(unsigned Kind = 0) const override {134 return &RISCV::GPRRegClass;135 }136 137 const TargetRegisterClass *138 getLargestLegalSuperClass(const TargetRegisterClass *RC,139 const MachineFunction &) const override;140 141 void getOffsetOpcodes(const StackOffset &Offset,142 SmallVectorImpl<uint64_t> &Ops) const override;143 144 unsigned getRegisterCostTableIndex(const MachineFunction &MF) const override;145 146 float getSpillWeightScaleFactor(const TargetRegisterClass *RC) const override;147 148 bool getRegAllocationHints(Register VirtReg, ArrayRef<MCPhysReg> Order,149 SmallVectorImpl<MCPhysReg> &Hints,150 const MachineFunction &MF, const VirtRegMap *VRM,151 const LiveRegMatrix *Matrix) const override;152 153 void updateRegAllocHint(Register Reg, Register NewReg,154 MachineFunction &MF) const override;155 156 Register findVRegWithEncoding(const TargetRegisterClass &RegClass,157 uint16_t Encoding) const;158 159 static bool isVRRegClass(const TargetRegisterClass *RC) {160 return RISCVRI::isVRegClass(RC->TSFlags) &&161 RISCVRI::getNF(RC->TSFlags) == 1;162 }163 164 static bool isVRNRegClass(const TargetRegisterClass *RC) {165 return RISCVRI::isVRegClass(RC->TSFlags) && RISCVRI::getNF(RC->TSFlags) > 1;166 }167 168 static bool isRVVRegClass(const TargetRegisterClass *RC) {169 return RISCVRI::isVRegClass(RC->TSFlags);170 }171};172} // namespace llvm173 174#endif175