101095a5dSDimitry Andric //===-- RegUsageInfoCollector.cpp - Register Usage Information Collector --===//
201095a5dSDimitry Andric //
3e6d15924SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4e6d15924SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
5e6d15924SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
601095a5dSDimitry Andric //
701095a5dSDimitry Andric //===----------------------------------------------------------------------===//
801095a5dSDimitry Andric ///
901095a5dSDimitry Andric /// This pass is required to take advantage of the interprocedural register
1001095a5dSDimitry Andric /// allocation infrastructure.
1101095a5dSDimitry Andric ///
1201095a5dSDimitry Andric /// This pass is simple MachineFunction pass which collects register usage
1301095a5dSDimitry Andric /// details by iterating through each physical registers and checking
1401095a5dSDimitry Andric /// MRI::isPhysRegUsed() then creates a RegMask based on this details.
1501095a5dSDimitry Andric /// The pass then stores this RegMask in PhysicalRegisterUsageInfo.cpp
1601095a5dSDimitry Andric ///
1701095a5dSDimitry Andric //===----------------------------------------------------------------------===//
1801095a5dSDimitry Andric
1901095a5dSDimitry Andric #include "llvm/ADT/Statistic.h"
2001095a5dSDimitry Andric #include "llvm/CodeGen/MachineFunctionPass.h"
2101095a5dSDimitry Andric #include "llvm/CodeGen/MachineOperand.h"
2201095a5dSDimitry Andric #include "llvm/CodeGen/MachineRegisterInfo.h"
2301095a5dSDimitry Andric #include "llvm/CodeGen/Passes.h"
2401095a5dSDimitry Andric #include "llvm/CodeGen/RegisterUsageInfo.h"
25145449b1SDimitry Andric #include "llvm/CodeGen/TargetFrameLowering.h"
26145449b1SDimitry Andric #include "llvm/IR/Function.h"
2701095a5dSDimitry Andric #include "llvm/Support/Debug.h"
2801095a5dSDimitry Andric #include "llvm/Support/raw_ostream.h"
2901095a5dSDimitry Andric
3001095a5dSDimitry Andric using namespace llvm;
3101095a5dSDimitry Andric
3201095a5dSDimitry Andric #define DEBUG_TYPE "ip-regalloc"
3301095a5dSDimitry Andric
3401095a5dSDimitry Andric STATISTIC(NumCSROpt,
3501095a5dSDimitry Andric "Number of functions optimized for callee saved registers");
3601095a5dSDimitry Andric
3701095a5dSDimitry Andric namespace {
38eb11fae6SDimitry Andric
3901095a5dSDimitry Andric class RegUsageInfoCollector : public MachineFunctionPass {
4001095a5dSDimitry Andric public:
RegUsageInfoCollector()4101095a5dSDimitry Andric RegUsageInfoCollector() : MachineFunctionPass(ID) {
4201095a5dSDimitry Andric PassRegistry &Registry = *PassRegistry::getPassRegistry();
4301095a5dSDimitry Andric initializeRegUsageInfoCollectorPass(Registry);
4401095a5dSDimitry Andric }
4501095a5dSDimitry Andric
getPassName() const46b915e9e0SDimitry Andric StringRef getPassName() const override {
4701095a5dSDimitry Andric return "Register Usage Information Collector Pass";
4801095a5dSDimitry Andric }
4901095a5dSDimitry Andric
getAnalysisUsage(AnalysisUsage & AU) const50eb11fae6SDimitry Andric void getAnalysisUsage(AnalysisUsage &AU) const override {
51eb11fae6SDimitry Andric AU.addRequired<PhysicalRegisterUsageInfo>();
52eb11fae6SDimitry Andric AU.setPreservesAll();
53eb11fae6SDimitry Andric MachineFunctionPass::getAnalysisUsage(AU);
54eb11fae6SDimitry Andric }
5501095a5dSDimitry Andric
5601095a5dSDimitry Andric bool runOnMachineFunction(MachineFunction &MF) override;
5701095a5dSDimitry Andric
58706b4fc4SDimitry Andric // Call getCalleeSaves and then also set the bits for subregs and
59eb11fae6SDimitry Andric // fully saved superregs.
60eb11fae6SDimitry Andric static void computeCalleeSavedRegs(BitVector &SavedRegs, MachineFunction &MF);
61eb11fae6SDimitry Andric
6201095a5dSDimitry Andric static char ID;
6301095a5dSDimitry Andric };
64eb11fae6SDimitry Andric
6501095a5dSDimitry Andric } // end of anonymous namespace
6601095a5dSDimitry Andric
6701095a5dSDimitry Andric char RegUsageInfoCollector::ID = 0;
6801095a5dSDimitry Andric
6901095a5dSDimitry Andric INITIALIZE_PASS_BEGIN(RegUsageInfoCollector, "RegUsageInfoCollector",
7001095a5dSDimitry Andric "Register Usage Information Collector", false, false)
INITIALIZE_PASS_DEPENDENCY(PhysicalRegisterUsageInfo)7101095a5dSDimitry Andric INITIALIZE_PASS_DEPENDENCY(PhysicalRegisterUsageInfo)
7201095a5dSDimitry Andric INITIALIZE_PASS_END(RegUsageInfoCollector, "RegUsageInfoCollector",
7301095a5dSDimitry Andric "Register Usage Information Collector", false, false)
7401095a5dSDimitry Andric
7501095a5dSDimitry Andric FunctionPass *llvm::createRegUsageInfoCollector() {
7601095a5dSDimitry Andric return new RegUsageInfoCollector();
7701095a5dSDimitry Andric }
7801095a5dSDimitry Andric
79e6d15924SDimitry Andric // TODO: Move to hook somwehere?
80e6d15924SDimitry Andric
81e6d15924SDimitry Andric // Return true if it is useful to track the used registers for IPRA / no CSR
82e6d15924SDimitry Andric // optimizations. This is not useful for entry points, and computing the
83e6d15924SDimitry Andric // register usage information is expensive.
isCallableFunction(const MachineFunction & MF)84e6d15924SDimitry Andric static bool isCallableFunction(const MachineFunction &MF) {
85e6d15924SDimitry Andric switch (MF.getFunction().getCallingConv()) {
86e6d15924SDimitry Andric case CallingConv::AMDGPU_VS:
87e6d15924SDimitry Andric case CallingConv::AMDGPU_GS:
88e6d15924SDimitry Andric case CallingConv::AMDGPU_PS:
89e6d15924SDimitry Andric case CallingConv::AMDGPU_CS:
90e6d15924SDimitry Andric case CallingConv::AMDGPU_HS:
91e6d15924SDimitry Andric case CallingConv::AMDGPU_ES:
92e6d15924SDimitry Andric case CallingConv::AMDGPU_LS:
93e6d15924SDimitry Andric case CallingConv::AMDGPU_KERNEL:
94e6d15924SDimitry Andric return false;
95e6d15924SDimitry Andric default:
96e6d15924SDimitry Andric return true;
97e6d15924SDimitry Andric }
98e6d15924SDimitry Andric }
99e6d15924SDimitry Andric
runOnMachineFunction(MachineFunction & MF)10001095a5dSDimitry Andric bool RegUsageInfoCollector::runOnMachineFunction(MachineFunction &MF) {
10101095a5dSDimitry Andric MachineRegisterInfo *MRI = &MF.getRegInfo();
10201095a5dSDimitry Andric const TargetRegisterInfo *TRI = MF.getSubtarget().getRegisterInfo();
103d8e91e46SDimitry Andric const LLVMTargetMachine &TM = MF.getTarget();
10401095a5dSDimitry Andric
105eb11fae6SDimitry Andric LLVM_DEBUG(dbgs() << " -------------------- " << getPassName()
106e6d15924SDimitry Andric << " -------------------- \nFunction Name : "
107e6d15924SDimitry Andric << MF.getName() << '\n');
108e6d15924SDimitry Andric
109e6d15924SDimitry Andric // Analyzing the register usage may be expensive on some targets.
110e6d15924SDimitry Andric if (!isCallableFunction(MF)) {
111e6d15924SDimitry Andric LLVM_DEBUG(dbgs() << "Not analyzing non-callable function\n");
112e6d15924SDimitry Andric return false;
113e6d15924SDimitry Andric }
114e6d15924SDimitry Andric
115e6d15924SDimitry Andric // If there are no callers, there's no point in computing more precise
116e6d15924SDimitry Andric // register usage here.
117e6d15924SDimitry Andric if (MF.getFunction().use_empty()) {
118e6d15924SDimitry Andric LLVM_DEBUG(dbgs() << "Not analyzing function with no callers\n");
119e6d15924SDimitry Andric return false;
120e6d15924SDimitry Andric }
12101095a5dSDimitry Andric
12201095a5dSDimitry Andric std::vector<uint32_t> RegMask;
12301095a5dSDimitry Andric
12401095a5dSDimitry Andric // Compute the size of the bit vector to represent all the registers.
12501095a5dSDimitry Andric // The bit vector is broken into 32-bit chunks, thus takes the ceil of
12601095a5dSDimitry Andric // the number of registers divided by 32 for the size.
127eb11fae6SDimitry Andric unsigned RegMaskSize = MachineOperand::getRegMaskSize(TRI->getNumRegs());
128eb11fae6SDimitry Andric RegMask.resize(RegMaskSize, ~((uint32_t)0));
12901095a5dSDimitry Andric
130044eb2f6SDimitry Andric const Function &F = MF.getFunction();
13101095a5dSDimitry Andric
132eb11fae6SDimitry Andric PhysicalRegisterUsageInfo &PRUI = getAnalysis<PhysicalRegisterUsageInfo>();
133eb11fae6SDimitry Andric PRUI.setTargetMachine(TM);
13401095a5dSDimitry Andric
135eb11fae6SDimitry Andric LLVM_DEBUG(dbgs() << "Clobbered Registers: ");
13601095a5dSDimitry Andric
137eb11fae6SDimitry Andric BitVector SavedRegs;
138eb11fae6SDimitry Andric computeCalleeSavedRegs(SavedRegs, MF);
13901095a5dSDimitry Andric
14071d5a254SDimitry Andric const BitVector &UsedPhysRegsMask = MRI->getUsedPhysRegsMask();
14171d5a254SDimitry Andric auto SetRegAsDefined = [&RegMask] (unsigned Reg) {
14271d5a254SDimitry Andric RegMask[Reg / 32] &= ~(1u << Reg % 32);
14371d5a254SDimitry Andric };
1441d5ae102SDimitry Andric
145ac9a064cSDimitry Andric // Don't include $noreg in any regmasks.
146ac9a064cSDimitry Andric SetRegAsDefined(MCRegister::NoRegister);
147ac9a064cSDimitry Andric
1481d5ae102SDimitry Andric // Some targets can clobber registers "inside" a call, typically in
1491d5ae102SDimitry Andric // linker-generated code.
1501d5ae102SDimitry Andric for (const MCPhysReg Reg : TRI->getIntraCallClobberedRegs(&MF))
1511d5ae102SDimitry Andric for (MCRegAliasIterator AI(Reg, TRI, true); AI.isValid(); ++AI)
1521d5ae102SDimitry Andric SetRegAsDefined(*AI);
1531d5ae102SDimitry Andric
15471d5a254SDimitry Andric // Scan all the physical registers. When a register is defined in the current
15571d5a254SDimitry Andric // function set it and all the aliasing registers as defined in the regmask.
156e6d15924SDimitry Andric // FIXME: Rewrite to use regunits.
15771d5a254SDimitry Andric for (unsigned PReg = 1, PRegE = TRI->getNumRegs(); PReg < PRegE; ++PReg) {
158eb11fae6SDimitry Andric // Don't count registers that are saved and restored.
159eb11fae6SDimitry Andric if (SavedRegs.test(PReg))
16071d5a254SDimitry Andric continue;
16171d5a254SDimitry Andric // If a register is defined by an instruction mark it as defined together
162eb11fae6SDimitry Andric // with all it's unsaved aliases.
16371d5a254SDimitry Andric if (!MRI->def_empty(PReg)) {
16471d5a254SDimitry Andric for (MCRegAliasIterator AI(PReg, TRI, true); AI.isValid(); ++AI)
165eb11fae6SDimitry Andric if (!SavedRegs.test(*AI))
16671d5a254SDimitry Andric SetRegAsDefined(*AI);
167eb11fae6SDimitry Andric continue;
16871d5a254SDimitry Andric }
169eb11fae6SDimitry Andric // If a register is in the UsedPhysRegsMask set then mark it as defined.
170eb11fae6SDimitry Andric // All clobbered aliases will also be in the set, so we can skip setting
171eb11fae6SDimitry Andric // as defined all the aliases here.
172eb11fae6SDimitry Andric if (UsedPhysRegsMask.test(PReg))
173eb11fae6SDimitry Andric SetRegAsDefined(PReg);
17471d5a254SDimitry Andric }
17501095a5dSDimitry Andric
1761d5ae102SDimitry Andric if (TargetFrameLowering::isSafeForNoCSROpt(F) &&
1771d5ae102SDimitry Andric MF.getSubtarget().getFrameLowering()->isProfitableForNoCSROpt(F)) {
17801095a5dSDimitry Andric ++NumCSROpt;
179eb11fae6SDimitry Andric LLVM_DEBUG(dbgs() << MF.getName()
18001095a5dSDimitry Andric << " function optimized for not having CSR.\n");
18101095a5dSDimitry Andric }
18201095a5dSDimitry Andric
183e6d15924SDimitry Andric LLVM_DEBUG(
184e6d15924SDimitry Andric for (unsigned PReg = 1, PRegE = TRI->getNumRegs(); PReg < PRegE; ++PReg) {
18501095a5dSDimitry Andric if (MachineOperand::clobbersPhysReg(&(RegMask[0]), PReg))
186e6d15924SDimitry Andric dbgs() << printReg(PReg, TRI) << " ";
187e6d15924SDimitry Andric }
18801095a5dSDimitry Andric
189e6d15924SDimitry Andric dbgs() << " \n----------------------------------------\n";
190e6d15924SDimitry Andric );
19101095a5dSDimitry Andric
192eb11fae6SDimitry Andric PRUI.storeUpdateRegUsageInfo(F, RegMask);
19301095a5dSDimitry Andric
19401095a5dSDimitry Andric return false;
19501095a5dSDimitry Andric }
196eb11fae6SDimitry Andric
197eb11fae6SDimitry Andric void RegUsageInfoCollector::
computeCalleeSavedRegs(BitVector & SavedRegs,MachineFunction & MF)198eb11fae6SDimitry Andric computeCalleeSavedRegs(BitVector &SavedRegs, MachineFunction &MF) {
199eb11fae6SDimitry Andric const TargetFrameLowering &TFI = *MF.getSubtarget().getFrameLowering();
200eb11fae6SDimitry Andric const TargetRegisterInfo &TRI = *MF.getSubtarget().getRegisterInfo();
201eb11fae6SDimitry Andric
202eb11fae6SDimitry Andric // Target will return the set of registers that it saves/restores as needed.
203eb11fae6SDimitry Andric SavedRegs.clear();
204706b4fc4SDimitry Andric TFI.getCalleeSaves(MF, SavedRegs);
205e6d15924SDimitry Andric if (SavedRegs.none())
206e6d15924SDimitry Andric return;
207eb11fae6SDimitry Andric
208eb11fae6SDimitry Andric // Insert subregs.
209eb11fae6SDimitry Andric const MCPhysReg *CSRegs = TRI.getCalleeSavedRegs(&MF);
210eb11fae6SDimitry Andric for (unsigned i = 0; CSRegs[i]; ++i) {
211e6d15924SDimitry Andric MCPhysReg Reg = CSRegs[i];
212e6d15924SDimitry Andric if (SavedRegs.test(Reg)) {
213e6d15924SDimitry Andric // Save subregisters
2147fa27ce4SDimitry Andric for (MCPhysReg SR : TRI.subregs(Reg))
2157fa27ce4SDimitry Andric SavedRegs.set(SR);
216eb11fae6SDimitry Andric }
217eb11fae6SDimitry Andric }
218d8e91e46SDimitry Andric }
219