Path: blob/main/contrib/llvm-project/llvm/lib/Target/RISCV/RISCVFrameLowering.cpp
35266 views
//===-- RISCVFrameLowering.cpp - RISC-V Frame Information -----------------===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//7//8// This file contains the RISC-V implementation of TargetFrameLowering class.9//10//===----------------------------------------------------------------------===//1112#include "RISCVFrameLowering.h"13#include "RISCVMachineFunctionInfo.h"14#include "RISCVSubtarget.h"15#include "llvm/BinaryFormat/Dwarf.h"16#include "llvm/CodeGen/MachineFrameInfo.h"17#include "llvm/CodeGen/MachineFunction.h"18#include "llvm/CodeGen/MachineInstrBuilder.h"19#include "llvm/CodeGen/MachineRegisterInfo.h"20#include "llvm/CodeGen/RegisterScavenging.h"21#include "llvm/IR/DiagnosticInfo.h"22#include "llvm/MC/MCDwarf.h"23#include "llvm/Support/LEB128.h"2425#include <algorithm>2627using namespace llvm;2829static Align getABIStackAlignment(RISCVABI::ABI ABI) {30if (ABI == RISCVABI::ABI_ILP32E)31return Align(4);32if (ABI == RISCVABI::ABI_LP64E)33return Align(8);34return Align(16);35}3637RISCVFrameLowering::RISCVFrameLowering(const RISCVSubtarget &STI)38: TargetFrameLowering(39StackGrowsDown, getABIStackAlignment(STI.getTargetABI()),40/*LocalAreaOffset=*/0,41/*TransientStackAlignment=*/getABIStackAlignment(STI.getTargetABI())),42STI(STI) {}4344// Offsets which need to be scale by XLen representing locations of CSRs which45// are given a fixed location by save/restore libcalls or Zcmp Push/Pop.46static const std::pair<MCPhysReg, int8_t> FixedCSRFIMap[] = {47{/*ra*/ RISCV::X1, -1}, {/*s0*/ RISCV::X8, -2},48{/*s1*/ RISCV::X9, -3}, {/*s2*/ RISCV::X18, -4},49{/*s3*/ RISCV::X19, -5}, {/*s4*/ RISCV::X20, -6},50{/*s5*/ RISCV::X21, -7}, {/*s6*/ RISCV::X22, -8},51{/*s7*/ RISCV::X23, -9}, {/*s8*/ RISCV::X24, -10},52{/*s9*/ RISCV::X25, -11}, {/*s10*/ RISCV::X26, -12},53{/*s11*/ RISCV::X27, -13}};5455// For now we use x3, a.k.a gp, as pointer to shadow call stack.56// User should not use x3 in their asm.57static void emitSCSPrologue(MachineFunction &MF, MachineBasicBlock &MBB,58MachineBasicBlock::iterator MI,59const DebugLoc &DL) {60if (!MF.getFunction().hasFnAttribute(Attribute::ShadowCallStack))61return;6263const auto &STI = MF.getSubtarget<RISCVSubtarget>();64const llvm::RISCVRegisterInfo *TRI = STI.getRegisterInfo();65Register RAReg = TRI->getRARegister();6667// Do not save RA to the SCS if it's not saved to the regular stack,68// i.e. RA is not at risk of being overwritten.69std::vector<CalleeSavedInfo> &CSI = MF.getFrameInfo().getCalleeSavedInfo();70if (llvm::none_of(71CSI, [&](CalleeSavedInfo &CSR) { return CSR.getReg() == RAReg; }))72return;7374const RISCVInstrInfo *TII = STI.getInstrInfo();75if (!STI.hasForcedSWShadowStack() && STI.hasStdExtZicfiss()) {76BuildMI(MBB, MI, DL, TII->get(RISCV::SSPUSH)).addReg(RAReg);77return;78}7980Register SCSPReg = RISCVABI::getSCSPReg();8182bool IsRV64 = STI.hasFeature(RISCV::Feature64Bit);83int64_t SlotSize = STI.getXLen() / 8;84// Store return address to shadow call stack85// addi gp, gp, [4|8]86// s[w|d] ra, -[4|8](gp)87BuildMI(MBB, MI, DL, TII->get(RISCV::ADDI))88.addReg(SCSPReg, RegState::Define)89.addReg(SCSPReg)90.addImm(SlotSize)91.setMIFlag(MachineInstr::FrameSetup);92BuildMI(MBB, MI, DL, TII->get(IsRV64 ? RISCV::SD : RISCV::SW))93.addReg(RAReg)94.addReg(SCSPReg)95.addImm(-SlotSize)96.setMIFlag(MachineInstr::FrameSetup);9798// Emit a CFI instruction that causes SlotSize to be subtracted from the value99// of the shadow stack pointer when unwinding past this frame.100char DwarfSCSReg = TRI->getDwarfRegNum(SCSPReg, /*IsEH*/ true);101assert(DwarfSCSReg < 32 && "SCS Register should be < 32 (X3).");102103char Offset = static_cast<char>(-SlotSize) & 0x7f;104const char CFIInst[] = {105dwarf::DW_CFA_val_expression,106DwarfSCSReg, // register1072, // length108static_cast<char>(unsigned(dwarf::DW_OP_breg0 + DwarfSCSReg)),109Offset, // addend (sleb128)110};111112unsigned CFIIndex = MF.addFrameInst(MCCFIInstruction::createEscape(113nullptr, StringRef(CFIInst, sizeof(CFIInst))));114BuildMI(MBB, MI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))115.addCFIIndex(CFIIndex)116.setMIFlag(MachineInstr::FrameSetup);117}118119static void emitSCSEpilogue(MachineFunction &MF, MachineBasicBlock &MBB,120MachineBasicBlock::iterator MI,121const DebugLoc &DL) {122if (!MF.getFunction().hasFnAttribute(Attribute::ShadowCallStack))123return;124125const auto &STI = MF.getSubtarget<RISCVSubtarget>();126Register RAReg = STI.getRegisterInfo()->getRARegister();127128// See emitSCSPrologue() above.129std::vector<CalleeSavedInfo> &CSI = MF.getFrameInfo().getCalleeSavedInfo();130if (llvm::none_of(131CSI, [&](CalleeSavedInfo &CSR) { return CSR.getReg() == RAReg; }))132return;133134const RISCVInstrInfo *TII = STI.getInstrInfo();135if (!STI.hasForcedSWShadowStack() && STI.hasStdExtZicfiss()) {136BuildMI(MBB, MI, DL, TII->get(RISCV::SSPOPCHK)).addReg(RAReg);137return;138}139140Register SCSPReg = RISCVABI::getSCSPReg();141142bool IsRV64 = STI.hasFeature(RISCV::Feature64Bit);143int64_t SlotSize = STI.getXLen() / 8;144// Load return address from shadow call stack145// l[w|d] ra, -[4|8](gp)146// addi gp, gp, -[4|8]147BuildMI(MBB, MI, DL, TII->get(IsRV64 ? RISCV::LD : RISCV::LW))148.addReg(RAReg, RegState::Define)149.addReg(SCSPReg)150.addImm(-SlotSize)151.setMIFlag(MachineInstr::FrameDestroy);152BuildMI(MBB, MI, DL, TII->get(RISCV::ADDI))153.addReg(SCSPReg, RegState::Define)154.addReg(SCSPReg)155.addImm(-SlotSize)156.setMIFlag(MachineInstr::FrameDestroy);157// Restore the SCS pointer158unsigned CFIIndex = MF.addFrameInst(MCCFIInstruction::createRestore(159nullptr, STI.getRegisterInfo()->getDwarfRegNum(SCSPReg, /*IsEH*/ true)));160BuildMI(MBB, MI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))161.addCFIIndex(CFIIndex)162.setMIFlags(MachineInstr::FrameDestroy);163}164165// Get the ID of the libcall used for spilling and restoring callee saved166// registers. The ID is representative of the number of registers saved or167// restored by the libcall, except it is zero-indexed - ID 0 corresponds to a168// single register.169static int getLibCallID(const MachineFunction &MF,170const std::vector<CalleeSavedInfo> &CSI) {171const auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();172173if (CSI.empty() || !RVFI->useSaveRestoreLibCalls(MF))174return -1;175176Register MaxReg = RISCV::NoRegister;177for (auto &CS : CSI)178// assignCalleeSavedSpillSlots assigns negative frame indexes to179// registers which can be saved by libcall.180if (CS.getFrameIdx() < 0)181MaxReg = std::max(MaxReg.id(), CS.getReg().id());182183if (MaxReg == RISCV::NoRegister)184return -1;185186switch (MaxReg) {187default:188llvm_unreachable("Something has gone wrong!");189case /*s11*/ RISCV::X27: return 12;190case /*s10*/ RISCV::X26: return 11;191case /*s9*/ RISCV::X25: return 10;192case /*s8*/ RISCV::X24: return 9;193case /*s7*/ RISCV::X23: return 8;194case /*s6*/ RISCV::X22: return 7;195case /*s5*/ RISCV::X21: return 6;196case /*s4*/ RISCV::X20: return 5;197case /*s3*/ RISCV::X19: return 4;198case /*s2*/ RISCV::X18: return 3;199case /*s1*/ RISCV::X9: return 2;200case /*s0*/ RISCV::X8: return 1;201case /*ra*/ RISCV::X1: return 0;202}203}204205// Get the name of the libcall used for spilling callee saved registers.206// If this function will not use save/restore libcalls, then return a nullptr.207static const char *208getSpillLibCallName(const MachineFunction &MF,209const std::vector<CalleeSavedInfo> &CSI) {210static const char *const SpillLibCalls[] = {211"__riscv_save_0",212"__riscv_save_1",213"__riscv_save_2",214"__riscv_save_3",215"__riscv_save_4",216"__riscv_save_5",217"__riscv_save_6",218"__riscv_save_7",219"__riscv_save_8",220"__riscv_save_9",221"__riscv_save_10",222"__riscv_save_11",223"__riscv_save_12"224};225226int LibCallID = getLibCallID(MF, CSI);227if (LibCallID == -1)228return nullptr;229return SpillLibCalls[LibCallID];230}231232// Get the name of the libcall used for restoring callee saved registers.233// If this function will not use save/restore libcalls, then return a nullptr.234static const char *235getRestoreLibCallName(const MachineFunction &MF,236const std::vector<CalleeSavedInfo> &CSI) {237static const char *const RestoreLibCalls[] = {238"__riscv_restore_0",239"__riscv_restore_1",240"__riscv_restore_2",241"__riscv_restore_3",242"__riscv_restore_4",243"__riscv_restore_5",244"__riscv_restore_6",245"__riscv_restore_7",246"__riscv_restore_8",247"__riscv_restore_9",248"__riscv_restore_10",249"__riscv_restore_11",250"__riscv_restore_12"251};252253int LibCallID = getLibCallID(MF, CSI);254if (LibCallID == -1)255return nullptr;256return RestoreLibCalls[LibCallID];257}258259// Return encoded value and register count for PUSH/POP instruction,260// representing registers to store/load.261static std::pair<unsigned, unsigned>262getPushPopEncodingAndNum(const Register MaxReg) {263switch (MaxReg) {264default:265llvm_unreachable("Unexpected Reg for Push/Pop Inst");266case RISCV::X27: /*s11*/267return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S11, 13);268case RISCV::X25: /*s9*/269return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S9, 11);270case RISCV::X24: /*s8*/271return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S8, 10);272case RISCV::X23: /*s7*/273return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S7, 9);274case RISCV::X22: /*s6*/275return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S6, 8);276case RISCV::X21: /*s5*/277return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S5, 7);278case RISCV::X20: /*s4*/279return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S4, 6);280case RISCV::X19: /*s3*/281return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S3, 5);282case RISCV::X18: /*s2*/283return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S2, 4);284case RISCV::X9: /*s1*/285return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0_S1, 3);286case RISCV::X8: /*s0*/287return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA_S0, 2);288case RISCV::X1: /*ra*/289return std::make_pair(llvm::RISCVZC::RLISTENCODE::RA, 1);290}291}292293// Get the max reg of Push/Pop for restoring callee saved registers.294static Register getMaxPushPopReg(const MachineFunction &MF,295const std::vector<CalleeSavedInfo> &CSI) {296Register MaxPushPopReg = RISCV::NoRegister;297for (auto &CS : CSI) {298if (llvm::find_if(FixedCSRFIMap, [&](auto P) {299return P.first == CS.getReg();300}) != std::end(FixedCSRFIMap))301MaxPushPopReg = std::max(MaxPushPopReg.id(), CS.getReg().id());302}303assert(MaxPushPopReg != RISCV::X26 && "x26 requires x27 to also be pushed");304return MaxPushPopReg;305}306307// Return true if the specified function should have a dedicated frame308// pointer register. This is true if frame pointer elimination is309// disabled, if it needs dynamic stack realignment, if the function has310// variable sized allocas, or if the frame address is taken.311bool RISCVFrameLowering::hasFP(const MachineFunction &MF) const {312const TargetRegisterInfo *RegInfo = MF.getSubtarget().getRegisterInfo();313314const MachineFrameInfo &MFI = MF.getFrameInfo();315return MF.getTarget().Options.DisableFramePointerElim(MF) ||316RegInfo->hasStackRealignment(MF) || MFI.hasVarSizedObjects() ||317MFI.isFrameAddressTaken();318}319320bool RISCVFrameLowering::hasBP(const MachineFunction &MF) const {321const MachineFrameInfo &MFI = MF.getFrameInfo();322const TargetRegisterInfo *TRI = STI.getRegisterInfo();323324// If we do not reserve stack space for outgoing arguments in prologue,325// we will adjust the stack pointer before call instruction. After the326// adjustment, we can not use SP to access the stack objects for the327// arguments. Instead, use BP to access these stack objects.328return (MFI.hasVarSizedObjects() ||329(!hasReservedCallFrame(MF) && (!MFI.isMaxCallFrameSizeComputed() ||330MFI.getMaxCallFrameSize() != 0))) &&331TRI->hasStackRealignment(MF);332}333334// Determines the size of the frame and maximum call frame size.335void RISCVFrameLowering::determineFrameLayout(MachineFunction &MF) const {336MachineFrameInfo &MFI = MF.getFrameInfo();337auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();338339// Get the number of bytes to allocate from the FrameInfo.340uint64_t FrameSize = MFI.getStackSize();341342// Get the alignment.343Align StackAlign = getStackAlign();344345// Make sure the frame is aligned.346FrameSize = alignTo(FrameSize, StackAlign);347348// Update frame info.349MFI.setStackSize(FrameSize);350351// When using SP or BP to access stack objects, we may require extra padding352// to ensure the bottom of the RVV stack is correctly aligned within the main353// stack. We calculate this as the amount required to align the scalar local354// variable section up to the RVV alignment.355const TargetRegisterInfo *TRI = STI.getRegisterInfo();356if (RVFI->getRVVStackSize() && (!hasFP(MF) || TRI->hasStackRealignment(MF))) {357int ScalarLocalVarSize = FrameSize - RVFI->getCalleeSavedStackSize() -358RVFI->getVarArgsSaveSize();359if (auto RVVPadding =360offsetToAlignment(ScalarLocalVarSize, RVFI->getRVVStackAlign()))361RVFI->setRVVPadding(RVVPadding);362}363}364365// Returns the stack size including RVV padding (when required), rounded back366// up to the required stack alignment.367uint64_t RISCVFrameLowering::getStackSizeWithRVVPadding(368const MachineFunction &MF) const {369const MachineFrameInfo &MFI = MF.getFrameInfo();370auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();371return alignTo(MFI.getStackSize() + RVFI->getRVVPadding(), getStackAlign());372}373374// Returns the register used to hold the frame pointer.375static Register getFPReg(const RISCVSubtarget &STI) { return RISCV::X8; }376377// Returns the register used to hold the stack pointer.378static Register getSPReg(const RISCVSubtarget &STI) { return RISCV::X2; }379380static SmallVector<CalleeSavedInfo, 8>381getUnmanagedCSI(const MachineFunction &MF,382const std::vector<CalleeSavedInfo> &CSI) {383const MachineFrameInfo &MFI = MF.getFrameInfo();384SmallVector<CalleeSavedInfo, 8> NonLibcallCSI;385386for (auto &CS : CSI) {387int FI = CS.getFrameIdx();388if (FI >= 0 && MFI.getStackID(FI) == TargetStackID::Default)389NonLibcallCSI.push_back(CS);390}391392return NonLibcallCSI;393}394395static SmallVector<CalleeSavedInfo, 8>396getRVVCalleeSavedInfo(const MachineFunction &MF,397const std::vector<CalleeSavedInfo> &CSI) {398const MachineFrameInfo &MFI = MF.getFrameInfo();399SmallVector<CalleeSavedInfo, 8> RVVCSI;400401for (auto &CS : CSI) {402int FI = CS.getFrameIdx();403if (FI >= 0 && MFI.getStackID(FI) == TargetStackID::ScalableVector)404RVVCSI.push_back(CS);405}406407return RVVCSI;408}409410void RISCVFrameLowering::adjustStackForRVV(MachineFunction &MF,411MachineBasicBlock &MBB,412MachineBasicBlock::iterator MBBI,413const DebugLoc &DL, int64_t Amount,414MachineInstr::MIFlag Flag) const {415assert(Amount != 0 && "Did not need to adjust stack pointer for RVV.");416417const Register SPReg = getSPReg(STI);418419// Optimize compile time offset case420StackOffset Offset = StackOffset::getScalable(Amount);421if (auto VLEN = STI.getRealVLen()) {422// 1. Multiply the number of v-slots by the (constant) length of register423const int64_t VLENB = *VLEN / 8;424assert(Amount % 8 == 0 &&425"Reserve the stack by the multiple of one vector size.");426const int64_t NumOfVReg = Amount / 8;427const int64_t FixedOffset = NumOfVReg * VLENB;428if (!isInt<32>(FixedOffset)) {429report_fatal_error(430"Frame size outside of the signed 32-bit range not supported");431}432Offset = StackOffset::getFixed(FixedOffset);433}434435const RISCVRegisterInfo &RI = *STI.getRegisterInfo();436// We must keep the stack pointer aligned through any intermediate437// updates.438RI.adjustReg(MBB, MBBI, DL, SPReg, SPReg, Offset,439Flag, getStackAlign());440}441442static void appendScalableVectorExpression(const TargetRegisterInfo &TRI,443SmallVectorImpl<char> &Expr,444int FixedOffset, int ScalableOffset,445llvm::raw_string_ostream &Comment) {446unsigned DwarfVLenB = TRI.getDwarfRegNum(RISCV::VLENB, true);447uint8_t Buffer[16];448if (FixedOffset) {449Expr.push_back(dwarf::DW_OP_consts);450Expr.append(Buffer, Buffer + encodeSLEB128(FixedOffset, Buffer));451Expr.push_back((uint8_t)dwarf::DW_OP_plus);452Comment << (FixedOffset < 0 ? " - " : " + ") << std::abs(FixedOffset);453}454455Expr.push_back((uint8_t)dwarf::DW_OP_consts);456Expr.append(Buffer, Buffer + encodeSLEB128(ScalableOffset, Buffer));457458Expr.push_back((uint8_t)dwarf::DW_OP_bregx);459Expr.append(Buffer, Buffer + encodeULEB128(DwarfVLenB, Buffer));460Expr.push_back(0);461462Expr.push_back((uint8_t)dwarf::DW_OP_mul);463Expr.push_back((uint8_t)dwarf::DW_OP_plus);464465Comment << (ScalableOffset < 0 ? " - " : " + ") << std::abs(ScalableOffset)466<< " * vlenb";467}468469static MCCFIInstruction createDefCFAExpression(const TargetRegisterInfo &TRI,470Register Reg,471uint64_t FixedOffset,472uint64_t ScalableOffset) {473assert(ScalableOffset != 0 && "Did not need to adjust CFA for RVV");474SmallString<64> Expr;475std::string CommentBuffer;476llvm::raw_string_ostream Comment(CommentBuffer);477// Build up the expression (Reg + FixedOffset + ScalableOffset * VLENB).478unsigned DwarfReg = TRI.getDwarfRegNum(Reg, true);479Expr.push_back((uint8_t)(dwarf::DW_OP_breg0 + DwarfReg));480Expr.push_back(0);481if (Reg == RISCV::X2)482Comment << "sp";483else484Comment << printReg(Reg, &TRI);485486appendScalableVectorExpression(TRI, Expr, FixedOffset, ScalableOffset,487Comment);488489SmallString<64> DefCfaExpr;490uint8_t Buffer[16];491DefCfaExpr.push_back(dwarf::DW_CFA_def_cfa_expression);492DefCfaExpr.append(Buffer, Buffer + encodeULEB128(Expr.size(), Buffer));493DefCfaExpr.append(Expr.str());494495return MCCFIInstruction::createEscape(nullptr, DefCfaExpr.str(), SMLoc(),496Comment.str());497}498499static MCCFIInstruction createDefCFAOffset(const TargetRegisterInfo &TRI,500Register Reg, uint64_t FixedOffset,501uint64_t ScalableOffset) {502assert(ScalableOffset != 0 && "Did not need to adjust CFA for RVV");503SmallString<64> Expr;504std::string CommentBuffer;505llvm::raw_string_ostream Comment(CommentBuffer);506Comment << printReg(Reg, &TRI) << " @ cfa";507508// Build up the expression (FixedOffset + ScalableOffset * VLENB).509appendScalableVectorExpression(TRI, Expr, FixedOffset, ScalableOffset,510Comment);511512SmallString<64> DefCfaExpr;513uint8_t Buffer[16];514unsigned DwarfReg = TRI.getDwarfRegNum(Reg, true);515DefCfaExpr.push_back(dwarf::DW_CFA_expression);516DefCfaExpr.append(Buffer, Buffer + encodeULEB128(DwarfReg, Buffer));517DefCfaExpr.append(Buffer, Buffer + encodeULEB128(Expr.size(), Buffer));518DefCfaExpr.append(Expr.str());519520return MCCFIInstruction::createEscape(nullptr, DefCfaExpr.str(), SMLoc(),521Comment.str());522}523524void RISCVFrameLowering::emitPrologue(MachineFunction &MF,525MachineBasicBlock &MBB) const {526MachineFrameInfo &MFI = MF.getFrameInfo();527auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();528const RISCVRegisterInfo *RI = STI.getRegisterInfo();529const RISCVInstrInfo *TII = STI.getInstrInfo();530MachineBasicBlock::iterator MBBI = MBB.begin();531532Register FPReg = getFPReg(STI);533Register SPReg = getSPReg(STI);534Register BPReg = RISCVABI::getBPReg();535536// Debug location must be unknown since the first debug location is used537// to determine the end of the prologue.538DebugLoc DL;539540// All calls are tail calls in GHC calling conv, and functions have no541// prologue/epilogue.542if (MF.getFunction().getCallingConv() == CallingConv::GHC)543return;544545// Emit prologue for shadow call stack.546emitSCSPrologue(MF, MBB, MBBI, DL);547548auto FirstFrameSetup = MBBI;549550// Since spillCalleeSavedRegisters may have inserted a libcall, skip past551// any instructions marked as FrameSetup552while (MBBI != MBB.end() && MBBI->getFlag(MachineInstr::FrameSetup))553++MBBI;554555// Determine the correct frame layout556determineFrameLayout(MF);557558// If libcalls are used to spill and restore callee-saved registers, the frame559// has two sections; the opaque section managed by the libcalls, and the560// section managed by MachineFrameInfo which can also hold callee saved561// registers in fixed stack slots, both of which have negative frame indices.562// This gets even more complicated when incoming arguments are passed via the563// stack, as these too have negative frame indices. An example is detailed564// below:565//566// | incoming arg | <- FI[-3]567// | libcallspill |568// | calleespill | <- FI[-2]569// | calleespill | <- FI[-1]570// | this_frame | <- FI[0]571//572// For negative frame indices, the offset from the frame pointer will differ573// depending on which of these groups the frame index applies to.574// The following calculates the correct offset knowing the number of callee575// saved registers spilt by the two methods.576if (int LibCallRegs = getLibCallID(MF, MFI.getCalleeSavedInfo()) + 1) {577// Calculate the size of the frame managed by the libcall. The stack578// alignment of these libcalls should be the same as how we set it in579// getABIStackAlignment.580unsigned LibCallFrameSize =581alignTo((STI.getXLen() / 8) * LibCallRegs, getStackAlign());582RVFI->setLibCallStackSize(LibCallFrameSize);583}584585// FIXME (note copied from Lanai): This appears to be overallocating. Needs586// investigation. Get the number of bytes to allocate from the FrameInfo.587uint64_t RealStackSize = getStackSizeWithRVVPadding(MF);588uint64_t StackSize = RealStackSize - RVFI->getReservedSpillsSize();589uint64_t RVVStackSize = RVFI->getRVVStackSize();590591// Early exit if there is no need to allocate on the stack592if (RealStackSize == 0 && !MFI.adjustsStack() && RVVStackSize == 0)593return;594595// If the stack pointer has been marked as reserved, then produce an error if596// the frame requires stack allocation597if (STI.isRegisterReservedByUser(SPReg))598MF.getFunction().getContext().diagnose(DiagnosticInfoUnsupported{599MF.getFunction(), "Stack pointer required, but has been reserved."});600601uint64_t FirstSPAdjustAmount = getFirstSPAdjustAmount(MF);602// Split the SP adjustment to reduce the offsets of callee saved spill.603if (FirstSPAdjustAmount) {604StackSize = FirstSPAdjustAmount;605RealStackSize = FirstSPAdjustAmount;606}607608if (RVFI->isPushable(MF) && FirstFrameSetup != MBB.end() &&609FirstFrameSetup->getOpcode() == RISCV::CM_PUSH) {610// Use available stack adjustment in push instruction to allocate additional611// stack space. Align the stack size down to a multiple of 16. This is612// needed for RVE.613// FIXME: Can we increase the stack size to a multiple of 16 instead?614uint64_t Spimm = std::min(alignDown(StackSize, 16), (uint64_t)48);615FirstFrameSetup->getOperand(1).setImm(Spimm);616StackSize -= Spimm;617}618619if (StackSize != 0) {620// Allocate space on the stack if necessary.621RI->adjustReg(MBB, MBBI, DL, SPReg, SPReg,622StackOffset::getFixed(-StackSize), MachineInstr::FrameSetup,623getStackAlign());624}625626// Emit ".cfi_def_cfa_offset RealStackSize"627unsigned CFIIndex = MF.addFrameInst(628MCCFIInstruction::cfiDefCfaOffset(nullptr, RealStackSize));629BuildMI(MBB, MBBI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))630.addCFIIndex(CFIIndex)631.setMIFlag(MachineInstr::FrameSetup);632633const auto &CSI = MFI.getCalleeSavedInfo();634635// The frame pointer is callee-saved, and code has been generated for us to636// save it to the stack. We need to skip over the storing of callee-saved637// registers as the frame pointer must be modified after it has been saved638// to the stack, not before.639// FIXME: assumes exactly one instruction is used to save each callee-saved640// register.641std::advance(MBBI, getUnmanagedCSI(MF, CSI).size());642643// Iterate over list of callee-saved registers and emit .cfi_offset644// directives.645for (const auto &Entry : CSI) {646int FrameIdx = Entry.getFrameIdx();647if (FrameIdx >= 0 &&648MFI.getStackID(FrameIdx) == TargetStackID::ScalableVector)649continue;650651int64_t Offset = MFI.getObjectOffset(FrameIdx);652Register Reg = Entry.getReg();653unsigned CFIIndex = MF.addFrameInst(MCCFIInstruction::createOffset(654nullptr, RI->getDwarfRegNum(Reg, true), Offset));655BuildMI(MBB, MBBI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))656.addCFIIndex(CFIIndex)657.setMIFlag(MachineInstr::FrameSetup);658}659660// Generate new FP.661if (hasFP(MF)) {662if (STI.isRegisterReservedByUser(FPReg))663MF.getFunction().getContext().diagnose(DiagnosticInfoUnsupported{664MF.getFunction(), "Frame pointer required, but has been reserved."});665// The frame pointer does need to be reserved from register allocation.666assert(MF.getRegInfo().isReserved(FPReg) && "FP not reserved");667668RI->adjustReg(MBB, MBBI, DL, FPReg, SPReg,669StackOffset::getFixed(RealStackSize - RVFI->getVarArgsSaveSize()),670MachineInstr::FrameSetup, getStackAlign());671672// Emit ".cfi_def_cfa $fp, RVFI->getVarArgsSaveSize()"673unsigned CFIIndex = MF.addFrameInst(MCCFIInstruction::cfiDefCfa(674nullptr, RI->getDwarfRegNum(FPReg, true), RVFI->getVarArgsSaveSize()));675BuildMI(MBB, MBBI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))676.addCFIIndex(CFIIndex)677.setMIFlag(MachineInstr::FrameSetup);678}679680// Emit the second SP adjustment after saving callee saved registers.681if (FirstSPAdjustAmount) {682uint64_t SecondSPAdjustAmount =683getStackSizeWithRVVPadding(MF) - FirstSPAdjustAmount;684assert(SecondSPAdjustAmount > 0 &&685"SecondSPAdjustAmount should be greater than zero");686RI->adjustReg(MBB, MBBI, DL, SPReg, SPReg,687StackOffset::getFixed(-SecondSPAdjustAmount),688MachineInstr::FrameSetup, getStackAlign());689690// If we are using a frame-pointer, and thus emitted ".cfi_def_cfa fp, 0",691// don't emit an sp-based .cfi_def_cfa_offset692if (!hasFP(MF)) {693// Emit ".cfi_def_cfa_offset StackSize"694unsigned CFIIndex = MF.addFrameInst(MCCFIInstruction::cfiDefCfaOffset(695nullptr, getStackSizeWithRVVPadding(MF)));696BuildMI(MBB, MBBI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))697.addCFIIndex(CFIIndex)698.setMIFlag(MachineInstr::FrameSetup);699}700}701702if (RVVStackSize) {703adjustStackForRVV(MF, MBB, MBBI, DL, -RVVStackSize,704MachineInstr::FrameSetup);705if (!hasFP(MF)) {706// Emit .cfi_def_cfa_expression "sp + StackSize + RVVStackSize * vlenb".707unsigned CFIIndex = MF.addFrameInst(createDefCFAExpression(708*RI, SPReg, getStackSizeWithRVVPadding(MF), RVVStackSize / 8));709BuildMI(MBB, MBBI, DL, TII->get(TargetOpcode::CFI_INSTRUCTION))710.addCFIIndex(CFIIndex)711.setMIFlag(MachineInstr::FrameSetup);712}713714std::advance(MBBI, getRVVCalleeSavedInfo(MF, CSI).size());715emitCalleeSavedRVVPrologCFI(MBB, MBBI, hasFP(MF));716}717718if (hasFP(MF)) {719// Realign Stack720const RISCVRegisterInfo *RI = STI.getRegisterInfo();721if (RI->hasStackRealignment(MF)) {722Align MaxAlignment = MFI.getMaxAlign();723724const RISCVInstrInfo *TII = STI.getInstrInfo();725if (isInt<12>(-(int)MaxAlignment.value())) {726BuildMI(MBB, MBBI, DL, TII->get(RISCV::ANDI), SPReg)727.addReg(SPReg)728.addImm(-(int)MaxAlignment.value())729.setMIFlag(MachineInstr::FrameSetup);730} else {731unsigned ShiftAmount = Log2(MaxAlignment);732Register VR =733MF.getRegInfo().createVirtualRegister(&RISCV::GPRRegClass);734BuildMI(MBB, MBBI, DL, TII->get(RISCV::SRLI), VR)735.addReg(SPReg)736.addImm(ShiftAmount)737.setMIFlag(MachineInstr::FrameSetup);738BuildMI(MBB, MBBI, DL, TII->get(RISCV::SLLI), SPReg)739.addReg(VR)740.addImm(ShiftAmount)741.setMIFlag(MachineInstr::FrameSetup);742}743// FP will be used to restore the frame in the epilogue, so we need744// another base register BP to record SP after re-alignment. SP will745// track the current stack after allocating variable sized objects.746if (hasBP(MF)) {747// move BP, SP748BuildMI(MBB, MBBI, DL, TII->get(RISCV::ADDI), BPReg)749.addReg(SPReg)750.addImm(0)751.setMIFlag(MachineInstr::FrameSetup);752}753}754}755}756757void RISCVFrameLowering::emitEpilogue(MachineFunction &MF,758MachineBasicBlock &MBB) const {759const RISCVRegisterInfo *RI = STI.getRegisterInfo();760MachineFrameInfo &MFI = MF.getFrameInfo();761auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();762Register FPReg = getFPReg(STI);763Register SPReg = getSPReg(STI);764765// All calls are tail calls in GHC calling conv, and functions have no766// prologue/epilogue.767if (MF.getFunction().getCallingConv() == CallingConv::GHC)768return;769770// Get the insert location for the epilogue. If there were no terminators in771// the block, get the last instruction.772MachineBasicBlock::iterator MBBI = MBB.end();773DebugLoc DL;774if (!MBB.empty()) {775MBBI = MBB.getLastNonDebugInstr();776if (MBBI != MBB.end())777DL = MBBI->getDebugLoc();778779MBBI = MBB.getFirstTerminator();780781// If callee-saved registers are saved via libcall, place stack adjustment782// before this call.783while (MBBI != MBB.begin() &&784std::prev(MBBI)->getFlag(MachineInstr::FrameDestroy))785--MBBI;786}787788const auto &CSI = getUnmanagedCSI(MF, MFI.getCalleeSavedInfo());789790// Skip to before the restores of scalar callee-saved registers791// FIXME: assumes exactly one instruction is used to restore each792// callee-saved register.793auto LastFrameDestroy = MBBI;794if (!CSI.empty())795LastFrameDestroy = std::prev(MBBI, CSI.size());796797uint64_t RealStackSize = getStackSizeWithRVVPadding(MF);798uint64_t StackSize = RealStackSize - RVFI->getReservedSpillsSize();799uint64_t FPOffset = RealStackSize - RVFI->getVarArgsSaveSize();800uint64_t RVVStackSize = RVFI->getRVVStackSize();801802// Restore the stack pointer using the value of the frame pointer. Only803// necessary if the stack pointer was modified, meaning the stack size is804// unknown.805//806// In order to make sure the stack point is right through the EH region,807// we also need to restore stack pointer from the frame pointer if we808// don't preserve stack space within prologue/epilogue for outgoing variables,809// normally it's just checking the variable sized object is present or not810// is enough, but we also don't preserve that at prologue/epilogue when811// have vector objects in stack.812if (RI->hasStackRealignment(MF) || MFI.hasVarSizedObjects() ||813!hasReservedCallFrame(MF)) {814assert(hasFP(MF) && "frame pointer should not have been eliminated");815RI->adjustReg(MBB, LastFrameDestroy, DL, SPReg, FPReg,816StackOffset::getFixed(-FPOffset),817MachineInstr::FrameDestroy, getStackAlign());818} else {819if (RVVStackSize)820adjustStackForRVV(MF, MBB, LastFrameDestroy, DL, RVVStackSize,821MachineInstr::FrameDestroy);822}823824uint64_t FirstSPAdjustAmount = getFirstSPAdjustAmount(MF);825if (FirstSPAdjustAmount) {826uint64_t SecondSPAdjustAmount =827getStackSizeWithRVVPadding(MF) - FirstSPAdjustAmount;828assert(SecondSPAdjustAmount > 0 &&829"SecondSPAdjustAmount should be greater than zero");830831RI->adjustReg(MBB, LastFrameDestroy, DL, SPReg, SPReg,832StackOffset::getFixed(SecondSPAdjustAmount),833MachineInstr::FrameDestroy, getStackAlign());834}835836if (FirstSPAdjustAmount)837StackSize = FirstSPAdjustAmount;838839if (RVFI->isPushable(MF) && MBBI != MBB.end() &&840MBBI->getOpcode() == RISCV::CM_POP) {841// Use available stack adjustment in pop instruction to deallocate stack842// space. Align the stack size down to a multiple of 16. This is needed for843// RVE.844// FIXME: Can we increase the stack size to a multiple of 16 instead?845uint64_t Spimm = std::min(alignDown(StackSize, 16), (uint64_t)48);846MBBI->getOperand(1).setImm(Spimm);847StackSize -= Spimm;848}849850// Deallocate stack851if (StackSize != 0) {852RI->adjustReg(MBB, MBBI, DL, SPReg, SPReg, StackOffset::getFixed(StackSize),853MachineInstr::FrameDestroy, getStackAlign());854}855856// Emit epilogue for shadow call stack.857emitSCSEpilogue(MF, MBB, MBBI, DL);858}859860StackOffset861RISCVFrameLowering::getFrameIndexReference(const MachineFunction &MF, int FI,862Register &FrameReg) const {863const MachineFrameInfo &MFI = MF.getFrameInfo();864const TargetRegisterInfo *RI = MF.getSubtarget().getRegisterInfo();865const auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();866867// Callee-saved registers should be referenced relative to the stack868// pointer (positive offset), otherwise use the frame pointer (negative869// offset).870const auto &CSI = getUnmanagedCSI(MF, MFI.getCalleeSavedInfo());871int MinCSFI = 0;872int MaxCSFI = -1;873StackOffset Offset;874auto StackID = MFI.getStackID(FI);875876assert((StackID == TargetStackID::Default ||877StackID == TargetStackID::ScalableVector) &&878"Unexpected stack ID for the frame object.");879if (StackID == TargetStackID::Default) {880assert(getOffsetOfLocalArea() == 0 && "LocalAreaOffset is not 0!");881Offset = StackOffset::getFixed(MFI.getObjectOffset(FI) +882MFI.getOffsetAdjustment());883} else if (StackID == TargetStackID::ScalableVector) {884Offset = StackOffset::getScalable(MFI.getObjectOffset(FI));885}886887uint64_t FirstSPAdjustAmount = getFirstSPAdjustAmount(MF);888889if (CSI.size()) {890MinCSFI = CSI[0].getFrameIdx();891MaxCSFI = CSI[CSI.size() - 1].getFrameIdx();892}893894if (FI >= MinCSFI && FI <= MaxCSFI) {895FrameReg = RISCV::X2;896897if (FirstSPAdjustAmount)898Offset += StackOffset::getFixed(FirstSPAdjustAmount);899else900Offset += StackOffset::getFixed(getStackSizeWithRVVPadding(MF));901return Offset;902}903904if (RI->hasStackRealignment(MF) && !MFI.isFixedObjectIndex(FI)) {905// If the stack was realigned, the frame pointer is set in order to allow906// SP to be restored, so we need another base register to record the stack907// after realignment.908// |--------------------------| -- <-- FP909// | callee-allocated save | | <----|910// | area for register varargs| | |911// |--------------------------| | |912// | callee-saved registers | | |913// |--------------------------| -- |914// | realignment (the size of | | |915// | this area is not counted | | |916// | in MFI.getStackSize()) | | |917// |--------------------------| -- |-- MFI.getStackSize()918// | RVV alignment padding | | |919// | (not counted in | | |920// | MFI.getStackSize() but | | |921// | counted in | | |922// | RVFI.getRVVStackSize()) | | |923// |--------------------------| -- |924// | RVV objects | | |925// | (not counted in | | |926// | MFI.getStackSize()) | | |927// |--------------------------| -- |928// | padding before RVV | | |929// | (not counted in | | |930// | MFI.getStackSize() or in | | |931// | RVFI.getRVVStackSize()) | | |932// |--------------------------| -- |933// | scalar local variables | | <----'934// |--------------------------| -- <-- BP (if var sized objects present)935// | VarSize objects | |936// |--------------------------| -- <-- SP937if (hasBP(MF)) {938FrameReg = RISCVABI::getBPReg();939} else {940// VarSize objects must be empty in this case!941assert(!MFI.hasVarSizedObjects());942FrameReg = RISCV::X2;943}944} else {945FrameReg = RI->getFrameRegister(MF);946}947948if (FrameReg == getFPReg(STI)) {949Offset += StackOffset::getFixed(RVFI->getVarArgsSaveSize());950// When using FP to access scalable vector objects, we need to minus951// the frame size.952//953// |--------------------------| -- <-- FP954// | callee-allocated save | |955// | area for register varargs| |956// |--------------------------| |957// | callee-saved registers | |958// |--------------------------| | MFI.getStackSize()959// | scalar local variables | |960// |--------------------------| -- (Offset of RVV objects is from here.)961// | RVV objects |962// |--------------------------|963// | VarSize objects |964// |--------------------------| <-- SP965if (MFI.getStackID(FI) == TargetStackID::ScalableVector) {966assert(!RI->hasStackRealignment(MF) &&967"Can't index across variable sized realign");968// We don't expect any extra RVV alignment padding, as the stack size969// and RVV object sections should be correct aligned in their own970// right.971assert(MFI.getStackSize() == getStackSizeWithRVVPadding(MF) &&972"Inconsistent stack layout");973Offset -= StackOffset::getFixed(MFI.getStackSize());974}975return Offset;976}977978// This case handles indexing off both SP and BP.979// If indexing off SP, there must not be any var sized objects980assert(FrameReg == RISCVABI::getBPReg() || !MFI.hasVarSizedObjects());981982// When using SP to access frame objects, we need to add RVV stack size.983//984// |--------------------------| -- <-- FP985// | callee-allocated save | | <----|986// | area for register varargs| | |987// |--------------------------| | |988// | callee-saved registers | | |989// |--------------------------| -- |990// | RVV alignment padding | | |991// | (not counted in | | |992// | MFI.getStackSize() but | | |993// | counted in | | |994// | RVFI.getRVVStackSize()) | | |995// |--------------------------| -- |996// | RVV objects | | |-- MFI.getStackSize()997// | (not counted in | | |998// | MFI.getStackSize()) | | |999// |--------------------------| -- |1000// | padding before RVV | | |1001// | (not counted in | | |1002// | MFI.getStackSize()) | | |1003// |--------------------------| -- |1004// | scalar local variables | | <----'1005// |--------------------------| -- <-- BP (if var sized objects present)1006// | VarSize objects | |1007// |--------------------------| -- <-- SP1008//1009// The total amount of padding surrounding RVV objects is described by1010// RVV->getRVVPadding() and it can be zero. It allows us to align the RVV1011// objects to the required alignment.1012if (MFI.getStackID(FI) == TargetStackID::Default) {1013if (MFI.isFixedObjectIndex(FI)) {1014assert(!RI->hasStackRealignment(MF) &&1015"Can't index across variable sized realign");1016Offset += StackOffset::get(getStackSizeWithRVVPadding(MF),1017RVFI->getRVVStackSize());1018} else {1019Offset += StackOffset::getFixed(MFI.getStackSize());1020}1021} else if (MFI.getStackID(FI) == TargetStackID::ScalableVector) {1022// Ensure the base of the RVV stack is correctly aligned: add on the1023// alignment padding.1024int ScalarLocalVarSize = MFI.getStackSize() -1025RVFI->getCalleeSavedStackSize() -1026RVFI->getRVPushStackSize() -1027RVFI->getVarArgsSaveSize() + RVFI->getRVVPadding();1028Offset += StackOffset::get(ScalarLocalVarSize, RVFI->getRVVStackSize());1029}1030return Offset;1031}10321033void RISCVFrameLowering::determineCalleeSaves(MachineFunction &MF,1034BitVector &SavedRegs,1035RegScavenger *RS) const {1036TargetFrameLowering::determineCalleeSaves(MF, SavedRegs, RS);1037// Unconditionally spill RA and FP only if the function uses a frame1038// pointer.1039if (hasFP(MF)) {1040SavedRegs.set(RISCV::X1);1041SavedRegs.set(RISCV::X8);1042}1043// Mark BP as used if function has dedicated base pointer.1044if (hasBP(MF))1045SavedRegs.set(RISCVABI::getBPReg());10461047// When using cm.push/pop we must save X27 if we save X26.1048auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();1049if (RVFI->isPushable(MF) && SavedRegs.test(RISCV::X26))1050SavedRegs.set(RISCV::X27);1051}10521053std::pair<int64_t, Align>1054RISCVFrameLowering::assignRVVStackObjectOffsets(MachineFunction &MF) const {1055MachineFrameInfo &MFI = MF.getFrameInfo();1056// Create a buffer of RVV objects to allocate.1057SmallVector<int, 8> ObjectsToAllocate;1058auto pushRVVObjects = [&](int FIBegin, int FIEnd) {1059for (int I = FIBegin, E = FIEnd; I != E; ++I) {1060unsigned StackID = MFI.getStackID(I);1061if (StackID != TargetStackID::ScalableVector)1062continue;1063if (MFI.isDeadObjectIndex(I))1064continue;10651066ObjectsToAllocate.push_back(I);1067}1068};1069// First push RVV Callee Saved object, then push RVV stack object1070std::vector<CalleeSavedInfo> &CSI = MF.getFrameInfo().getCalleeSavedInfo();1071const auto &RVVCSI = getRVVCalleeSavedInfo(MF, CSI);1072if (!RVVCSI.empty())1073pushRVVObjects(RVVCSI[0].getFrameIdx(),1074RVVCSI[RVVCSI.size() - 1].getFrameIdx() + 1);1075pushRVVObjects(0, MFI.getObjectIndexEnd() - RVVCSI.size());10761077// The minimum alignment is 16 bytes.1078Align RVVStackAlign(16);1079const auto &ST = MF.getSubtarget<RISCVSubtarget>();10801081if (!ST.hasVInstructions()) {1082assert(ObjectsToAllocate.empty() &&1083"Can't allocate scalable-vector objects without V instructions");1084return std::make_pair(0, RVVStackAlign);1085}10861087// Allocate all RVV locals and spills1088int64_t Offset = 0;1089for (int FI : ObjectsToAllocate) {1090// ObjectSize in bytes.1091int64_t ObjectSize = MFI.getObjectSize(FI);1092auto ObjectAlign = std::max(Align(8), MFI.getObjectAlign(FI));1093// If the data type is the fractional vector type, reserve one vector1094// register for it.1095if (ObjectSize < 8)1096ObjectSize = 8;1097Offset = alignTo(Offset + ObjectSize, ObjectAlign);1098MFI.setObjectOffset(FI, -Offset);1099// Update the maximum alignment of the RVV stack section1100RVVStackAlign = std::max(RVVStackAlign, ObjectAlign);1101}11021103// Ensure the alignment of the RVV stack. Since we want the most-aligned1104// object right at the bottom (i.e., any padding at the top of the frame),1105// readjust all RVV objects down by the alignment padding.1106uint64_t StackSize = Offset;1107if (auto AlignmentPadding = offsetToAlignment(StackSize, RVVStackAlign)) {1108StackSize += AlignmentPadding;1109for (int FI : ObjectsToAllocate)1110MFI.setObjectOffset(FI, MFI.getObjectOffset(FI) - AlignmentPadding);1111}11121113return std::make_pair(StackSize, RVVStackAlign);1114}11151116static unsigned getScavSlotsNumForRVV(MachineFunction &MF) {1117// For RVV spill, scalable stack offsets computing requires up to two scratch1118// registers1119static constexpr unsigned ScavSlotsNumRVVSpillScalableObject = 2;11201121// For RVV spill, non-scalable stack offsets computing requires up to one1122// scratch register.1123static constexpr unsigned ScavSlotsNumRVVSpillNonScalableObject = 1;11241125// ADDI instruction's destination register can be used for computing1126// offsets. So Scalable stack offsets require up to one scratch register.1127static constexpr unsigned ScavSlotsADDIScalableObject = 1;11281129static constexpr unsigned MaxScavSlotsNumKnown =1130std::max({ScavSlotsADDIScalableObject, ScavSlotsNumRVVSpillScalableObject,1131ScavSlotsNumRVVSpillNonScalableObject});11321133unsigned MaxScavSlotsNum = 0;1134if (!MF.getSubtarget<RISCVSubtarget>().hasVInstructions())1135return false;1136for (const MachineBasicBlock &MBB : MF)1137for (const MachineInstr &MI : MBB) {1138bool IsRVVSpill = RISCV::isRVVSpill(MI);1139for (auto &MO : MI.operands()) {1140if (!MO.isFI())1141continue;1142bool IsScalableVectorID = MF.getFrameInfo().getStackID(MO.getIndex()) ==1143TargetStackID::ScalableVector;1144if (IsRVVSpill) {1145MaxScavSlotsNum = std::max(1146MaxScavSlotsNum, IsScalableVectorID1147? ScavSlotsNumRVVSpillScalableObject1148: ScavSlotsNumRVVSpillNonScalableObject);1149} else if (MI.getOpcode() == RISCV::ADDI && IsScalableVectorID) {1150MaxScavSlotsNum =1151std::max(MaxScavSlotsNum, ScavSlotsADDIScalableObject);1152}1153}1154if (MaxScavSlotsNum == MaxScavSlotsNumKnown)1155return MaxScavSlotsNumKnown;1156}1157return MaxScavSlotsNum;1158}11591160static bool hasRVVFrameObject(const MachineFunction &MF) {1161// Originally, the function will scan all the stack objects to check whether1162// if there is any scalable vector object on the stack or not. However, it1163// causes errors in the register allocator. In issue 53016, it returns false1164// before RA because there is no RVV stack objects. After RA, it returns true1165// because there are spilling slots for RVV values during RA. It will not1166// reserve BP during register allocation and generate BP access in the PEI1167// pass due to the inconsistent behavior of the function.1168//1169// The function is changed to use hasVInstructions() as the return value. It1170// is not precise, but it can make the register allocation correct.1171//1172// FIXME: Find a better way to make the decision or revisit the solution in1173// D103622.1174//1175// Refer to https://github.com/llvm/llvm-project/issues/53016.1176return MF.getSubtarget<RISCVSubtarget>().hasVInstructions();1177}11781179static unsigned estimateFunctionSizeInBytes(const MachineFunction &MF,1180const RISCVInstrInfo &TII) {1181unsigned FnSize = 0;1182for (auto &MBB : MF) {1183for (auto &MI : MBB) {1184// Far branches over 20-bit offset will be relaxed in branch relaxation1185// pass. In the worst case, conditional branches will be relaxed into1186// the following instruction sequence. Unconditional branches are1187// relaxed in the same way, with the exception that there is no first1188// branch instruction.1189//1190// foo1191// bne t5, t6, .rev_cond # `TII->getInstSizeInBytes(MI)` bytes1192// sd s11, 0(sp) # 4 bytes, or 2 bytes in RVC1193// jump .restore, s11 # 8 bytes1194// .rev_cond1195// bar1196// j .dest_bb # 4 bytes, or 2 bytes in RVC1197// .restore:1198// ld s11, 0(sp) # 4 bytes, or 2 bytes in RVC1199// .dest:1200// baz1201if (MI.isConditionalBranch())1202FnSize += TII.getInstSizeInBytes(MI);1203if (MI.isConditionalBranch() || MI.isUnconditionalBranch()) {1204if (MF.getSubtarget<RISCVSubtarget>().hasStdExtCOrZca())1205FnSize += 2 + 8 + 2 + 2;1206else1207FnSize += 4 + 8 + 4 + 4;1208continue;1209}12101211FnSize += TII.getInstSizeInBytes(MI);1212}1213}1214return FnSize;1215}12161217void RISCVFrameLowering::processFunctionBeforeFrameFinalized(1218MachineFunction &MF, RegScavenger *RS) const {1219const RISCVRegisterInfo *RegInfo =1220MF.getSubtarget<RISCVSubtarget>().getRegisterInfo();1221const RISCVInstrInfo *TII = MF.getSubtarget<RISCVSubtarget>().getInstrInfo();1222MachineFrameInfo &MFI = MF.getFrameInfo();1223const TargetRegisterClass *RC = &RISCV::GPRRegClass;1224auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();12251226int64_t RVVStackSize;1227Align RVVStackAlign;1228std::tie(RVVStackSize, RVVStackAlign) = assignRVVStackObjectOffsets(MF);12291230RVFI->setRVVStackSize(RVVStackSize);1231RVFI->setRVVStackAlign(RVVStackAlign);12321233if (hasRVVFrameObject(MF)) {1234// Ensure the entire stack is aligned to at least the RVV requirement: some1235// scalable-vector object alignments are not considered by the1236// target-independent code.1237MFI.ensureMaxAlignment(RVVStackAlign);1238}12391240unsigned ScavSlotsNum = 0;12411242// estimateStackSize has been observed to under-estimate the final stack1243// size, so give ourselves wiggle-room by checking for stack size1244// representable an 11-bit signed field rather than 12-bits.1245if (!isInt<11>(MFI.estimateStackSize(MF)))1246ScavSlotsNum = 1;12471248// Far branches over 20-bit offset require a spill slot for scratch register.1249bool IsLargeFunction = !isInt<20>(estimateFunctionSizeInBytes(MF, *TII));1250if (IsLargeFunction)1251ScavSlotsNum = std::max(ScavSlotsNum, 1u);12521253// RVV loads & stores have no capacity to hold the immediate address offsets1254// so we must always reserve an emergency spill slot if the MachineFunction1255// contains any RVV spills.1256ScavSlotsNum = std::max(ScavSlotsNum, getScavSlotsNumForRVV(MF));12571258for (unsigned I = 0; I < ScavSlotsNum; I++) {1259int FI = MFI.CreateStackObject(RegInfo->getSpillSize(*RC),1260RegInfo->getSpillAlign(*RC), false);1261RS->addScavengingFrameIndex(FI);12621263if (IsLargeFunction && RVFI->getBranchRelaxationScratchFrameIndex() == -1)1264RVFI->setBranchRelaxationScratchFrameIndex(FI);1265}12661267unsigned Size = RVFI->getReservedSpillsSize();1268for (const auto &Info : MFI.getCalleeSavedInfo()) {1269int FrameIdx = Info.getFrameIdx();1270if (FrameIdx < 0 || MFI.getStackID(FrameIdx) != TargetStackID::Default)1271continue;12721273Size += MFI.getObjectSize(FrameIdx);1274}1275RVFI->setCalleeSavedStackSize(Size);1276}12771278// Not preserve stack space within prologue for outgoing variables when the1279// function contains variable size objects or there are vector objects accessed1280// by the frame pointer.1281// Let eliminateCallFramePseudoInstr preserve stack space for it.1282bool RISCVFrameLowering::hasReservedCallFrame(const MachineFunction &MF) const {1283return !MF.getFrameInfo().hasVarSizedObjects() &&1284!(hasFP(MF) && hasRVVFrameObject(MF));1285}12861287// Eliminate ADJCALLSTACKDOWN, ADJCALLSTACKUP pseudo instructions.1288MachineBasicBlock::iterator RISCVFrameLowering::eliminateCallFramePseudoInstr(1289MachineFunction &MF, MachineBasicBlock &MBB,1290MachineBasicBlock::iterator MI) const {1291Register SPReg = RISCV::X2;1292DebugLoc DL = MI->getDebugLoc();12931294if (!hasReservedCallFrame(MF)) {1295// If space has not been reserved for a call frame, ADJCALLSTACKDOWN and1296// ADJCALLSTACKUP must be converted to instructions manipulating the stack1297// pointer. This is necessary when there is a variable length stack1298// allocation (e.g. alloca), which means it's not possible to allocate1299// space for outgoing arguments from within the function prologue.1300int64_t Amount = MI->getOperand(0).getImm();13011302if (Amount != 0) {1303// Ensure the stack remains aligned after adjustment.1304Amount = alignSPAdjust(Amount);13051306if (MI->getOpcode() == RISCV::ADJCALLSTACKDOWN)1307Amount = -Amount;13081309const RISCVRegisterInfo &RI = *STI.getRegisterInfo();1310RI.adjustReg(MBB, MI, DL, SPReg, SPReg, StackOffset::getFixed(Amount),1311MachineInstr::NoFlags, getStackAlign());1312}1313}13141315return MBB.erase(MI);1316}13171318// We would like to split the SP adjustment to reduce prologue/epilogue1319// as following instructions. In this way, the offset of the callee saved1320// register could fit in a single store. Supposed that the first sp adjust1321// amount is 2032.1322// add sp,sp,-20321323// sw ra,2028(sp)1324// sw s0,2024(sp)1325// sw s1,2020(sp)1326// sw s3,2012(sp)1327// sw s4,2008(sp)1328// add sp,sp,-641329uint64_t1330RISCVFrameLowering::getFirstSPAdjustAmount(const MachineFunction &MF) const {1331const auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();1332const MachineFrameInfo &MFI = MF.getFrameInfo();1333const std::vector<CalleeSavedInfo> &CSI = MFI.getCalleeSavedInfo();1334uint64_t StackSize = getStackSizeWithRVVPadding(MF);13351336// Disable SplitSPAdjust if save-restore libcall is used. The callee-saved1337// registers will be pushed by the save-restore libcalls, so we don't have to1338// split the SP adjustment in this case.1339if (RVFI->getReservedSpillsSize())1340return 0;13411342// Return the FirstSPAdjustAmount if the StackSize can not fit in a signed1343// 12-bit and there exists a callee-saved register needing to be pushed.1344if (!isInt<12>(StackSize) && (CSI.size() > 0)) {1345// FirstSPAdjustAmount is chosen at most as (2048 - StackAlign) because1346// 2048 will cause sp = sp + 2048 in the epilogue to be split into multiple1347// instructions. Offsets smaller than 2048 can fit in a single load/store1348// instruction, and we have to stick with the stack alignment. 2048 has1349// 16-byte alignment. The stack alignment for RV32 and RV64 is 16 and for1350// RV32E it is 4. So (2048 - StackAlign) will satisfy the stack alignment.1351const uint64_t StackAlign = getStackAlign().value();13521353// Amount of (2048 - StackAlign) will prevent callee saved and restored1354// instructions be compressed, so try to adjust the amount to the largest1355// offset that stack compression instructions accept when target supports1356// compression instructions.1357if (STI.hasStdExtCOrZca()) {1358// The compression extensions may support the following instructions:1359// riscv32: c.lwsp rd, offset[7:2] => 2^(6 + 2)1360// c.swsp rs2, offset[7:2] => 2^(6 + 2)1361// c.flwsp rd, offset[7:2] => 2^(6 + 2)1362// c.fswsp rs2, offset[7:2] => 2^(6 + 2)1363// riscv64: c.ldsp rd, offset[8:3] => 2^(6 + 3)1364// c.sdsp rs2, offset[8:3] => 2^(6 + 3)1365// c.fldsp rd, offset[8:3] => 2^(6 + 3)1366// c.fsdsp rs2, offset[8:3] => 2^(6 + 3)1367const uint64_t RVCompressLen = STI.getXLen() * 8;1368// Compared with amount (2048 - StackAlign), StackSize needs to1369// satisfy the following conditions to avoid using more instructions1370// to adjust the sp after adjusting the amount, such as1371// StackSize meets the condition (StackSize <= 2048 + RVCompressLen),1372// case1: Amount is 2048 - StackAlign: use addi + addi to adjust sp.1373// case2: Amount is RVCompressLen: use addi + addi to adjust sp.1374auto CanCompress = [&](uint64_t CompressLen) -> bool {1375if (StackSize <= 2047 + CompressLen ||1376(StackSize > 2048 * 2 - StackAlign &&1377StackSize <= 2047 * 2 + CompressLen) ||1378StackSize > 2048 * 3 - StackAlign)1379return true;13801381return false;1382};1383// In the epilogue, addi sp, sp, 496 is used to recover the sp and it1384// can be compressed(C.ADDI16SP, offset can be [-512, 496]), but1385// addi sp, sp, 512 can not be compressed. So try to use 496 first.1386const uint64_t ADDI16SPCompressLen = 496;1387if (STI.is64Bit() && CanCompress(ADDI16SPCompressLen))1388return ADDI16SPCompressLen;1389if (CanCompress(RVCompressLen))1390return RVCompressLen;1391}1392return 2048 - StackAlign;1393}1394return 0;1395}13961397bool RISCVFrameLowering::assignCalleeSavedSpillSlots(1398MachineFunction &MF, const TargetRegisterInfo *TRI,1399std::vector<CalleeSavedInfo> &CSI, unsigned &MinCSFrameIndex,1400unsigned &MaxCSFrameIndex) const {1401// Early exit if no callee saved registers are modified!1402if (CSI.empty())1403return true;14041405auto *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();14061407if (RVFI->isPushable(MF)) {1408// Determine how many GPRs we need to push and save it to RVFI.1409Register MaxReg = getMaxPushPopReg(MF, CSI);1410if (MaxReg != RISCV::NoRegister) {1411auto [RegEnc, PushedRegNum] = getPushPopEncodingAndNum(MaxReg);1412RVFI->setRVPushRegs(PushedRegNum);1413RVFI->setRVPushStackSize(alignTo((STI.getXLen() / 8) * PushedRegNum, 16));14141415// Use encoded number to represent registers to spill.1416RVFI->setRVPushRlist(RegEnc);1417}1418}14191420MachineFrameInfo &MFI = MF.getFrameInfo();1421const TargetRegisterInfo *RegInfo = MF.getSubtarget().getRegisterInfo();14221423for (auto &CS : CSI) {1424unsigned Reg = CS.getReg();1425const TargetRegisterClass *RC = RegInfo->getMinimalPhysRegClass(Reg);1426unsigned Size = RegInfo->getSpillSize(*RC);14271428// This might need a fixed stack slot.1429if (RVFI->useSaveRestoreLibCalls(MF) || RVFI->isPushable(MF)) {1430const auto *FII = llvm::find_if(1431FixedCSRFIMap, [&](auto P) { return P.first == CS.getReg(); });1432if (FII != std::end(FixedCSRFIMap)) {1433int64_t Offset;1434if (RVFI->isPushable(MF))1435Offset = -((FII->second + RVFI->getRVPushRegs() + 1) * (int64_t)Size);1436else1437Offset = FII->second * (int64_t)Size;14381439int FrameIdx = MFI.CreateFixedSpillStackObject(Size, Offset);1440assert(FrameIdx < 0);1441CS.setFrameIdx(FrameIdx);1442continue;1443}1444}14451446// Not a fixed slot.1447Align Alignment = RegInfo->getSpillAlign(*RC);1448// We may not be able to satisfy the desired alignment specification of1449// the TargetRegisterClass if the stack alignment is smaller. Use the1450// min.1451Alignment = std::min(Alignment, getStackAlign());1452int FrameIdx = MFI.CreateStackObject(Size, Alignment, true);1453if ((unsigned)FrameIdx < MinCSFrameIndex)1454MinCSFrameIndex = FrameIdx;1455if ((unsigned)FrameIdx > MaxCSFrameIndex)1456MaxCSFrameIndex = FrameIdx;1457CS.setFrameIdx(FrameIdx);1458}14591460// Allocate a fixed object that covers the full push or libcall size.1461if (RVFI->isPushable(MF)) {1462if (int64_t PushSize = RVFI->getRVPushStackSize())1463MFI.CreateFixedSpillStackObject(PushSize, -PushSize);1464} else if (int LibCallRegs = getLibCallID(MF, CSI) + 1) {1465int64_t LibCallFrameSize =1466alignTo((STI.getXLen() / 8) * LibCallRegs, getStackAlign());1467MFI.CreateFixedSpillStackObject(LibCallFrameSize, -LibCallFrameSize);1468}14691470return true;1471}14721473bool RISCVFrameLowering::spillCalleeSavedRegisters(1474MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,1475ArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const {1476if (CSI.empty())1477return true;14781479MachineFunction *MF = MBB.getParent();1480const TargetInstrInfo &TII = *MF->getSubtarget().getInstrInfo();1481DebugLoc DL;1482if (MI != MBB.end() && !MI->isDebugInstr())1483DL = MI->getDebugLoc();14841485// Emit CM.PUSH with base SPimm & evaluate Push stack1486RISCVMachineFunctionInfo *RVFI = MF->getInfo<RISCVMachineFunctionInfo>();1487if (RVFI->isPushable(*MF)) {1488unsigned PushedRegNum = RVFI->getRVPushRegs();1489if (PushedRegNum > 0) {1490// Use encoded number to represent registers to spill.1491int RegEnc = RVFI->getRVPushRlist();1492MachineInstrBuilder PushBuilder =1493BuildMI(MBB, MI, DL, TII.get(RISCV::CM_PUSH))1494.setMIFlag(MachineInstr::FrameSetup);1495PushBuilder.addImm((int64_t)RegEnc);1496PushBuilder.addImm(0);14971498for (unsigned i = 0; i < PushedRegNum; i++)1499PushBuilder.addUse(FixedCSRFIMap[i].first, RegState::Implicit);1500}1501} else if (const char *SpillLibCall = getSpillLibCallName(*MF, CSI)) {1502// Add spill libcall via non-callee-saved register t0.1503BuildMI(MBB, MI, DL, TII.get(RISCV::PseudoCALLReg), RISCV::X5)1504.addExternalSymbol(SpillLibCall, RISCVII::MO_CALL)1505.setMIFlag(MachineInstr::FrameSetup);15061507// Add registers spilled in libcall as liveins.1508for (auto &CS : CSI)1509MBB.addLiveIn(CS.getReg());1510}15111512// Manually spill values not spilled by libcall & Push/Pop.1513const auto &UnmanagedCSI = getUnmanagedCSI(*MF, CSI);1514const auto &RVVCSI = getRVVCalleeSavedInfo(*MF, CSI);15151516auto storeRegToStackSlot = [&](decltype(UnmanagedCSI) CSInfo) {1517for (auto &CS : CSInfo) {1518// Insert the spill to the stack frame.1519Register Reg = CS.getReg();1520const TargetRegisterClass *RC = TRI->getMinimalPhysRegClass(Reg);1521TII.storeRegToStackSlot(MBB, MI, Reg, !MBB.isLiveIn(Reg),1522CS.getFrameIdx(), RC, TRI, Register());1523}1524};1525storeRegToStackSlot(UnmanagedCSI);1526storeRegToStackSlot(RVVCSI);15271528return true;1529}15301531void RISCVFrameLowering::emitCalleeSavedRVVPrologCFI(1532MachineBasicBlock &MBB, MachineBasicBlock::iterator MI, bool HasFP) const {1533MachineFunction *MF = MBB.getParent();1534const MachineFrameInfo &MFI = MF->getFrameInfo();1535RISCVMachineFunctionInfo *RVFI = MF->getInfo<RISCVMachineFunctionInfo>();1536const TargetInstrInfo &TII = *STI.getInstrInfo();1537DebugLoc DL = MBB.findDebugLoc(MI);15381539const auto &RVVCSI = getRVVCalleeSavedInfo(*MF, MFI.getCalleeSavedInfo());1540if (RVVCSI.empty())1541return;15421543uint64_t FixedSize = getStackSizeWithRVVPadding(*MF);1544if (!HasFP) {1545uint64_t ScalarLocalVarSize =1546MFI.getStackSize() - RVFI->getCalleeSavedStackSize() -1547RVFI->getRVPushStackSize() - RVFI->getVarArgsSaveSize() +1548RVFI->getRVVPadding();1549FixedSize -= ScalarLocalVarSize;1550}15511552for (auto &CS : RVVCSI) {1553// Insert the spill to the stack frame.1554int FI = CS.getFrameIdx();1555if (FI >= 0 && MFI.getStackID(FI) == TargetStackID::ScalableVector) {1556unsigned CFIIndex = MF->addFrameInst(1557createDefCFAOffset(*STI.getRegisterInfo(), CS.getReg(), -FixedSize,1558MFI.getObjectOffset(FI) / 8));1559BuildMI(MBB, MI, DL, TII.get(TargetOpcode::CFI_INSTRUCTION))1560.addCFIIndex(CFIIndex)1561.setMIFlag(MachineInstr::FrameSetup);1562}1563}1564}15651566bool RISCVFrameLowering::restoreCalleeSavedRegisters(1567MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,1568MutableArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const {1569if (CSI.empty())1570return true;15711572MachineFunction *MF = MBB.getParent();1573const TargetInstrInfo &TII = *MF->getSubtarget().getInstrInfo();1574DebugLoc DL;1575if (MI != MBB.end() && !MI->isDebugInstr())1576DL = MI->getDebugLoc();15771578// Manually restore values not restored by libcall & Push/Pop.1579// Reverse the restore order in epilog. In addition, the return1580// address will be restored first in the epilogue. It increases1581// the opportunity to avoid the load-to-use data hazard between1582// loading RA and return by RA. loadRegFromStackSlot can insert1583// multiple instructions.1584const auto &UnmanagedCSI = getUnmanagedCSI(*MF, CSI);1585const auto &RVVCSI = getRVVCalleeSavedInfo(*MF, CSI);15861587auto loadRegFromStackSlot = [&](decltype(UnmanagedCSI) CSInfo) {1588for (auto &CS : CSInfo) {1589Register Reg = CS.getReg();1590const TargetRegisterClass *RC = TRI->getMinimalPhysRegClass(Reg);1591TII.loadRegFromStackSlot(MBB, MI, Reg, CS.getFrameIdx(), RC, TRI,1592Register());1593assert(MI != MBB.begin() &&1594"loadRegFromStackSlot didn't insert any code!");1595}1596};1597loadRegFromStackSlot(RVVCSI);1598loadRegFromStackSlot(UnmanagedCSI);15991600RISCVMachineFunctionInfo *RVFI = MF->getInfo<RISCVMachineFunctionInfo>();1601if (RVFI->isPushable(*MF)) {1602int RegEnc = RVFI->getRVPushRlist();1603if (RegEnc != llvm::RISCVZC::RLISTENCODE::INVALID_RLIST) {1604MachineInstrBuilder PopBuilder =1605BuildMI(MBB, MI, DL, TII.get(RISCV::CM_POP))1606.setMIFlag(MachineInstr::FrameDestroy);1607// Use encoded number to represent registers to restore.1608PopBuilder.addImm(RegEnc);1609PopBuilder.addImm(0);16101611for (unsigned i = 0; i < RVFI->getRVPushRegs(); i++)1612PopBuilder.addDef(FixedCSRFIMap[i].first, RegState::ImplicitDefine);1613}1614} else {1615const char *RestoreLibCall = getRestoreLibCallName(*MF, CSI);1616if (RestoreLibCall) {1617// Add restore libcall via tail call.1618MachineBasicBlock::iterator NewMI =1619BuildMI(MBB, MI, DL, TII.get(RISCV::PseudoTAIL))1620.addExternalSymbol(RestoreLibCall, RISCVII::MO_CALL)1621.setMIFlag(MachineInstr::FrameDestroy);16221623// Remove trailing returns, since the terminator is now a tail call to the1624// restore function.1625if (MI != MBB.end() && MI->getOpcode() == RISCV::PseudoRET) {1626NewMI->copyImplicitOps(*MF, *MI);1627MI->eraseFromParent();1628}1629}1630}1631return true;1632}16331634bool RISCVFrameLowering::enableShrinkWrapping(const MachineFunction &MF) const {1635// Keep the conventional code flow when not optimizing.1636if (MF.getFunction().hasOptNone())1637return false;16381639return true;1640}16411642bool RISCVFrameLowering::canUseAsPrologue(const MachineBasicBlock &MBB) const {1643MachineBasicBlock *TmpMBB = const_cast<MachineBasicBlock *>(&MBB);1644const MachineFunction *MF = MBB.getParent();1645const auto *RVFI = MF->getInfo<RISCVMachineFunctionInfo>();16461647if (!RVFI->useSaveRestoreLibCalls(*MF))1648return true;16491650// Inserting a call to a __riscv_save libcall requires the use of the register1651// t0 (X5) to hold the return address. Therefore if this register is already1652// used we can't insert the call.16531654RegScavenger RS;1655RS.enterBasicBlock(*TmpMBB);1656return !RS.isRegUsed(RISCV::X5);1657}16581659bool RISCVFrameLowering::canUseAsEpilogue(const MachineBasicBlock &MBB) const {1660const MachineFunction *MF = MBB.getParent();1661MachineBasicBlock *TmpMBB = const_cast<MachineBasicBlock *>(&MBB);1662const auto *RVFI = MF->getInfo<RISCVMachineFunctionInfo>();16631664if (!RVFI->useSaveRestoreLibCalls(*MF))1665return true;16661667// Using the __riscv_restore libcalls to restore CSRs requires a tail call.1668// This means if we still need to continue executing code within this function1669// the restore cannot take place in this basic block.16701671if (MBB.succ_size() > 1)1672return false;16731674MachineBasicBlock *SuccMBB =1675MBB.succ_empty() ? TmpMBB->getFallThrough() : *MBB.succ_begin();16761677// Doing a tail call should be safe if there are no successors, because either1678// we have a returning block or the end of the block is unreachable, so the1679// restore will be eliminated regardless.1680if (!SuccMBB)1681return true;16821683// The successor can only contain a return, since we would effectively be1684// replacing the successor with our own tail return at the end of our block.1685return SuccMBB->isReturnBlock() && SuccMBB->size() == 1;1686}16871688bool RISCVFrameLowering::isSupportedStackID(TargetStackID::Value ID) const {1689switch (ID) {1690case TargetStackID::Default:1691case TargetStackID::ScalableVector:1692return true;1693case TargetStackID::NoAlloc:1694case TargetStackID::SGPRSpill:1695case TargetStackID::WasmLocal:1696return false;1697}1698llvm_unreachable("Invalid TargetStackID::Value");1699}17001701TargetStackID::Value RISCVFrameLowering::getStackIDForScalableVectors() const {1702return TargetStackID::ScalableVector;1703}170417051706