]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/include/llvm/MCA/HardwareUnits/RetireControlUnit.h
Merge llvm, clang, compiler-rt, libc++, libunwind, lld, lldb and openmp
[FreeBSD/FreeBSD.git] / contrib / llvm / include / llvm / MCA / HardwareUnits / RetireControlUnit.h
1 //===---------------------- RetireControlUnit.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 /// \file
10 ///
11 /// This file simulates the hardware responsible for retiring instructions.
12 ///
13 //===----------------------------------------------------------------------===//
14
15 #ifndef LLVM_MCA_RETIRE_CONTROL_UNIT_H
16 #define LLVM_MCA_RETIRE_CONTROL_UNIT_H
17
18 #include "llvm/MC/MCSchedule.h"
19 #include "llvm/MCA/HardwareUnits/HardwareUnit.h"
20 #include "llvm/MCA/Instruction.h"
21 #include <vector>
22
23 namespace llvm {
24 namespace mca {
25
26 /// This class tracks which instructions are in-flight (i.e., dispatched but not
27 /// retired) in the OoO backend.
28 //
29 /// This class checks on every cycle if/which instructions can be retired.
30 /// Instructions are retired in program order.
31 /// In the event of an instruction being retired, the pipeline that owns
32 /// this RetireControlUnit (RCU) gets notified.
33 ///
34 /// On instruction retired, register updates are all architecturally
35 /// committed, and any physicall registers previously allocated for the
36 /// retired instruction are freed.
37 struct RetireControlUnit : public HardwareUnit {
38   // A RUToken is created by the RCU for every instruction dispatched to the
39   // schedulers.  These "tokens" are managed by the RCU in its token Queue.
40   //
41   // On every cycle ('cycleEvent'), the RCU iterates through the token queue
42   // looking for any token with its 'Executed' flag set.  If a token has that
43   // flag set, then the instruction has reached the write-back stage and will
44   // be retired by the RCU.
45   //
46   // 'NumSlots' represents the number of entries consumed by the instruction in
47   // the reorder buffer. Those entries will become available again once the
48   // instruction is retired.
49   //
50   // Note that the size of the reorder buffer is defined by the scheduling
51   // model via field 'NumMicroOpBufferSize'.
52   struct RUToken {
53     InstRef IR;
54     unsigned NumSlots; // Slots reserved to this instruction.
55     bool Executed;     // True if the instruction is past the WB stage.
56   };
57
58 private:
59   unsigned NextAvailableSlotIdx;
60   unsigned CurrentInstructionSlotIdx;
61   unsigned AvailableSlots;
62   unsigned MaxRetirePerCycle; // 0 means no limit.
63   std::vector<RUToken> Queue;
64
65 public:
66   RetireControlUnit(const MCSchedModel &SM);
67
68   bool isEmpty() const { return AvailableSlots == Queue.size(); }
69   bool isAvailable(unsigned Quantity = 1) const {
70     // Some instructions may declare a number of uOps which exceeds the size
71     // of the reorder buffer. To avoid problems, cap the amount of slots to
72     // the size of the reorder buffer.
73     Quantity = std::min(Quantity, static_cast<unsigned>(Queue.size()));
74
75     // Further normalize the number of micro opcodes for instructions that
76     // declare zero opcodes. This should match the behavior of method
77     // reserveSlot().
78     Quantity = std::max(Quantity, 1U);
79     return AvailableSlots >= Quantity;
80   }
81
82   unsigned getMaxRetirePerCycle() const { return MaxRetirePerCycle; }
83
84   // Reserves a number of slots, and returns a new token.
85   unsigned reserveSlot(const InstRef &IS, unsigned NumMicroOps);
86
87   // Return the current token from the RCU's circular token queue.
88   const RUToken &peekCurrentToken() const;
89
90   // Advance the pointer to the next token in the circular token queue.
91   void consumeCurrentToken();
92
93   // Update the RCU token to represent the executed state.
94   void onInstructionExecuted(unsigned TokenID);
95
96 #ifndef NDEBUG
97   void dump() const;
98 #endif
99 };
100
101 } // namespace mca
102 } // namespace llvm
103
104 #endif // LLVM_MCA_RETIRE_CONTROL_UNIT_H