14dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//===-- RegisterPressure.h - Dynamic Register Pressure -*- C++ -*-------===//
24dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//
34dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//                     The LLVM Compiler Infrastructure
44dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//
54dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick// This file is distributed under the University of Illinois Open Source
64dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick// License. See LICENSE.TXT for details.
74dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//
84dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//===----------------------------------------------------------------------===//
94dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//
104dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick// This file defines the RegisterPressure class which can be used to track
114dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick// MachineInstr level register pressure.
124dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//
134dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick//===----------------------------------------------------------------------===//
144dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
154dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#ifndef LLVM_CODEGEN_REGISTERPRESSURE_H
164dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#define LLVM_CODEGEN_REGISTERPRESSURE_H
174dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
184dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#include "llvm/CodeGen/SlotIndexes.h"
194dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#include "llvm/Target/TargetRegisterInfo.h"
204dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#include "llvm/ADT/SparseSet.h"
214dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
224dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Tricknamespace llvm {
234dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
244dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickclass LiveIntervals;
254dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickclass RegisterClassInfo;
2655ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trickclass MachineInstr;
274dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
284dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// Base class for register pressure results.
294dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickstruct RegisterPressure {
304dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Map of max reg pressure indexed by pressure set ID, not class ID.
314dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  std::vector<unsigned> MaxSetPressure;
324dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
334dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// List of live in registers.
344dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SmallVector<unsigned,8> LiveInRegs;
354dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SmallVector<unsigned,8> LiveOutRegs;
364dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
374dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Increase register pressure for each pressure set impacted by this register
384dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// class. Normally called by RegPressureTracker, but may be called manually
394dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// to account for live through (global liveness).
404dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void increase(const TargetRegisterClass *RC, const TargetRegisterInfo *TRI);
414dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
424dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Decrease register pressure for each pressure set impacted by this register
434dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// class. This is only useful to account for spilling or rematerialization.
444dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void decrease(const TargetRegisterClass *RC, const TargetRegisterInfo *TRI);
455f887fab35cd71a1e6fcbfa64ae5cbbf43b39807Andrew Trick
465f887fab35cd71a1e6fcbfa64ae5cbbf43b39807Andrew Trick  void dump(const TargetRegisterInfo *TRI);
474dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick};
484dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
494dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// RegisterPressure computed within a region of instructions delimited by
504dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// TopIdx and BottomIdx.  During pressure computation, the maximum pressure per
514dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// register pressure set is increased. Once pressure within a region is fully
524dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// computed, the live-in and live-out sets are recorded.
534dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick///
544dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// This is preferable to RegionPressure when LiveIntervals are available,
554dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// because delimiting regions by SlotIndex is more robust and convenient than
564dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// holding block iterators. The block contents can change without invalidating
574dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// the pressure result.
584dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickstruct IntervalPressure : RegisterPressure {
594dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Record the boundary of the region being tracked.
604dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SlotIndex TopIdx;
614dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SlotIndex BottomIdx;
624dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
634dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void reset();
644dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
654dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void openTop(SlotIndex NextTop);
664dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
674dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void openBottom(SlotIndex PrevBottom);
684dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick};
694dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
704dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// RegisterPressure computed within a region of instructions delimited by
714dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// TopPos and BottomPos. This is a less precise version of IntervalPressure for
724dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// use when LiveIntervals are unavailable.
734dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickstruct RegionPressure : RegisterPressure {
744dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Record the boundary of the region being tracked.
754dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  MachineBasicBlock::const_iterator TopPos;
764dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  MachineBasicBlock::const_iterator BottomPos;
774dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
784dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void reset();
794dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
804dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void openTop(MachineBasicBlock::const_iterator PrevTop);
814dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
824dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void openBottom(MachineBasicBlock::const_iterator PrevBottom);
834dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick};
844dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
8573a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// An element of pressure difference that identifies the pressure set and
8673a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// amount of increase or decrease in units of pressure.
8773a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trickstruct PressureElement {
8873a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  unsigned PSetID;
8973a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  int UnitIncrease;
9073a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick
9173a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  PressureElement(): PSetID(~0U), UnitIncrease(0) {}
9273a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  PressureElement(unsigned id, int inc): PSetID(id), UnitIncrease(inc) {}
9373a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick
9473a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  bool isValid() const { return PSetID != ~0U; }
9573a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick};
9673a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick
9773a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// Store the effects of a change in pressure on things that MI scheduler cares
9873a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// about.
9955ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick///
10073a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// Excess records the value of the largest difference in register units beyond
10155ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick/// the target's pressure limits across the affected pressure sets, where
10255ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick/// largest is defined as the absolute value of the difference. Negative
10355ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick/// ExcessUnits indicates a reduction in pressure that had already exceeded the
10455ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick/// target's limits.
10555ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick///
10673a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// CriticalMax records the largest increase in the tracker's max pressure that
10773a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// exceeds the critical limit for some pressure set determined by the client.
10855ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick///
10973a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// CurrentMax records the largest increase in the tracker's max pressure that
11073a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick/// exceeds the current limit for some pressure set determined by the client.
11155ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trickstruct RegPressureDelta {
11273a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  PressureElement Excess;
11373a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  PressureElement CriticalMax;
11473a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  PressureElement CurrentMax;
11555ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick
11673a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  RegPressureDelta() {}
11755ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick};
11855ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick
1194dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// Track the current register pressure at some position in the instruction
1204dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// stream, and remember the high water mark within the region traversed. This
1214dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// does not automatically consider live-through ranges. The client may
1224dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// independently adjust for global liveness.
1234dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick///
1244dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// Each RegPressureTracker only works within a MachineBasicBlock. Pressure can
1254dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// be tracked across a larger region by storing a RegisterPressure result at
1264dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// each block boundary and explicitly adjusting pressure to account for block
1274dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// live-in and live-out register sets.
1284dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick///
1294dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// RegPressureTracker holds a reference to a RegisterPressure result that it
1304dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// computes incrementally. During downward tracking, P.BottomIdx or P.BottomPos
1314dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// is invalid until it reaches the end of the block or closeRegion() is
1324dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// explicitly called. Similarly, P.TopIdx is invalid during upward
1334dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// tracking. Changing direction has the side effect of closing region, and
1344dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick/// traversing past TopIdx or BottomIdx reopens it.
1354dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickclass RegPressureTracker {
1364dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const MachineFunction     *MF;
1374dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const TargetRegisterInfo  *TRI;
1384dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const RegisterClassInfo   *RCI;
1394dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const MachineRegisterInfo *MRI;
1404dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const LiveIntervals       *LIS;
1414dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1424dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// We currently only allow pressure tracking within a block.
1434dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  const MachineBasicBlock *MBB;
1444dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1454dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Track the max pressure within the region traversed so far.
1464dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  RegisterPressure &P;
1474dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1484dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Run in two modes dependending on whether constructed with IntervalPressure
1494dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// or RegisterPressure. If requireIntervals is false, LIS are ignored.
1504dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  bool RequireIntervals;
1514dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1524dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Register pressure corresponds to liveness before this instruction
1534dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// iterator. It may point to the end of the block rather than an instruction.
1544dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  MachineBasicBlock::const_iterator CurrPos;
1554dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1564dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Pressure map indexed by pressure set ID, not class ID.
1574dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  std::vector<unsigned> CurrSetPressure;
1584dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1594dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// List of live registers.
1604dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SparseSet<unsigned> LivePhysRegs;
1614dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  SparseSet<unsigned, VirtReg2IndexFunctor> LiveVirtRegs;
1624dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1634dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickpublic:
1644dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  RegPressureTracker(IntervalPressure &rp) :
1654dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick    MF(0), TRI(0), RCI(0), LIS(0), MBB(0), P(rp), RequireIntervals(true) {}
1664dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1674dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  RegPressureTracker(RegionPressure &rp) :
1684dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick    MF(0), TRI(0), RCI(0), LIS(0), MBB(0), P(rp), RequireIntervals(false) {}
1694dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1704dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void init(const MachineFunction *mf, const RegisterClassInfo *rci,
1714dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick            const LiveIntervals *lis, const MachineBasicBlock *mbb,
1724dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick            MachineBasicBlock::const_iterator pos);
1734dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1747f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  /// Force liveness of registers. Particularly useful to initialize the
1757f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  /// livein/out state of the tracker before the first call to advance/recede.
1767f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void addLiveRegs(ArrayRef<unsigned> Regs);
1777f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
1787f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  /// Get the MI position corresponding to this register pressure.
1794dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  MachineBasicBlock::const_iterator getPos() const { return CurrPos; }
1804dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1817f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  // Reset the MI position corresponding to the register pressure. This allows
1827f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  // schedulers to move instructions above the RegPressureTracker's
1837f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  // CurrPos. Since the pressure is computed before CurrPos, the iterator
1847f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  // position changes while pressure does not.
1857f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void setPos(MachineBasicBlock::const_iterator Pos) { CurrPos = Pos; }
1867f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
1874dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Recede across the previous instruction.
1884dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  bool recede();
1894dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1904dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Advance across the current instruction.
1914dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  bool advance();
1924dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1934dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Finalize the region boundaries and recored live ins and live outs.
1944dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  void closeRegion();
1954dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
1964dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// Get the resulting register pressure over the traversed region.
1974dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// This result is complete if either advance() or recede() has returned true,
1984dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  /// or if closeRegion() was explicitly invoked.
1994dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick  RegisterPressure &getPressure() { return P; }
2004dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
201ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  /// Get the register set pressure at the current position, which may be less
202ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  /// than the pressure across the traversed region.
203ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  std::vector<unsigned> &getRegSetPressureAtPos() { return CurrSetPressure; }
204ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
2057f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void discoverPhysLiveIn(unsigned Reg);
2067f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void discoverPhysLiveOut(unsigned Reg);
2077f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
2087f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void discoverVirtLiveIn(unsigned Reg);
2097f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void discoverVirtLiveOut(unsigned Reg);
2107f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
2117f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  bool isTopClosed() const;
2127f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  bool isBottomClosed() const;
2137f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
2147f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void closeTop();
2157f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick  void closeBottom();
2167f8ab785af09e4d6e4db07157a5b5aa449b5c3aeAndrew Trick
21755ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// Consider the pressure increase caused by traversing this instruction
21855ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// bottom-up. Find the pressure set with the most change beyond its pressure
21955ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// limit based on the tracker's current pressure, and record the number of
22055ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// excess register units of that pressure set introduced by this instruction.
22155ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  void getMaxUpwardPressureDelta(const MachineInstr *MI,
22273a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                 RegPressureDelta &Delta,
22373a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                 ArrayRef<PressureElement> CriticalPSets,
22473a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                 ArrayRef<unsigned> MaxPressureLimit);
22555ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick
22655ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// Consider the pressure increase caused by traversing this instruction
22755ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// top-down. Find the pressure set with the most change beyond its pressure
22855ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// limit based on the tracker's current pressure, and record the number of
22955ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// excess register units of that pressure set introduced by this instruction.
23055ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  void getMaxDownwardPressureDelta(const MachineInstr *MI,
23173a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                   RegPressureDelta &Delta,
23273a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                   ArrayRef<PressureElement> CriticalPSets,
23373a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                   ArrayRef<unsigned> MaxPressureLimit);
23455ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick
23555ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// Find the pressure set with the most change beyond its pressure limit after
23655ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// traversing this instruction either upward or downward depending on the
23755ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  /// closed end of the current region.
23873a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick  void getMaxPressureDelta(const MachineInstr *MI, RegPressureDelta &Delta,
23973a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                           ArrayRef<PressureElement> CriticalPSets,
24073a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                           ArrayRef<unsigned> MaxPressureLimit) {
24155ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick    if (isTopClosed())
24273a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick      return getMaxDownwardPressureDelta(MI, Delta, CriticalPSets,
24373a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                         MaxPressureLimit);
24424617213ba8e9d1e0f10af33d88285a92304ab95Andrew Trick
24555ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick    assert(isBottomClosed() && "Uninitialized pressure tracker");
24673a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick    return getMaxUpwardPressureDelta(MI, Delta, CriticalPSets,
24773a0d8ecf838a9b333c9865d2a4b72c5768fb49fAndrew Trick                                     MaxPressureLimit);
24855ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick  }
24955ba5dff3c1a723adf302f1124aafde797dbf31aAndrew Trick
250ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  /// Get the pressure of each PSet after traversing this instruction bottom-up.
251ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  void getUpwardPressure(const MachineInstr *MI,
2520eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                         std::vector<unsigned> &PressureResult,
2530eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                         std::vector<unsigned> &MaxPressureResult);
254ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
255ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  /// Get the pressure of each PSet after traversing this instruction top-down.
256ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  void getDownwardPressure(const MachineInstr *MI,
2570eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                           std::vector<unsigned> &PressureResult,
2580eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                           std::vector<unsigned> &MaxPressureResult);
259ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
260ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  void getPressureAfterInst(const MachineInstr *MI,
2610eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                            std::vector<unsigned> &PressureResult,
2620eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick                            std::vector<unsigned> &MaxPressureResult) {
263ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick    if (isTopClosed())
2640eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick      return getUpwardPressure(MI, PressureResult, MaxPressureResult);
265ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
266ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick    assert(isBottomClosed() && "Uninitialized pressure tracker");
2670eb3a3524e9d68642e574780d19c781386ed4469Andrew Trick    return getDownwardPressure(MI, PressureResult, MaxPressureResult);
268ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  }
269ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
2704dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trickprotected:
2712b8d0501b169c3ee81a9af1cb715e1be4d6a079eBenjamin Kramer  void increasePhysRegPressure(ArrayRef<unsigned> Regs);
2722b8d0501b169c3ee81a9af1cb715e1be4d6a079eBenjamin Kramer  void decreasePhysRegPressure(ArrayRef<unsigned> Regs);
2734dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
2742b8d0501b169c3ee81a9af1cb715e1be4d6a079eBenjamin Kramer  void increaseVirtRegPressure(ArrayRef<unsigned> Regs);
2752b8d0501b169c3ee81a9af1cb715e1be4d6a079eBenjamin Kramer  void decreaseVirtRegPressure(ArrayRef<unsigned> Regs);
276ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick
277ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  void bumpUpwardPressure(const MachineInstr *MI);
278ba17293a8827a7e0e390b0a1d6075148a58d9eddAndrew Trick  void bumpDownwardPressure(const MachineInstr *MI);
2794dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick};
2804dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick} // end namespace llvm
2814dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick
2824dfeef100d940a0c1ca22055dcb29b02a4848f65Andrew Trick#endif
283