[InstCombine] Signed saturation patterns
[llvm-core.git] / include / llvm / MCA / HardwareUnits / RetireControlUnit.h
blobacbd4543bd4ad6091f9ad1e859a7e1c4a4ea3eec
1 //===---------------------- RetireControlUnit.h -----------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 /// \file
9 ///
10 /// This file simulates the hardware responsible for retiring instructions.
11 ///
12 //===----------------------------------------------------------------------===//
14 #ifndef LLVM_MCA_RETIRE_CONTROL_UNIT_H
15 #define LLVM_MCA_RETIRE_CONTROL_UNIT_H
17 #include "llvm/MC/MCSchedule.h"
18 #include "llvm/MCA/HardwareUnits/HardwareUnit.h"
19 #include "llvm/MCA/Instruction.h"
20 #include <vector>
22 namespace llvm {
23 namespace mca {
25 /// This class tracks which instructions are in-flight (i.e., dispatched but not
26 /// retired) in the OoO backend.
28 /// This class checks on every cycle if/which instructions can be retired.
29 /// Instructions are retired in program order.
30 /// In the event of an instruction being retired, the pipeline that owns
31 /// this RetireControlUnit (RCU) gets notified.
32 ///
33 /// On instruction retired, register updates are all architecturally
34 /// committed, and any physicall registers previously allocated for the
35 /// retired instruction are freed.
36 struct RetireControlUnit : public HardwareUnit {
37 // A RUToken is created by the RCU for every instruction dispatched to the
38 // schedulers. These "tokens" are managed by the RCU in its token Queue.
40 // On every cycle ('cycleEvent'), the RCU iterates through the token queue
41 // looking for any token with its 'Executed' flag set. If a token has that
42 // flag set, then the instruction has reached the write-back stage and will
43 // be retired by the RCU.
45 // 'NumSlots' represents the number of entries consumed by the instruction in
46 // the reorder buffer. Those entries will become available again once the
47 // instruction is retired.
49 // Note that the size of the reorder buffer is defined by the scheduling
50 // model via field 'NumMicroOpBufferSize'.
51 struct RUToken {
52 InstRef IR;
53 unsigned NumSlots; // Slots reserved to this instruction.
54 bool Executed; // True if the instruction is past the WB stage.
57 private:
58 unsigned NextAvailableSlotIdx;
59 unsigned CurrentInstructionSlotIdx;
60 unsigned NumROBEntries;
61 unsigned AvailableEntries;
62 unsigned MaxRetirePerCycle; // 0 means no limit.
63 std::vector<RUToken> Queue;
65 unsigned normalizeQuantity(unsigned Quantity) const {
66 // Some instructions may declare a number of uOps which exceeds the size
67 // of the reorder buffer. To avoid problems, cap the amount of slots to
68 // the size of the reorder buffer.
69 Quantity = std::min(Quantity, NumROBEntries);
71 // Further normalize the number of micro opcodes for instructions that
72 // declare zero opcodes. This should match the behavior of method
73 // reserveSlot().
74 return std::max(Quantity, 1U);
77 unsigned computeNextSlotIdx() const;
79 public:
80 RetireControlUnit(const MCSchedModel &SM);
82 bool isEmpty() const { return AvailableEntries == NumROBEntries; }
84 bool isAvailable(unsigned Quantity = 1) const {
85 return AvailableEntries >= normalizeQuantity(Quantity);
88 unsigned getMaxRetirePerCycle() const { return MaxRetirePerCycle; }
90 // Reserves a number of slots, and returns a new token reference.
91 unsigned dispatch(const InstRef &IS);
93 // Return the current token from the RCU's circular token queue.
94 const RUToken &getCurrentToken() const;
96 const RUToken &peekNextToken() const;
98 // Advance the pointer to the next token in the circular token queue.
99 void consumeCurrentToken();
101 // Update the RCU token to represent the executed state.
102 void onInstructionExecuted(unsigned TokenID);
104 #ifndef NDEBUG
105 void dump() const;
106 #endif
109 } // namespace mca
110 } // namespace llvm
112 #endif // LLVM_MCA_RETIRE_CONTROL_UNIT_H