xref: /freebsd-src/contrib/llvm-project/llvm/lib/Target/RISCV/RISCVFrameLowering.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
106c3fb27SDimitry Andric //===-- RISCVFrameLowering.h - Define frame lowering for RISC-V -*- C++ -*-===//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric //
906c3fb27SDimitry Andric // This class implements RISC-V specific bits of TargetFrameLowering class.
100b57cec5SDimitry Andric //
110b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
120b57cec5SDimitry Andric 
130b57cec5SDimitry Andric #ifndef LLVM_LIB_TARGET_RISCV_RISCVFRAMELOWERING_H
140b57cec5SDimitry Andric #define LLVM_LIB_TARGET_RISCV_RISCVFRAMELOWERING_H
150b57cec5SDimitry Andric 
160b57cec5SDimitry Andric #include "llvm/CodeGen/TargetFrameLowering.h"
17e8d8bef9SDimitry Andric #include "llvm/Support/TypeSize.h"
180b57cec5SDimitry Andric 
190b57cec5SDimitry Andric namespace llvm {
200b57cec5SDimitry Andric class RISCVSubtarget;
210b57cec5SDimitry Andric 
220b57cec5SDimitry Andric class RISCVFrameLowering : public TargetFrameLowering {
230b57cec5SDimitry Andric public:
247a6dacacSDimitry Andric   explicit RISCVFrameLowering(const RISCVSubtarget &STI);
250b57cec5SDimitry Andric 
260b57cec5SDimitry Andric   void emitPrologue(MachineFunction &MF, MachineBasicBlock &MBB) const override;
270b57cec5SDimitry Andric   void emitEpilogue(MachineFunction &MF, MachineBasicBlock &MBB) const override;
280b57cec5SDimitry Andric 
2981ad6265SDimitry Andric   uint64_t getStackSizeWithRVVPadding(const MachineFunction &MF) const;
3081ad6265SDimitry Andric 
31e8d8bef9SDimitry Andric   StackOffset getFrameIndexReference(const MachineFunction &MF, int FI,
325ffd83dbSDimitry Andric                                      Register &FrameReg) const override;
330b57cec5SDimitry Andric 
340b57cec5SDimitry Andric   void determineCalleeSaves(MachineFunction &MF, BitVector &SavedRegs,
350b57cec5SDimitry Andric                             RegScavenger *RS) const override;
360b57cec5SDimitry Andric 
370b57cec5SDimitry Andric   void processFunctionBeforeFrameFinalized(MachineFunction &MF,
380b57cec5SDimitry Andric                                            RegScavenger *RS) const override;
390b57cec5SDimitry Andric 
400b57cec5SDimitry Andric   bool hasFP(const MachineFunction &MF) const override;
410b57cec5SDimitry Andric 
42480093f4SDimitry Andric   bool hasBP(const MachineFunction &MF) const;
43480093f4SDimitry Andric 
440b57cec5SDimitry Andric   bool hasReservedCallFrame(const MachineFunction &MF) const override;
450b57cec5SDimitry Andric   MachineBasicBlock::iterator
460b57cec5SDimitry Andric   eliminateCallFramePseudoInstr(MachineFunction &MF, MachineBasicBlock &MBB,
470b57cec5SDimitry Andric                                 MachineBasicBlock::iterator MI) const override;
48*0fca6ea1SDimitry Andric 
49*0fca6ea1SDimitry Andric   bool assignCalleeSavedSpillSlots(MachineFunction &MF,
50*0fca6ea1SDimitry Andric                                    const TargetRegisterInfo *TRI,
51*0fca6ea1SDimitry Andric                                    std::vector<CalleeSavedInfo> &CSI,
52*0fca6ea1SDimitry Andric                                    unsigned &MinCSFrameIndex,
53*0fca6ea1SDimitry Andric                                    unsigned &MaxCSFrameIndex) const override;
545ffd83dbSDimitry Andric   bool spillCalleeSavedRegisters(MachineBasicBlock &MBB,
555ffd83dbSDimitry Andric                                  MachineBasicBlock::iterator MI,
565ffd83dbSDimitry Andric                                  ArrayRef<CalleeSavedInfo> CSI,
575ffd83dbSDimitry Andric                                  const TargetRegisterInfo *TRI) const override;
585ffd83dbSDimitry Andric   bool
595ffd83dbSDimitry Andric   restoreCalleeSavedRegisters(MachineBasicBlock &MBB,
605ffd83dbSDimitry Andric                               MachineBasicBlock::iterator MI,
615ffd83dbSDimitry Andric                               MutableArrayRef<CalleeSavedInfo> CSI,
625ffd83dbSDimitry Andric                               const TargetRegisterInfo *TRI) const override;
630b57cec5SDimitry Andric 
648bcb0991SDimitry Andric   // Get the first stack adjustment amount for SplitSPAdjust.
655f757f3fSDimitry Andric   // Return 0 if we don't want to split the SP adjustment in prologue and
668bcb0991SDimitry Andric   // epilogue.
678bcb0991SDimitry Andric   uint64_t getFirstSPAdjustAmount(const MachineFunction &MF) const;
688bcb0991SDimitry Andric 
695ffd83dbSDimitry Andric   bool canUseAsPrologue(const MachineBasicBlock &MBB) const override;
705ffd83dbSDimitry Andric   bool canUseAsEpilogue(const MachineBasicBlock &MBB) const override;
715ffd83dbSDimitry Andric 
7281ad6265SDimitry Andric   bool enableShrinkWrapping(const MachineFunction &MF) const override;
7381ad6265SDimitry Andric 
74fe6060f1SDimitry Andric   bool isSupportedStackID(TargetStackID::Value ID) const override;
75fe6060f1SDimitry Andric   TargetStackID::Value getStackIDForScalableVectors() const override;
76fe6060f1SDimitry Andric 
77bdd1243dSDimitry Andric   bool isStackIdSafeForLocalArea(unsigned StackId) const override {
7806c3fb27SDimitry Andric     // We don't support putting RISC-V Vector objects into the pre-allocated
79bdd1243dSDimitry Andric     // local frame block at the moment.
80bdd1243dSDimitry Andric     return StackId != TargetStackID::ScalableVector;
81bdd1243dSDimitry Andric   }
82bdd1243dSDimitry Andric 
830b57cec5SDimitry Andric protected:
840b57cec5SDimitry Andric   const RISCVSubtarget &STI;
850b57cec5SDimitry Andric 
860b57cec5SDimitry Andric private:
870b57cec5SDimitry Andric   void determineFrameLayout(MachineFunction &MF) const;
88fe6060f1SDimitry Andric   void adjustStackForRVV(MachineFunction &MF, MachineBasicBlock &MBB,
89fe6060f1SDimitry Andric                          MachineBasicBlock::iterator MBBI, const DebugLoc &DL,
90fe6060f1SDimitry Andric                          int64_t Amount, MachineInstr::MIFlag Flag) const;
91*0fca6ea1SDimitry Andric   void emitCalleeSavedRVVPrologCFI(MachineBasicBlock &MBB,
92*0fca6ea1SDimitry Andric                                    MachineBasicBlock::iterator MI,
93*0fca6ea1SDimitry Andric                                    bool HasFP) const;
9481ad6265SDimitry Andric   std::pair<int64_t, Align>
95753f127fSDimitry Andric   assignRVVStackObjectOffsets(MachineFunction &MF) const;
960b57cec5SDimitry Andric };
97753f127fSDimitry Andric } // namespace llvm
980b57cec5SDimitry Andric #endif
99