#include "X86FrameLowering.h"
#include "MCTargetDesc/X86MCTargetDesc.h"
#include "X86InstrBuilder.h"
#include "X86InstrInfo.h"
#include "X86MachineFunctionInfo.h"
#include "X86Subtarget.h"
#include "X86TargetMachine.h"
#include "llvm/ADT/Statistic.h"
#include "llvm/CodeGen/LivePhysRegs.h"
#include "llvm/CodeGen/MachineFrameInfo.h"
#include "llvm/CodeGen/MachineFunction.h"
#include "llvm/CodeGen/MachineInstrBuilder.h"
#include "llvm/CodeGen/MachineModuleInfo.h"
#include "llvm/CodeGen/MachineRegisterInfo.h"
#include "llvm/CodeGen/WinEHFuncInfo.h"
#include "llvm/IR/DataLayout.h"
#include "llvm/IR/EHPersonalities.h"
#include "llvm/IR/Function.h"
#include "llvm/IR/Module.h"
#include "llvm/MC/MCAsmInfo.h"
#include "llvm/MC/MCObjectFileInfo.h"
#include "llvm/MC/MCSymbol.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/LEB128.h"
#include "llvm/Target/TargetOptions.h"
#include <cstdlib>
#define DEBUG_TYPE …
STATISTIC(NumFrameLoopProbe, "Number of loop stack probes used in prologue");
STATISTIC(NumFrameExtraProbe,
"Number of extra stack probes generated in prologue");
STATISTIC(NumFunctionUsingPush2Pop2, "Number of funtions using push2/pop2");
usingnamespacellvm;
X86FrameLowering::X86FrameLowering(const X86Subtarget &STI,
MaybeAlign StackAlignOverride)
: … { … }
bool X86FrameLowering::hasReservedCallFrame(const MachineFunction &MF) const { … }
bool X86FrameLowering::canSimplifyCallFramePseudos(
const MachineFunction &MF) const { … }
bool X86FrameLowering::needsFrameIndexResolution(
const MachineFunction &MF) const { … }
bool X86FrameLowering::hasFP(const MachineFunction &MF) const { … }
static unsigned getSUBriOpcode(bool IsLP64) { … }
static unsigned getADDriOpcode(bool IsLP64) { … }
static unsigned getSUBrrOpcode(bool IsLP64) { … }
static unsigned getADDrrOpcode(bool IsLP64) { … }
static unsigned getANDriOpcode(bool IsLP64, int64_t Imm) { … }
static unsigned getLEArOpcode(bool IsLP64) { … }
static unsigned getMOVriOpcode(bool Use64BitReg, int64_t Imm) { … }
static unsigned getPUSHOpcode(const X86Subtarget &ST) { … }
static unsigned getPOPOpcode(const X86Subtarget &ST) { … }
static unsigned getPUSH2Opcode(const X86Subtarget &ST) { … }
static unsigned getPOP2Opcode(const X86Subtarget &ST) { … }
static bool isEAXLiveIn(MachineBasicBlock &MBB) { … }
static bool
flagsNeedToBePreservedBeforeTheTerminators(const MachineBasicBlock &MBB) { … }
void X86FrameLowering::emitSPUpdate(MachineBasicBlock &MBB,
MachineBasicBlock::iterator &MBBI,
const DebugLoc &DL, int64_t NumBytes,
bool InEpilogue) const { … }
MachineInstrBuilder X86FrameLowering::BuildStackAdjustment(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
const DebugLoc &DL, int64_t Offset, bool InEpilogue) const { … }
int X86FrameLowering::mergeSPUpdates(MachineBasicBlock &MBB,
MachineBasicBlock::iterator &MBBI,
bool doMergeWithPrevious) const { … }
void X86FrameLowering::BuildCFI(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI,
const DebugLoc &DL,
const MCCFIInstruction &CFIInst,
MachineInstr::MIFlag Flag) const { … }
void X86FrameLowering::emitCalleeSavedFrameMovesFullCFA(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI) const { … }
void X86FrameLowering::emitCalleeSavedFrameMoves(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
const DebugLoc &DL, bool IsPrologue) const { … }
void X86FrameLowering::emitZeroCallUsedRegs(BitVector RegsToZero,
MachineBasicBlock &MBB) const { … }
void X86FrameLowering::emitStackProbe(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, bool InProlog,
std::optional<MachineFunction::DebugInstrOperandPair> InstrNum) const { … }
bool X86FrameLowering::stackProbeFunctionModifiesSP() const { … }
void X86FrameLowering::inlineStackProbe(MachineFunction &MF,
MachineBasicBlock &PrologMBB) const { … }
void X86FrameLowering::emitStackProbeInline(MachineFunction &MF,
MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI,
const DebugLoc &DL,
bool InProlog) const { … }
void X86FrameLowering::emitStackProbeInlineGeneric(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, bool InProlog) const { … }
void X86FrameLowering::emitStackProbeInlineGenericBlock(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, uint64_t Offset,
uint64_t AlignOffset) const { … }
void X86FrameLowering::emitStackProbeInlineGenericLoop(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, uint64_t Offset,
uint64_t AlignOffset) const { … }
void X86FrameLowering::emitStackProbeInlineWindowsCoreCLR64(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, bool InProlog) const { … }
void X86FrameLowering::emitStackProbeCall(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, const DebugLoc &DL, bool InProlog,
std::optional<MachineFunction::DebugInstrOperandPair> InstrNum) const { … }
static unsigned calculateSetFPREG(uint64_t SPAdjust) { … }
uint64_t
X86FrameLowering::calculateMaxStackAlign(const MachineFunction &MF) const { … }
void X86FrameLowering::BuildStackAlignAND(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI,
const DebugLoc &DL, unsigned Reg,
uint64_t MaxAlign) const { … }
bool X86FrameLowering::has128ByteRedZone(const MachineFunction &MF) const { … }
bool X86FrameLowering::isWin64Prologue(const MachineFunction &MF) const { … }
bool X86FrameLowering::needsDwarfCFI(const MachineFunction &MF) const { … }
static bool isOpcodeRep(unsigned Opcode) { … }
void X86FrameLowering::emitPrologue(MachineFunction &MF,
MachineBasicBlock &MBB) const { … }
bool X86FrameLowering::canUseLEAForSPInEpilogue(
const MachineFunction &MF) const { … }
static bool isFuncletReturnInstr(MachineInstr &MI) { … }
unsigned
X86FrameLowering::getPSPSlotOffsetFromSP(const MachineFunction &MF) const { … }
unsigned
X86FrameLowering::getWinEHFuncletFrameSize(const MachineFunction &MF) const { … }
static bool isTailCallOpcode(unsigned Opc) { … }
void X86FrameLowering::emitEpilogue(MachineFunction &MF,
MachineBasicBlock &MBB) const { … }
StackOffset X86FrameLowering::getFrameIndexReference(const MachineFunction &MF,
int FI,
Register &FrameReg) const { … }
int X86FrameLowering::getWin64EHFrameIndexRef(const MachineFunction &MF, int FI,
Register &FrameReg) const { … }
StackOffset
X86FrameLowering::getFrameIndexReferenceSP(const MachineFunction &MF, int FI,
Register &FrameReg,
int Adjustment) const { … }
StackOffset
X86FrameLowering::getFrameIndexReferencePreferSP(const MachineFunction &MF,
int FI, Register &FrameReg,
bool IgnoreSPUpdates) const { … }
bool X86FrameLowering::assignCalleeSavedSpillSlots(
MachineFunction &MF, const TargetRegisterInfo *TRI,
std::vector<CalleeSavedInfo> &CSI) const { … }
bool X86FrameLowering::spillCalleeSavedRegisters(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
ArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const { … }
void X86FrameLowering::emitCatchRetReturnValue(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI,
MachineInstr *CatchRet) const { … }
bool X86FrameLowering::restoreCalleeSavedRegisters(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MI,
MutableArrayRef<CalleeSavedInfo> CSI, const TargetRegisterInfo *TRI) const { … }
void X86FrameLowering::determineCalleeSaves(MachineFunction &MF,
BitVector &SavedRegs,
RegScavenger *RS) const { … }
static bool HasNestArgument(const MachineFunction *MF) { … }
static unsigned GetScratchRegister(bool Is64Bit, bool IsLP64,
const MachineFunction &MF, bool Primary) { … }
static const uint64_t kSplitStackAvailable = …;
void X86FrameLowering::adjustForSegmentedStacks(
MachineFunction &MF, MachineBasicBlock &PrologueMBB) const { … }
static unsigned getHiPELiteral(NamedMDNode *HiPELiteralsMD,
const StringRef LiteralName) { … }
static bool blockEndIsUnreachable(const MachineBasicBlock &MBB,
MachineBasicBlock::const_iterator MBBI) { … }
void X86FrameLowering::adjustForHiPEPrologue(
MachineFunction &MF, MachineBasicBlock &PrologueMBB) const { … }
bool X86FrameLowering::adjustStackWithPops(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI,
const DebugLoc &DL,
int Offset) const { … }
MachineBasicBlock::iterator X86FrameLowering::eliminateCallFramePseudoInstr(
MachineFunction &MF, MachineBasicBlock &MBB,
MachineBasicBlock::iterator I) const { … }
bool X86FrameLowering::canUseAsPrologue(const MachineBasicBlock &MBB) const { … }
bool X86FrameLowering::canUseAsEpilogue(const MachineBasicBlock &MBB) const { … }
bool X86FrameLowering::enableShrinkWrapping(const MachineFunction &MF) const { … }
MachineBasicBlock::iterator X86FrameLowering::restoreWin32EHStackPointers(
MachineBasicBlock &MBB, MachineBasicBlock::iterator MBBI,
const DebugLoc &DL, bool RestoreSP) const { … }
int X86FrameLowering::getInitialCFAOffset(const MachineFunction &MF) const { … }
Register
X86FrameLowering::getInitialCFARegister(const MachineFunction &MF) const { … }
TargetFrameLowering::DwarfFrameBase
X86FrameLowering::getDwarfFrameBase(const MachineFunction &MF) const { … }
namespace {
struct X86FrameSortingObject { … };
struct X86FrameSortingComparator { … };
}
void X86FrameLowering::orderFrameObjects(
const MachineFunction &MF, SmallVectorImpl<int> &ObjectsToAllocate) const { … }
unsigned
X86FrameLowering::getWinEHParentFrameOffset(const MachineFunction &MF) const { … }
void X86FrameLowering::processFunctionBeforeFrameFinalized(
MachineFunction &MF, RegScavenger *RS) const { … }
void X86FrameLowering::adjustFrameForMsvcCxxEh(MachineFunction &MF) const { … }
void X86FrameLowering::processFunctionBeforeFrameIndicesReplaced(
MachineFunction &MF, RegScavenger *RS) const { … }
void X86FrameLowering::restoreWinEHStackPointersInParent(
MachineFunction &MF) const { … }
static int computeFPBPAlignmentGap(MachineFunction &MF,
const TargetRegisterClass *RC,
unsigned NumSpilledRegs) { … }
void X86FrameLowering::spillFPBPUsingSP(MachineFunction &MF,
MachineBasicBlock::iterator BeforeMI,
Register FP, Register BP,
int SPAdjust) const { … }
void X86FrameLowering::restoreFPBPUsingSP(MachineFunction &MF,
MachineBasicBlock::iterator AfterMI,
Register FP, Register BP,
int SPAdjust) const { … }
void X86FrameLowering::saveAndRestoreFPBPUsingSP(
MachineFunction &MF, MachineBasicBlock::iterator BeforeMI,
MachineBasicBlock::iterator AfterMI, bool SpillFP, bool SpillBP) const { … }
bool X86FrameLowering::skipSpillFPBP(
MachineFunction &MF, MachineBasicBlock::reverse_iterator &MI) const { … }
static bool isFPBPAccess(const MachineInstr &MI, Register FP, Register BP,
const TargetRegisterInfo *TRI, bool &AccessFP,
bool &AccessBP) { … }
static bool isInvoke(const MachineInstr &MI, bool InsideEHLabels) { … }
void X86FrameLowering::checkInterferedAccess(
MachineFunction &MF, MachineBasicBlock::reverse_iterator DefMI,
MachineBasicBlock::reverse_iterator KillMI, bool SpillFP,
bool SpillBP) const { … }
void X86FrameLowering::spillFPBP(MachineFunction &MF) const { … }