1 //===-- llvm/CodeGen/RenderMachineFunction.h - MF->HTML -*- C++ -*---------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 //===----------------------------------------------------------------------===//
12 #ifndef LLVM_CODEGEN_RENDERMACHINEFUNCTION_H
13 #define LLVM_CODEGEN_RENDERMACHINEFUNCTION_H
15 #include "llvm/CodeGen/LiveInterval.h"
16 #include "llvm/CodeGen/MachineFunctionPass.h"
17 #include "llvm/CodeGen/SlotIndexes.h"
18 #include "llvm/Target/TargetRegisterInfo.h"
30 class MachineRegisterInfo;
31 class TargetRegisterClass;
32 class TargetRegisterInfo;
35 /// \brief Provide extra information about the physical and virtual registers
36 /// in the function being compiled.
37 class TargetRegisterExtraInfo {
39 TargetRegisterExtraInfo();
41 /// \brief Set up TargetRegisterExtraInfo with pointers to necessary
42 /// sources of information.
43 void setup(MachineFunction *mf, MachineRegisterInfo *mri,
44 const TargetRegisterInfo *tri, LiveIntervals *lis);
46 /// \brief Recompute tables for changed function.
49 /// \brief Free all tables in TargetRegisterExtraInfo.
52 /// \brief Maximum number of registers from trc which alias reg.
53 unsigned getWorst(unsigned reg, const TargetRegisterClass *trc) const;
55 /// \brief Returns the number of allocable registers in trc.
56 unsigned getCapacity(const TargetRegisterClass *trc) const;
58 /// \brief Return the number of registers of class trc that may be
60 unsigned getPressureAtSlot(const TargetRegisterClass *trc,
63 /// \brief Return true if the number of registers of type trc that may be
64 /// needed at slot i is greater than the capacity of trc.
65 bool classOverCapacityAtSlot(const TargetRegisterClass *trc,
71 MachineRegisterInfo *mri;
72 const TargetRegisterInfo *tri;
75 typedef std::map<const TargetRegisterClass*, unsigned> WorstMapLine;
76 typedef std::map<const TargetRegisterClass*, WorstMapLine> VRWorstMap;
79 typedef std::map<unsigned, WorstMapLine> PRWorstMap;
82 typedef std::map<const TargetRegisterClass*, unsigned> CapacityMap;
83 CapacityMap capacityMap;
85 typedef std::map<const TargetRegisterClass*, unsigned> PressureMapLine;
86 typedef std::map<SlotIndex, PressureMapLine> PressureMap;
87 PressureMap pressureMap;
91 /// \brief Initialise the 'worst' table.
94 /// \brief Initialise the 'capacity' table.
97 /// \brief Initialise/Reset the 'pressure' and live states tables.
98 void resetPressureAndLiveStates();
101 /// \brief Helper class to process rendering options. Tries to be as lazy as
103 class MFRenderingOptions {
106 struct RegClassComp {
107 bool operator()(const TargetRegisterClass *trc1,
108 const TargetRegisterClass *trc2) const {
109 std::string trc1Name(trc1->getName()), trc2Name(trc2->getName());
110 return std::lexicographical_compare(trc1Name.begin(), trc1Name.end(),
111 trc2Name.begin(), trc2Name.end());
115 typedef std::set<const TargetRegisterClass*, RegClassComp> RegClassSet;
117 struct IntervalComp {
118 bool operator()(const LiveInterval *li1, const LiveInterval *li2) const {
119 return li1->reg < li2->reg;
123 typedef std::set<const LiveInterval*, IntervalComp> IntervalSet;
125 /// Initialise the rendering options.
126 void setup(MachineFunction *mf, const TargetRegisterInfo *tri,
129 /// Clear translations of options to the current function.
132 /// Reset any options computed for this specific rendering.
133 void resetRenderSpecificOptions();
135 /// Should we render the current function.
136 bool shouldRenderCurrentMachineFunction() const;
138 /// Return the set of register classes to render pressure for.
139 const RegClassSet& regClasses() const;
141 /// Return the set of live intervals to render liveness for.
142 const IntervalSet& intervals() const;
144 /// Render indexes which are not associated with instructions / MBB starts.
145 bool renderEmptyIndexes() const;
147 /// Return whether or not to render using SVG for fancy vertical text.
148 bool fancyVerticals() const;
152 static bool renderingOptionsProcessed;
153 static std::set<std::string> mfNamesToRender;
154 static bool renderAllMFs;
156 static std::set<std::string> classNamesToRender;
157 static bool renderAllClasses;
160 static std::set<std::pair<unsigned, unsigned> > intervalNumsToRender;
161 typedef enum { ExplicitOnly = 0,
162 VirtPlusExplicit = 1,
163 PhysPlusExplicit = 2,
165 IntervalTypesToRender;
166 static unsigned intervalTypesToRender;
168 template <typename OutputItr>
169 static void splitComaSeperatedList(const std::string &s, OutputItr outItr);
171 static void processOptions();
173 static void processFuncNames();
174 static void processRegClassNames();
175 static void processIntervalNumbers();
177 static void processIntervalRange(const std::string &intervalRangeStr);
180 const TargetRegisterInfo *tri;
183 mutable bool regClassesTranslatedToCurrentFunction;
184 mutable RegClassSet regClassSet;
186 mutable bool intervalsTranslatedToCurrentFunction;
187 mutable IntervalSet intervalSet;
189 void translateRegClassNamesToCurrentFunction() const;
191 void translateIntervalNumbersToCurrentFunction() const;
194 /// \brief Render MachineFunction objects and related information to a HTML
196 class RenderMachineFunction : public MachineFunctionPass {
200 RenderMachineFunction() : MachineFunctionPass(&ID) {}
202 virtual void getAnalysisUsage(AnalysisUsage &au) const;
204 virtual bool runOnMachineFunction(MachineFunction &fn);
206 virtual void releaseMemory();
208 /// \brief Render this machine function to HTML.
210 /// @param renderContextStr This parameter will be included in the top of
211 /// the html file to explain where (in the
212 /// codegen pipeline) this function was rendered
213 /// from. Set it to something like
214 /// "Pre-register-allocation".
215 /// @param vrm If non-null the VRM will be queried to determine
216 /// whether a virtual register was allocated to a
217 /// physical register or spilled.
218 /// @param renderFilePrefix This string will be appended to the function
219 /// name (before the output file suffix) to enable
220 /// multiple renderings from the same function.
221 void renderMachineFunction(const char *renderContextStr,
222 const VirtRegMap *vrm = 0,
223 const char *renderSuffix = 0);
228 template <typename OStream>
229 friend OStream& operator<<(OStream &os, const Spacer &s);
235 MachineRegisterInfo *mri;
236 const TargetRegisterInfo *tri;
239 const VirtRegMap *vrm;
241 TargetRegisterExtraInfo trei;
242 MFRenderingOptions ro;
245 typedef enum { Dead, Defined, Used, AliveReg, AliveStack } LiveState;
246 LiveState getLiveStateAt(const LiveInterval *li, SlotIndex i) const;
248 typedef enum { Zero, Low, High } PressureState;
249 PressureState getPressureStateAt(const TargetRegisterClass *trc,
252 // ---------- Rendering methods ----------
254 /// For inserting spaces when pretty printing.
257 explicit Spacer(unsigned numSpaces) : ns(numSpaces) {}
258 Spacer operator+(const Spacer &o) const { return Spacer(ns + o.ns); }
259 template <typename OStream> void print(OStream &os) const;
264 Spacer s(unsigned ns) const;
266 template <typename Iterator>
267 std::string escapeChars(Iterator sBegin, Iterator sEnd) const;
269 /// \brief Render a machine instruction.
270 template <typename OStream>
271 void renderMachineInstr(OStream &os,
272 const MachineInstr *mi) const;
274 /// \brief Render vertical text.
275 template <typename OStream, typename T>
276 void renderVertical(const Spacer &indent,
280 /// \brief Insert CSS layout info.
281 template <typename OStream>
282 void insertCSS(const Spacer &indent,
285 /// \brief Render a brief summary of the function (including rendering
287 template <typename OStream>
288 void renderFunctionSummary(const Spacer &indent,
290 const char * const renderContextStr) const;
292 /// \brief Render a legend for the pressure table.
293 template <typename OStream>
294 void renderPressureTableLegend(const Spacer &indent,
297 /// \brief Render a consecutive set of HTML cells of the same class using
298 /// the colspan attribute for run-length encoding.
299 template <typename OStream, typename CellType>
300 void renderCellsWithRLE(
301 const Spacer &indent, OStream &os,
302 const std::pair<CellType, unsigned> &rleAccumulator,
303 const std::map<CellType, std::string> &cellTypeStrs) const;
305 /// \brief Render code listing, potentially with register pressure
306 /// and live intervals shown alongside.
307 template <typename OStream>
308 void renderCodeTablePlusPI(const Spacer &indent,
311 /// \brief Render warnings about the machine function, or weird rendering
312 /// parameter combinations (e.g. rendering specified live intervals
313 /// over more than one machine function).
314 template <typename OStream>
315 void renderWarnings(const Spacer &indent,
318 /// \brief Render the HTML page representing the MachineFunction.
319 template <typename OStream>
320 void renderFunctionPage(OStream &os,
321 const char * const renderContextStr) const;
323 std::string escapeChars(const std::string &s) const;
327 #endif /* LLVM_CODEGEN_RENDERMACHINEFUNCTION_H */