RenderMachineFunction.h [plain text]
#ifndef LLVM_CODEGEN_RENDERMACHINEFUNCTION_H
#define LLVM_CODEGEN_RENDERMACHINEFUNCTION_H
#include "llvm/CodeGen/LiveInterval.h"
#include "llvm/CodeGen/MachineFunctionPass.h"
#include "llvm/CodeGen/SlotIndexes.h"
#include "llvm/Target/TargetRegisterInfo.h"
#include <algorithm>
#include <map>
#include <set>
#include <string>
namespace llvm {
class LiveInterval;
class LiveIntervals;
class MachineInstr;
class MachineRegisterInfo;
class RenderMachineFunction;
class TargetRegisterClass;
class TargetRegisterInfo;
class VirtRegMap;
class raw_ostream;
class MFRenderingOptions {
public:
struct RegClassComp {
bool operator()(const TargetRegisterClass *trc1,
const TargetRegisterClass *trc2) const {
std::string trc1Name(trc1->getName()), trc2Name(trc2->getName());
return std::lexicographical_compare(trc1Name.begin(), trc1Name.end(),
trc2Name.begin(), trc2Name.end());
}
};
typedef std::set<const TargetRegisterClass*, RegClassComp> RegClassSet;
struct IntervalComp {
bool operator()(const LiveInterval *li1, const LiveInterval *li2) const {
return li1->reg < li2->reg;
}
};
typedef std::set<const LiveInterval*, IntervalComp> IntervalSet;
void setup(MachineFunction *mf, const TargetRegisterInfo *tri,
LiveIntervals *lis, const RenderMachineFunction *rmf);
void clear();
void resetRenderSpecificOptions();
bool shouldRenderCurrentMachineFunction() const;
const RegClassSet& regClasses() const;
const IntervalSet& intervals() const;
bool renderEmptyIndexes() const;
bool fancyVerticals() const;
private:
static bool renderingOptionsProcessed;
static std::set<std::string> mfNamesToRender;
static bool renderAllMFs;
static std::set<std::string> classNamesToRender;
static bool renderAllClasses;
static std::set<std::pair<unsigned, unsigned> > intervalNumsToRender;
typedef enum { ExplicitOnly = 0,
AllPhys = 1,
VirtNoSpills = 2,
VirtSpills = 4,
AllVirt = 6,
All = 7 }
IntervalTypesToRender;
static unsigned intervalTypesToRender;
template <typename OutputItr>
static void splitComaSeperatedList(const std::string &s, OutputItr outItr);
static void processOptions();
static void processFuncNames();
static void processRegClassNames();
static void processIntervalNumbers();
static void processIntervalRange(const std::string &intervalRangeStr);
MachineFunction *mf;
const TargetRegisterInfo *tri;
LiveIntervals *lis;
const RenderMachineFunction *rmf;
mutable bool regClassesTranslatedToCurrentFunction;
mutable RegClassSet regClassSet;
mutable bool intervalsTranslatedToCurrentFunction;
mutable IntervalSet intervalSet;
void translateRegClassNamesToCurrentFunction() const;
void translateIntervalNumbersToCurrentFunction() const;
};
class TargetRegisterExtraInfo {
public:
TargetRegisterExtraInfo();
void setup(MachineFunction *mf, MachineRegisterInfo *mri,
const TargetRegisterInfo *tri, LiveIntervals *lis);
void reset();
void clear();
unsigned getWorst(unsigned reg, const TargetRegisterClass *trc) const;
unsigned getCapacity(const TargetRegisterClass *trc) const;
unsigned getPressureAtSlot(const TargetRegisterClass *trc,
SlotIndex i) const;
bool classOverCapacityAtSlot(const TargetRegisterClass *trc,
SlotIndex i) const;
private:
MachineFunction *mf;
MachineRegisterInfo *mri;
const TargetRegisterInfo *tri;
LiveIntervals *lis;
typedef std::map<const TargetRegisterClass*, unsigned> WorstMapLine;
typedef std::map<const TargetRegisterClass*, WorstMapLine> VRWorstMap;
VRWorstMap vrWorst;
typedef std::map<unsigned, WorstMapLine> PRWorstMap;
PRWorstMap prWorst;
typedef std::map<const TargetRegisterClass*, unsigned> CapacityMap;
CapacityMap capacityMap;
typedef std::map<const TargetRegisterClass*, unsigned> PressureMapLine;
typedef std::map<SlotIndex, PressureMapLine> PressureMap;
PressureMap pressureMap;
bool mapsPopulated;
void initWorst();
void initCapacity();
void resetPressureAndLiveStates();
};
class RenderMachineFunction : public MachineFunctionPass {
public:
static char ID;
RenderMachineFunction() : MachineFunctionPass(ID) {
initializeRenderMachineFunctionPass(*PassRegistry::getPassRegistry());
}
virtual void getAnalysisUsage(AnalysisUsage &au) const;
virtual bool runOnMachineFunction(MachineFunction &fn);
virtual void releaseMemory();
void rememberUseDefs(const LiveInterval *li);
void rememberSpills(const LiveInterval *li,
const std::vector<LiveInterval*> &spills);
bool isSpill(const LiveInterval *li) const;
void renderMachineFunction(const char *renderContextStr,
const VirtRegMap *vrm = 0,
const char *renderSuffix = 0);
private:
class Spacer;
friend raw_ostream& operator<<(raw_ostream &os, const Spacer &s);
std::string fqn;
MachineFunction *mf;
MachineRegisterInfo *mri;
const TargetRegisterInfo *tri;
LiveIntervals *lis;
SlotIndexes *sis;
const VirtRegMap *vrm;
TargetRegisterExtraInfo trei;
MFRenderingOptions ro;
typedef enum { Dead, Defined, Used, AliveReg, AliveStack } LiveState;
LiveState getLiveStateAt(const LiveInterval *li, SlotIndex i) const;
typedef enum { Zero, Low, High } PressureState;
PressureState getPressureStateAt(const TargetRegisterClass *trc,
SlotIndex i) const;
typedef std::map<const LiveInterval*, std::set<const LiveInterval*> >
SpillIntervals;
SpillIntervals spillIntervals;
typedef std::map<const LiveInterval*, const LiveInterval*> SpillForMap;
SpillForMap spillFor;
typedef std::set<SlotIndex> SlotSet;
typedef std::map<const LiveInterval*, SlotSet> UseDefs;
UseDefs useDefs;
class Spacer {
public:
explicit Spacer(unsigned numSpaces) : ns(numSpaces) {}
Spacer operator+(const Spacer &o) const { return Spacer(ns + o.ns); }
void print(raw_ostream &os) const;
private:
unsigned ns;
};
Spacer s(unsigned ns) const;
template <typename Iterator>
std::string escapeChars(Iterator sBegin, Iterator sEnd) const;
void renderMachineInstr(raw_ostream &os,
const MachineInstr *mi) const;
template <typename T>
void renderVertical(const Spacer &indent,
raw_ostream &os,
const T &t) const;
void insertCSS(const Spacer &indent,
raw_ostream &os) const;
void renderFunctionSummary(const Spacer &indent,
raw_ostream &os,
const char * const renderContextStr) const;
void renderPressureTableLegend(const Spacer &indent,
raw_ostream &os) const;
template <typename CellType>
void renderCellsWithRLE(
const Spacer &indent, raw_ostream &os,
const std::pair<CellType, unsigned> &rleAccumulator,
const std::map<CellType, std::string> &cellTypeStrs) const;
void renderCodeTablePlusPI(const Spacer &indent,
raw_ostream &os) const;
void renderFunctionPage(raw_ostream &os,
const char * const renderContextStr) const;
std::string escapeChars(const std::string &s) const;
};
}
#endif