LLVM  6.0.0svn
Legalizer.cpp
Go to the documentation of this file.
1 //===-- llvm/CodeGen/GlobalISel/Legalizer.cpp -----------------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 /// \file This file implements the LegalizerHelper class to legalize individual
11 /// instructions and the LegalizePass wrapper pass for the primary
12 /// legalization.
13 //
14 //===----------------------------------------------------------------------===//
15 
18 #include "llvm/ADT/SetVector.h"
28 #include "llvm/Support/Debug.h"
29 
30 #include <iterator>
31 
32 #define DEBUG_TYPE "legalizer"
33 
34 using namespace llvm;
35 
36 char Legalizer::ID = 0;
38  "Legalize the Machine IR a function's Machine IR", false,
39  false)
42  "Legalize the Machine IR a function's Machine IR", false,
43  false)
44 
45 Legalizer::Legalizer() : MachineFunctionPass(ID) {
47 }
48 
52 }
53 
54 void Legalizer::init(MachineFunction &MF) {
55 }
56 
57 static bool isArtifact(const MachineInstr &MI) {
58  switch (MI.getOpcode()) {
59  default:
60  return false;
61  case TargetOpcode::G_TRUNC:
62  case TargetOpcode::G_ZEXT:
63  case TargetOpcode::G_ANYEXT:
64  case TargetOpcode::G_SEXT:
65  case TargetOpcode::G_MERGE_VALUES:
66  case TargetOpcode::G_UNMERGE_VALUES:
67  return true;
68  }
69 }
70 
72  // If the ISel pipeline failed, do not bother running that pass.
73  if (MF.getProperties().hasProperty(
75  return false;
76  DEBUG(dbgs() << "Legalize Machine IR for: " << MF.getName() << '\n');
77  init(MF);
78  const TargetPassConfig &TPC = getAnalysis<TargetPassConfig>();
79  MachineOptimizationRemarkEmitter MORE(MF, /*MBFI=*/nullptr);
80  LegalizerHelper Helper(MF);
81 
82  const size_t NumBlocks = MF.size();
84 
85  // Populate Insts
86  GISelWorkList<256> InstList;
87  GISelWorkList<128> ArtifactList;
89  // Perform legalization bottom up so we can DCE as we legalize.
90  // Traverse BB in RPOT and within each basic block, add insts top down,
91  // so when we pop_back_val in the legalization process, we traverse bottom-up.
92  for (auto *MBB : RPOT) {
93  if (MBB->empty())
94  continue;
95  for (MachineInstr &MI : *MBB) {
96  // Only legalize pre-isel generic instructions: others don't have types
97  // and are assumed to be legal.
98  if (!isPreISelGenericOpcode(MI.getOpcode()))
99  continue;
100  if (isArtifact(MI))
101  ArtifactList.insert(&MI);
102  else
103  InstList.insert(&MI);
104  }
105  }
107  // Only legalize pre-isel generic instructions.
108  // Legalization process could generate Target specific pseudo
109  // instructions with generic types. Don't record them
110  if (isPreISelGenericOpcode(MI->getOpcode())) {
111  if (isArtifact(*MI))
112  ArtifactList.insert(MI);
113  else
114  InstList.insert(MI);
115  }
116  DEBUG(dbgs() << ".. .. New MI: " << *MI;);
117  });
118  const LegalizerInfo &LInfo(Helper.getLegalizerInfo());
119  LegalizationArtifactCombiner ArtCombiner(Helper.MIRBuilder, MF.getRegInfo(), LInfo);
120  auto RemoveDeadInstFromLists = [&InstList,
121  &ArtifactList](MachineInstr *DeadMI) {
122  InstList.remove(DeadMI);
123  ArtifactList.remove(DeadMI);
124  };
125  bool Changed = false;
126  do {
127  while (!InstList.empty()) {
128  MachineInstr &MI = *InstList.pop_back_val();
129  assert(isPreISelGenericOpcode(MI.getOpcode()) && "Expecting generic opcode");
130  if (isTriviallyDead(MI, MRI)) {
131  DEBUG(dbgs() << MI << "Is dead; erasing.\n");
133  continue;
134  }
135 
136  // Do the legalization for this instruction.
137  auto Res = Helper.legalizeInstrStep(MI);
138  // Error out if we couldn't legalize this instruction. We may want to
139  // fall back to DAG ISel instead in the future.
142  reportGISelFailure(MF, TPC, MORE, "gisel-legalize",
143  "unable to legalize instruction", MI);
144  return false;
145  }
146  Changed |= Res == LegalizerHelper::Legalized;
147  }
148  while (!ArtifactList.empty()) {
149  MachineInstr &MI = *ArtifactList.pop_back_val();
150  assert(isPreISelGenericOpcode(MI.getOpcode()) && "Expecting generic opcode");
151  if (isTriviallyDead(MI, MRI)) {
152  DEBUG(dbgs() << MI << "Is dead; erasing.\n");
153  RemoveDeadInstFromLists(&MI);
155  continue;
156  }
157  SmallVector<MachineInstr *, 4> DeadInstructions;
158  if (ArtCombiner.tryCombineInstruction(MI, DeadInstructions)) {
159  for (auto *DeadMI : DeadInstructions) {
160  DEBUG(dbgs() << ".. Erasing Dead Instruction " << *DeadMI);
161  RemoveDeadInstFromLists(DeadMI);
162  DeadMI->eraseFromParentAndMarkDBGValuesForRemoval();
163  }
164  Changed = true;
165  continue;
166  }
167  // If this was not an artifact (that could be combined away), this might
168  // need special handling. Add it to InstList, so when it's processed
169  // there, it has to be legal or specially handled.
170  else
171  InstList.insert(&MI);
172  }
173  } while (!InstList.empty());
174 
175  // For now don't support if new blocks are inserted - we would need to fix the
176  // outerloop for that.
177  if (MF.size() != NumBlocks) {
178  MachineOptimizationRemarkMissed R("gisel-legalize", "GISelFailure",
179  MF.getFunction()->getSubprogram(),
180  /*MBB=*/nullptr);
181  R << "inserting blocks is not supported yet";
182  reportGISelFailure(MF, TPC, MORE, R);
183  return false;
184  }
185 
186  return Changed;
187 }
const LegalizerInfo & getLegalizerInfo() const
Expose LegalizerInfo so the clients can re-use.
MachineIRBuilder MIRBuilder
Expose MIRBuilder so clients can set their own RecordInsertInstruction functions. ...
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
Compute iterated dominance frontiers using a linear time algorithm.
Definition: AllocatorList.h:24
const MachineFunctionProperties & getProperties() const
Get the function properties.
unsigned size() const
bool empty() const
Definition: GISelWorkList.h:33
void remove(MachineInstr *I)
Remove - remove I from the worklist if it exists.
Definition: GISelWorkList.h:46
INITIALIZE_PASS_BEGIN(Legalizer, DEBUG_TYPE, "Legalize the Machine IR a function's Machine IR", false, false) INITIALIZE_PASS_END(Legalizer
AnalysisUsage & addRequired()
#define INITIALIZE_PASS_DEPENDENCY(depName)
Definition: PassSupport.h:51
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
Definition: MachineInstr.h:290
Target-Independent Code Generator Pass Configuration Options.
void eraseFromParentAndMarkDBGValuesForRemoval()
Unlink &#39;this&#39; from the containing basic block and delete it.
void recordInsertions(std::function< void(MachineInstr *)> InsertedInstr)
COFF::MachineTypes Machine
Definition: COFFYAML.cpp:363
StringRef getName() const
getName - Return the name of the corresponding LLVM function.
===- MachineOptimizationRemarkEmitter.h - Opt Diagnostics -*- C++ -*-—===//
unsigned const MachineRegisterInfo * MRI
LegalizeResult legalizeInstrStep(MachineInstr &MI)
Replace MI by a sequence of legal instructions that can implement the same operation.
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - Subclasses that override getAnalysisUsage must call this.
DISubprogram * getSubprogram() const
Get the attached subprogram.
Definition: Metadata.cpp:1497
Represent the analysis usage information of a pass.
bool runOnMachineFunction(MachineFunction &MF) override
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...
Definition: Legalizer.cpp:71
Some kind of error has occurred and we could not legalize this instruction.
Legalize the Machine IR a function s Machine IR
Definition: Legalizer.cpp:41
INITIALIZE_PASS_END(RegBankSelect, DEBUG_TYPE, "Assign register bank of generic virtual registers", false, false) RegBankSelect
The optimization diagnostic interface.
#define MORE()
Definition: regcomp.c:256
MachineInstr * pop_back_val()
Definition: GISelWorkList.h:56
void insert(MachineInstr *I)
Add - Add the specified instruction to the worklist if it isn&#39;t already in it.
Definition: GISelWorkList.h:39
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition: Debug.cpp:132
static char ID
Definition: Legalizer.h:33
MachineRegisterInfo - Keep track of information for virtual and physical registers, including vreg register classes, use/def chains for registers, etc.
bool isTriviallyDead(const MachineInstr &MI, const MachineRegisterInfo &MRI)
Check whether an instruction MI is dead: it only defines dead virtual registers, and doesn&#39;t have oth...
Definition: Utils.cpp:59
Representation of each machine instruction.
Definition: MachineInstr.h:59
Instruction has been legalized and the MachineFunction changed.
#define DEBUG_TYPE
Definition: Legalizer.cpp:32
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
static bool isArtifact(const MachineInstr &MI)
Definition: Legalizer.cpp:57
void initializeLegalizerPass(PassRegistry &)
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - This function should be overriden by passes that need analysis information to do t...
Definition: Legalizer.cpp:49
Diagnostic information for missed-optimization remarks.
const Function * getFunction() const
getFunction - Return the LLVM function that this machine code represents
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
bool hasProperty(Property P) const
bool isPreISelGenericOpcode(unsigned Opcode)
Check whether the given Opcode is a generic opcode that is not supposed to appear after ISel...
Definition: TargetOpcodes.h:31
#define DEBUG(X)
Definition: Debug.h:118
print Print MemDeps of function
IRTranslator LLVM IR MI
void reportGISelFailure(MachineFunction &MF, const TargetPassConfig &TPC, MachineOptimizationRemarkEmitter &MORE, MachineOptimizationRemarkMissed &R)
Report an ISel error as a missed optimization remark to the LLVMContext&#39;s diagnostic stream...
Definition: Utils.cpp:80