Counter Strike : Global Offensive Source Code
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

165 lines
5.9 KiB

  1. //===-- RegAllocPBQP.h ------------------------------------------*- C++ -*-===//
  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. // This file defines the PBQPBuilder interface, for classes which build PBQP
  11. // instances to represent register allocation problems, and the RegAllocPBQP
  12. // interface.
  13. //
  14. //===----------------------------------------------------------------------===//
  15. #ifndef LLVM_CODEGEN_REGALLOCPBQP_H
  16. #define LLVM_CODEGEN_REGALLOCPBQP_H
  17. #include "llvm/ADT/DenseMap.h"
  18. #include "llvm/CodeGen/MachineFunctionPass.h"
  19. #include "llvm/CodeGen/PBQP/Graph.h"
  20. #include "llvm/CodeGen/PBQP/Solution.h"
  21. #include <map>
  22. #include <set>
  23. namespace llvm {
  24. class LiveIntervals;
  25. class MachineFunction;
  26. class MachineLoopInfo;
  27. class TargetRegisterInfo;
  28. template<class T> class OwningPtr;
  29. /// This class wraps up a PBQP instance representing a register allocation
  30. /// problem, plus the structures necessary to map back from the PBQP solution
  31. /// to a register allocation solution. (i.e. The PBQP-node <--> vreg map,
  32. /// and the PBQP option <--> storage location map).
  33. class PBQPRAProblem {
  34. public:
  35. typedef SmallVector<unsigned, 16> AllowedSet;
  36. PBQP::Graph& getGraph() { return graph; }
  37. const PBQP::Graph& getGraph() const { return graph; }
  38. /// Record the mapping between the given virtual register and PBQP node,
  39. /// and the set of allowed pregs for the vreg.
  40. ///
  41. /// If you are extending
  42. /// PBQPBuilder you are unlikely to need this: Nodes and options for all
  43. /// vregs will already have been set up for you by the base class.
  44. template <typename AllowedRegsItr>
  45. void recordVReg(unsigned vreg, PBQP::Graph::NodeItr node,
  46. AllowedRegsItr arBegin, AllowedRegsItr arEnd) {
  47. assert(node2VReg.find(node) == node2VReg.end() && "Re-mapping node.");
  48. assert(vreg2Node.find(vreg) == vreg2Node.end() && "Re-mapping vreg.");
  49. assert(allowedSets[vreg].empty() && "vreg already has pregs.");
  50. node2VReg[node] = vreg;
  51. vreg2Node[vreg] = node;
  52. std::copy(arBegin, arEnd, std::back_inserter(allowedSets[vreg]));
  53. }
  54. /// Get the virtual register corresponding to the given PBQP node.
  55. unsigned getVRegForNode(PBQP::Graph::ConstNodeItr node) const;
  56. /// Get the PBQP node corresponding to the given virtual register.
  57. PBQP::Graph::NodeItr getNodeForVReg(unsigned vreg) const;
  58. /// Returns true if the given PBQP option represents a physical register,
  59. /// false otherwise.
  60. bool isPRegOption(unsigned vreg, unsigned option) const {
  61. // At present we only have spills or pregs, so anything that's not a
  62. // spill is a preg. (This might be extended one day to support remat).
  63. return !isSpillOption(vreg, option);
  64. }
  65. /// Returns true if the given PBQP option represents spilling, false
  66. /// otherwise.
  67. bool isSpillOption(unsigned vreg, unsigned option) const {
  68. // We hardcode option zero as the spill option.
  69. return option == 0;
  70. }
  71. /// Returns the allowed set for the given virtual register.
  72. const AllowedSet& getAllowedSet(unsigned vreg) const;
  73. /// Get PReg for option.
  74. unsigned getPRegForOption(unsigned vreg, unsigned option) const;
  75. private:
  76. typedef std::map<PBQP::Graph::ConstNodeItr, unsigned,
  77. PBQP::NodeItrComparator> Node2VReg;
  78. typedef DenseMap<unsigned, PBQP::Graph::NodeItr> VReg2Node;
  79. typedef DenseMap<unsigned, AllowedSet> AllowedSetMap;
  80. PBQP::Graph graph;
  81. Node2VReg node2VReg;
  82. VReg2Node vreg2Node;
  83. AllowedSetMap allowedSets;
  84. };
  85. /// Builds PBQP instances to represent register allocation problems. Includes
  86. /// spill, interference and coalescing costs by default. You can extend this
  87. /// class to support additional constraints for your architecture.
  88. class PBQPBuilder {
  89. private:
  90. PBQPBuilder(const PBQPBuilder&) LLVM_DELETED_FUNCTION;
  91. void operator=(const PBQPBuilder&) LLVM_DELETED_FUNCTION;
  92. public:
  93. typedef std::set<unsigned> RegSet;
  94. /// Default constructor.
  95. PBQPBuilder() {}
  96. /// Clean up a PBQPBuilder.
  97. virtual ~PBQPBuilder() {}
  98. /// Build a PBQP instance to represent the register allocation problem for
  99. /// the given MachineFunction.
  100. virtual PBQPRAProblem *build(MachineFunction *mf, const LiveIntervals *lis,
  101. const MachineLoopInfo *loopInfo,
  102. const RegSet &vregs);
  103. private:
  104. void addSpillCosts(PBQP::Vector &costVec, PBQP::PBQPNum spillCost);
  105. void addInterferenceCosts(PBQP::Matrix &costMat,
  106. const PBQPRAProblem::AllowedSet &vr1Allowed,
  107. const PBQPRAProblem::AllowedSet &vr2Allowed,
  108. const TargetRegisterInfo *tri);
  109. };
  110. /// Extended builder which adds coalescing constraints to a problem.
  111. class PBQPBuilderWithCoalescing : public PBQPBuilder {
  112. public:
  113. /// Build a PBQP instance to represent the register allocation problem for
  114. /// the given MachineFunction.
  115. virtual PBQPRAProblem *build(MachineFunction *mf, const LiveIntervals *lis,
  116. const MachineLoopInfo *loopInfo,
  117. const RegSet &vregs);
  118. private:
  119. void addPhysRegCoalesce(PBQP::Vector &costVec, unsigned pregOption,
  120. PBQP::PBQPNum benefit);
  121. void addVirtRegCoalesce(PBQP::Matrix &costMat,
  122. const PBQPRAProblem::AllowedSet &vr1Allowed,
  123. const PBQPRAProblem::AllowedSet &vr2Allowed,
  124. PBQP::PBQPNum benefit);
  125. };
  126. FunctionPass* createPBQPRegisterAllocator(OwningPtr<PBQPBuilder> &builder,
  127. char *customPassID=0);
  128. }
  129. #endif /* LLVM_CODEGEN_REGALLOCPBQP_H */