44 enum Lowering { TouchAndSub, Sub, Probe };
53 Lowering getLowering(int64_t CurrentOffset, int64_t AllocaAmount);
64 int64_t StackProbeSize;
66 StringRef getPassName()
const override {
return "X86 WinAlloca Expander"; }
75 return new X86WinAllocaExpander();
99 X86WinAllocaExpander::Lowering
100 X86WinAllocaExpander::getLowering(int64_t CurrentOffset,
101 int64_t AllocaAmount) {
103 if (AllocaAmount < 0 || AllocaAmount > StackProbeSize)
107 if (CurrentOffset + AllocaAmount <= StackProbeSize)
135 LoweringMap &Lowerings) {
143 OutOffset[&
MBB] = INT32_MAX;
155 Offset = std::max(Offset, OutOffset[Pred]);
156 if (Offset == -1) Offset = INT32_MAX;
159 if (
MI.getOpcode() == X86::WIN_ALLOCA_32 ||
160 MI.getOpcode() == X86::WIN_ALLOCA_64) {
163 Lowering L = getLowering(Offset, Amount);
179 }
else if (
MI.getOpcode() == X86::ADJCALLSTACKUP32 ||
180 MI.getOpcode() == X86::ADJCALLSTACKUP64) {
181 Offset -=
MI.getOperand(0).getImm();
182 }
else if (
MI.getOpcode() == X86::ADJCALLSTACKDOWN32 ||
183 MI.getOpcode() == X86::ADJCALLSTACKDOWN64) {
184 Offset +=
MI.getOperand(0).getImm();
185 }
else if (
MI.modifiesRegister(StackPtr, TRI)) {
197 return isInt<8>(Amount) ? X86::SUB64ri8 : X86::SUB64ri32;
198 return isInt<8>(Amount) ? X86::SUB32ri8 : X86::SUB32ri;
212 bool Is64Bit = STI->is64Bit();
213 assert(SlotSize == 4 || SlotSize == 8);
214 unsigned RegA = (SlotSize == 8) ? X86::RAX : X86::EAX;
218 assert(Amount >= SlotSize);
221 BuildMI(*MBB, I, DL,
TII->get(Is64Bit ? X86::PUSH64r : X86::PUSH32r))
231 if (Amount == SlotSize) {
233 BuildMI(*MBB, I, DL,
TII->get(Is64Bit ? X86::PUSH64r : X86::PUSH32r))
244 BuildMI(*MBB, MI, DL,
TII->get(TargetOpcode::COPY), RegA)
248 STI->getFrameLowering()->emitStackProbe(*MBB->
getParent(), *
MBB,
MI, DL,
258 if (!
MRI->use_empty(AmountReg))
276 TII = STI->getInstrInfo();
279 SlotSize = TRI->getSlotSize();
281 StackProbeSize = 4096;
289 LoweringMap Lowerings;
290 computeLowerings(MF, Lowerings);
291 for (
auto &
P : Lowerings)
292 lower(
P.first,
P.second);
std::enable_if< std::numeric_limits< T >::is_signed, bool >::type getAsInteger(unsigned Radix, T &Result) const
Parse the current string as an integer of the specified radix.
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
constexpr bool isInt< 8 >(int64_t x)
This class implements a map that also provides access to all stored values in a deterministic order...
Attribute getFnAttribute(Attribute::AttrKind Kind) const
Return the attribute for the given attribute kind.
const Function * getFunction() const
getFunction - Return the LLVM function that this machine code represents
X86MachineFunctionInfo - This class is derived from MachineFunction and contains private X86 target-s...
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
const HexagonInstrInfo * TII
bool isImm() const
isImm - Tests if this is a MO_Immediate operand.
bool isReg() const
isReg - Tests if this is a MO_Register operand.
void eraseFromParent()
Unlink 'this' from the containing basic block and delete it.
static int64_t getWinAllocaAmount(MachineInstr *MI, MachineRegisterInfo *MRI)
Return the allocation amount for a WinAlloca instruction, or -1 if unknown.
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
const HexagonRegisterInfo & getRegisterInfo() const
HexagonInstrInfo specifics.
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
const MachineBasicBlock * getParent() const
TargetInstrInfo - Interface to description of machine instruction set.
MachineInstrBuilder BuildMI(MachineFunction &MF, const DebugLoc &DL, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
unsigned const MachineRegisterInfo * MRI
const MachineOperand & getOperand(unsigned i) const
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
FunctionPass class - This class is used to implement most global optimizations.
iterator_range< pred_iterator > predecessors()
shadow stack gc Shadow Stack GC Lowering
MachineInstr * getUniqueVRegDef(unsigned Reg) const
getUniqueVRegDef - Return the unique machine instr that defines the specified virtual register or nul...
const DebugLoc & getDebugLoc() const
Returns the debug location id of this MachineInstr.
FunctionPass * createX86WinAllocaExpander()
Return a pass that expands WinAlloca pseudo-instructions.
MachineRegisterInfo - Keep track of information for virtual and physical registers, including vreg register classes, use/def chains for registers, etc.
Representation of each machine instruction.
bool hasFnAttribute(Attribute::AttrKind Kind) const
Return true if the function has the attribute.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
bool hasWinAlloca() const
unsigned getStackRegister() const
unsigned getReg() const
getReg - Returns the register number.
StringRef getValueAsString() const
Return the attribute's value as a string.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
rpo Deduce function attributes in RPO
#define LLVM_FALLTHROUGH
LLVM_FALLTHROUGH - Mark fallthrough cases in switch statements.
static unsigned getSubOpcode(bool Is64Bit, int64_t Amount)
StringRef - Represent a constant reference to a string, i.e.
static bool isPushPop(const MachineInstr &MI)