brintos

brintos / llvm-project-archived public Read only

0
0
Text · 3.8 KiB · e9d2e9a Raw
120 lines · cpp
1//===- ReduceRegisterDefs.cpp - Specialized Delta Pass --------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// This file implements a function which calls the Generic Delta pass in order10// to reduce uninteresting register uses from the MachineFunction.11//12//===----------------------------------------------------------------------===//13 14#include "ReduceRegisterDefs.h"15#include "llvm/CodeGen/MachineFunction.h"16#include "llvm/CodeGen/MachineModuleInfo.h"17#include "llvm/CodeGen/MachineRegisterInfo.h"18#include "llvm/CodeGen/TargetInstrInfo.h"19 20using namespace llvm;21 22static void removeDefsFromFunction(Oracle &O, MachineFunction &MF) {23  MachineRegisterInfo &MRI = MF.getRegInfo();24  const TargetSubtargetInfo &STI = MF.getSubtarget();25  const TargetInstrInfo *TII = STI.getInstrInfo();26 27  DenseSet<MachineOperand *> KeepDefs;28  DenseSet<TargetInstrInfo::RegSubRegPair> DeleteDefs;29 30  for (MachineBasicBlock &MBB : MF) {31    for (MachineBasicBlock::iterator It = MBB.begin(),32                                     E = MBB.getFirstTerminator();33         It != E;) {34      MachineBasicBlock::iterator InsPt = It;35      MachineInstr &MI = *It;36      ++It;37 38      KeepDefs.clear();39      DeleteDefs.clear();40 41      int NumOperands = MI.getNumOperands();42      int NumRequiredOps = MI.getNumExplicitOperands() +43                           MI.getDesc().implicit_defs().size() +44                           MI.getDesc().implicit_uses().size();45 46      bool HaveDelete = false;47      // Do an initial scan in case the instruction defines the same register48      // multiple times.49      for (int I = NumOperands - 1; I >= 0; --I) {50        MachineOperand &MO = MI.getOperand(I);51        if (!MO.isReg() || !MO.isDef())52          continue;53 54        TargetInstrInfo::RegSubRegPair RegPair(MO.getReg(), MO.getSubReg());55        if (!RegPair.Reg.isVirtual())56          continue;57 58        if (O.shouldKeep())59          KeepDefs.insert(&MO);60        else61          HaveDelete = true;62      }63 64      if (!HaveDelete)65        continue;66 67      bool HaveKeptDef = !KeepDefs.empty();68      for (int I = NumOperands - 1; I >= 0; --I) {69        MachineOperand &MO = MI.getOperand(I);70        if (!MO.isReg() || !MO.isDef())71          continue;72 73        if (KeepDefs.count(&MO))74          continue;75 76        TargetInstrInfo::RegSubRegPair RegPair(MO.getReg(), MO.getSubReg());77        if (!RegPair.Reg.isVirtual())78          continue;79 80        if (!DeleteDefs.insert(RegPair).second)81          continue;82 83        if (MRI.use_empty(RegPair.Reg)) {84          if (I >= NumRequiredOps) {85            // Delete implicit def operands that aren't part of the instruction86            // definition87            MI.removeOperand(I);88          }89 90          continue;91        }92 93        // If we aren't going to delete the instruction, replace it with a dead94        // def.95        if (HaveKeptDef)96          MO.setReg(MRI.cloneVirtualRegister(MO.getReg()));97 98        bool IsGeneric = MRI.getRegClassOrNull(RegPair.Reg) == nullptr;99        unsigned ImpDef = IsGeneric ? TargetOpcode::G_IMPLICIT_DEF100                                    : TargetOpcode::IMPLICIT_DEF;101 102        unsigned OpFlags = getRegState(MO) & ~RegState::Implicit;103        InsPt = BuildMI(MBB, InsPt, DebugLoc(), TII->get(ImpDef))104          .addReg(RegPair.Reg, OpFlags, RegPair.SubReg);105      }106 107      if (!HaveKeptDef)108        MI.eraseFromParent();109    }110  }111}112 113void llvm::reduceRegisterDefsMIRDeltaPass(Oracle &O,114                                          ReducerWorkItem &WorkItem) {115  for (const Function &F : WorkItem.getModule()) {116    if (auto *MF = WorkItem.MMI->getMachineFunction(F))117      removeDefsFromFunction(O, *MF);118  }119}120