summaryrefslogtreecommitdiffstats
path: root/llvm/tools/llvm-mca/RetireControlUnit.h
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/tools/llvm-mca/RetireControlUnit.h')
-rw-r--r--llvm/tools/llvm-mca/RetireControlUnit.h91
1 files changed, 91 insertions, 0 deletions
diff --git a/llvm/tools/llvm-mca/RetireControlUnit.h b/llvm/tools/llvm-mca/RetireControlUnit.h
new file mode 100644
index 00000000000..0c74442aefe
--- /dev/null
+++ b/llvm/tools/llvm-mca/RetireControlUnit.h
@@ -0,0 +1,91 @@
+//===---------------------- RetireControlUnit.h -----------------*- C++ -*-===//
+//
+// The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+/// \file
+///
+/// This file implements the logic for retiring instructions.
+///
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_TOOLS_LLVM_MCA_RETIRE_CONTROL_UNIT_H
+#define LLVM_TOOLS_LLVM_MCA_RETIRE_CONTROL_UNIT_H
+
+#include "llvm/MC/MCSchedule.h"
+
+namespace mca {
+
+class DispatchUnit;
+
+/// This class tracks which instructions are in-flight (i.e., dispatched but not
+/// retired) in the OoO backend.
+//
+/// This class checks on every cycle if/which instructions can be retired.
+/// Instructions are retired in program order.
+/// In the event of instruction retired, the DispatchUnit object that owns
+/// this RetireControlUnit (RCU) gets notified.
+/// On instruction retired, register updates are all architecturally
+/// committed, and any temporary registers originally allocated for the
+/// retired instruction are freed.
+struct RetireControlUnit {
+ // A RUToken is created by the RCU for every instruction dispatched to the
+ // schedulers. These "tokens" are managed by the RCU in its token Queue.
+ //
+ // On evey cycle ('cycleEvent'), the RCU iterates through the token queue
+ // looking for any token with its 'Executed' flag set. If a token has that
+ // flag set, then the instruction has reached the write-back stage and will
+ // be retired by the RCU.
+ //
+ // 'NumSlots' represents the number of entries consumed by the instruction in
+ // the reorder buffer. Those entries will become available again once the
+ // instruction is retired.
+ //
+ // Note that the size of the reorder buffer is defined by the scheduling
+ // model via field 'NumMicroOpBufferSize'.
+ struct RUToken {
+ unsigned Index; // Instruction index.
+ unsigned NumSlots; // Slots reserved to this instruction.
+ bool Executed; // True if the instruction is past the WB stage.
+ };
+
+private:
+ unsigned NextAvailableSlotIdx;
+ unsigned CurrentInstructionSlotIdx;
+ unsigned AvailableSlots;
+ unsigned MaxRetirePerCycle; // 0 means no limit.
+ std::vector<RUToken> Queue;
+ DispatchUnit *Owner;
+
+public:
+ RetireControlUnit(const llvm::MCSchedModel &SM, DispatchUnit *DU);
+
+ bool isFull() const { return !AvailableSlots; }
+ bool isEmpty() const { return AvailableSlots == Queue.size(); }
+ bool isAvailable(unsigned Quantity = 1) const {
+ // Some instructions may declare a number of uOps which exceedes the size
+ // of the reorder buffer. To avoid problems, cap the amount of slots to
+ // the size of the reorder buffer.
+ Quantity = std::min(Quantity, static_cast<unsigned>(Queue.size()));
+ return AvailableSlots >= Quantity;
+ }
+
+ // Reserves a number of slots, and returns a new token.
+ unsigned reserveSlot(unsigned Index, unsigned NumMicroOps);
+
+ /// Retires instructions in program order.
+ void cycleEvent();
+
+ void onInstructionExecuted(unsigned TokenID);
+
+#ifndef NDEBUG
+ void dump() const;
+#endif
+};
+
+} // namespace mca
+
+#endif // LLVM_TOOLS_LLVM_MCA_RETIRE_CONTROL_UNIT_H
OpenPOWER on IntegriCloud