1274955Ssvnmir//===-- StackMapLivenessAnalysis.cpp - StackMap live Out Analysis ----------===// 2274955Ssvnmir// 3274955Ssvnmir// The LLVM Compiler Infrastructure 4274955Ssvnmir// 5274955Ssvnmir// This file is distributed under the University of Illinois Open Source 6274955Ssvnmir// License. See LICENSE.TXT for details. 7274955Ssvnmir// 8274955Ssvnmir//===----------------------------------------------------------------------===// 9274955Ssvnmir// 10274955Ssvnmir// This file implements the StackMap Liveness analysis pass. The pass calculates 11274955Ssvnmir// the liveness for each basic block in a function and attaches the register 12274955Ssvnmir// live-out information to a stackmap or patchpoint intrinsic if present. 13274955Ssvnmir// 14274955Ssvnmir//===----------------------------------------------------------------------===// 15274955Ssvnmir 16274955Ssvnmir#include "llvm/ADT/Statistic.h" 17288943Sdim#include "llvm/CodeGen/LivePhysRegs.h" 18274955Ssvnmir#include "llvm/CodeGen/MachineFrameInfo.h" 19274955Ssvnmir#include "llvm/CodeGen/MachineFunction.h" 20274955Ssvnmir#include "llvm/CodeGen/MachineFunctionAnalysis.h" 21288943Sdim#include "llvm/CodeGen/MachineFunctionPass.h" 22274955Ssvnmir#include "llvm/CodeGen/Passes.h" 23274955Ssvnmir#include "llvm/Support/CommandLine.h" 24274955Ssvnmir#include "llvm/Support/Debug.h" 25288943Sdim#include "llvm/Support/raw_ostream.h" 26280031Sdim#include "llvm/Target/TargetSubtargetInfo.h" 27274955Ssvnmir 28274955Ssvnmirusing namespace llvm; 29274955Ssvnmir 30274955Ssvnmir#define DEBUG_TYPE "stackmaps" 31274955Ssvnmir 32288943Sdimstatic cl::opt<bool> EnablePatchPointLiveness( 33288943Sdim "enable-patchpoint-liveness", cl::Hidden, cl::init(true), 34288943Sdim cl::desc("Enable PatchPoint Liveness Analysis Pass")); 35274955Ssvnmir 36274955SsvnmirSTATISTIC(NumStackMapFuncVisited, "Number of functions visited"); 37274955SsvnmirSTATISTIC(NumStackMapFuncSkipped, "Number of functions skipped"); 38274955SsvnmirSTATISTIC(NumBBsVisited, "Number of basic blocks visited"); 39274955SsvnmirSTATISTIC(NumBBsHaveNoStackmap, "Number of basic blocks with no stackmap"); 40274955SsvnmirSTATISTIC(NumStackMaps, "Number of StackMaps visited"); 41274955Ssvnmir 42288943Sdimnamespace { 43288943Sdim/// \brief This pass calculates the liveness information for each basic block in 44288943Sdim/// a function and attaches the register live-out information to a patchpoint 45288943Sdim/// intrinsic if present. 46288943Sdim/// 47288943Sdim/// This pass can be disabled via the -enable-patchpoint-liveness=false flag. 48288943Sdim/// The pass skips functions that don't have any patchpoint intrinsics. The 49288943Sdim/// information provided by this pass is optional and not required by the 50288943Sdim/// aformentioned intrinsic to function. 51288943Sdimclass StackMapLiveness : public MachineFunctionPass { 52288943Sdim const TargetRegisterInfo *TRI; 53288943Sdim LivePhysRegs LiveRegs; 54288943Sdim 55288943Sdimpublic: 56288943Sdim static char ID; 57288943Sdim 58288943Sdim /// \brief Default construct and initialize the pass. 59288943Sdim StackMapLiveness(); 60288943Sdim 61288943Sdim /// \brief Tell the pass manager which passes we depend on and what 62288943Sdim /// information we preserve. 63288943Sdim void getAnalysisUsage(AnalysisUsage &AU) const override; 64288943Sdim 65288943Sdim /// \brief Calculate the liveness information for the given machine function. 66288943Sdim bool runOnMachineFunction(MachineFunction &MF) override; 67288943Sdim 68288943Sdimprivate: 69288943Sdim /// \brief Performs the actual liveness calculation for the function. 70288943Sdim bool calculateLiveness(MachineFunction &MF); 71288943Sdim 72288943Sdim /// \brief Add the current register live set to the instruction. 73288943Sdim void addLiveOutSetToMI(MachineFunction &MF, MachineInstr &MI); 74288943Sdim 75288943Sdim /// \brief Create a register mask and initialize it with the registers from 76288943Sdim /// the register live set. 77288943Sdim uint32_t *createRegisterMask(MachineFunction &MF) const; 78288943Sdim}; 79288943Sdim} // namespace 80288943Sdim 81274955Ssvnmirchar StackMapLiveness::ID = 0; 82274955Ssvnmirchar &llvm::StackMapLivenessID = StackMapLiveness::ID; 83274955SsvnmirINITIALIZE_PASS(StackMapLiveness, "stackmap-liveness", 84274955Ssvnmir "StackMap Liveness Analysis", false, false) 85274955Ssvnmir 86274955Ssvnmir/// Default construct and initialize the pass. 87274955SsvnmirStackMapLiveness::StackMapLiveness() : MachineFunctionPass(ID) { 88274955Ssvnmir initializeStackMapLivenessPass(*PassRegistry::getPassRegistry()); 89274955Ssvnmir} 90274955Ssvnmir 91274955Ssvnmir/// Tell the pass manager which passes we depend on and what information we 92274955Ssvnmir/// preserve. 93274955Ssvnmirvoid StackMapLiveness::getAnalysisUsage(AnalysisUsage &AU) const { 94274955Ssvnmir // We preserve all information. 95274955Ssvnmir AU.setPreservesAll(); 96274955Ssvnmir AU.setPreservesCFG(); 97288943Sdim MachineFunctionPass::getAnalysisUsage(AU); 98274955Ssvnmir} 99274955Ssvnmir 100274955Ssvnmir/// Calculate the liveness information for the given machine function. 101288943Sdimbool StackMapLiveness::runOnMachineFunction(MachineFunction &MF) { 102274955Ssvnmir if (!EnablePatchPointLiveness) 103274955Ssvnmir return false; 104274955Ssvnmir 105288943Sdim DEBUG(dbgs() << "********** COMPUTING STACKMAP LIVENESS: " << MF.getName() 106288943Sdim << " **********\n"); 107288943Sdim TRI = MF.getSubtarget().getRegisterInfo(); 108274955Ssvnmir ++NumStackMapFuncVisited; 109274955Ssvnmir 110274955Ssvnmir // Skip this function if there are no patchpoints to process. 111288943Sdim if (!MF.getFrameInfo()->hasPatchPoint()) { 112274955Ssvnmir ++NumStackMapFuncSkipped; 113274955Ssvnmir return false; 114274955Ssvnmir } 115288943Sdim return calculateLiveness(MF); 116274955Ssvnmir} 117274955Ssvnmir 118274955Ssvnmir/// Performs the actual liveness calculation for the function. 119288943Sdimbool StackMapLiveness::calculateLiveness(MachineFunction &MF) { 120274955Ssvnmir bool HasChanged = false; 121274955Ssvnmir // For all basic blocks in the function. 122288943Sdim for (auto &MBB : MF) { 123288943Sdim DEBUG(dbgs() << "****** BB " << MBB.getName() << " ******\n"); 124274955Ssvnmir LiveRegs.init(TRI); 125288943Sdim LiveRegs.addLiveOuts(&MBB); 126274955Ssvnmir bool HasStackMap = false; 127274955Ssvnmir // Reverse iterate over all instructions and add the current live register 128274955Ssvnmir // set to an instruction if we encounter a patchpoint instruction. 129288943Sdim for (auto I = MBB.rbegin(), E = MBB.rend(); I != E; ++I) { 130274955Ssvnmir if (I->getOpcode() == TargetOpcode::PATCHPOINT) { 131288943Sdim addLiveOutSetToMI(MF, *I); 132274955Ssvnmir HasChanged = true; 133274955Ssvnmir HasStackMap = true; 134274955Ssvnmir ++NumStackMaps; 135274955Ssvnmir } 136274955Ssvnmir DEBUG(dbgs() << " " << LiveRegs << " " << *I); 137274955Ssvnmir LiveRegs.stepBackward(*I); 138274955Ssvnmir } 139274955Ssvnmir ++NumBBsVisited; 140274955Ssvnmir if (!HasStackMap) 141274955Ssvnmir ++NumBBsHaveNoStackmap; 142274955Ssvnmir } 143274955Ssvnmir return HasChanged; 144274955Ssvnmir} 145274955Ssvnmir 146274955Ssvnmir/// Add the current register live set to the instruction. 147288943Sdimvoid StackMapLiveness::addLiveOutSetToMI(MachineFunction &MF, 148288943Sdim MachineInstr &MI) { 149288943Sdim uint32_t *Mask = createRegisterMask(MF); 150274955Ssvnmir MachineOperand MO = MachineOperand::CreateRegLiveOut(Mask); 151288943Sdim MI.addOperand(MF, MO); 152274955Ssvnmir} 153274955Ssvnmir 154274955Ssvnmir/// Create a register mask and initialize it with the registers from the 155274955Ssvnmir/// register live set. 156288943Sdimuint32_t *StackMapLiveness::createRegisterMask(MachineFunction &MF) const { 157274955Ssvnmir // The mask is owned and cleaned up by the Machine Function. 158288943Sdim uint32_t *Mask = MF.allocateRegisterMask(TRI->getNumRegs()); 159288943Sdim for (auto Reg : LiveRegs) 160288943Sdim Mask[Reg / 32] |= 1U << (Reg % 32); 161280031Sdim 162288943Sdim // Give the target a chance to adjust the mask. 163280031Sdim TRI->adjustStackMapLiveOutMask(Mask); 164288943Sdim 165274955Ssvnmir return Mask; 166274955Ssvnmir} 167