//===---------------------- RetireControlUnit.cpp ---------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
/// \file
///
/// This file simulates the hardware responsible for retiring instructions.
///
//===----------------------------------------------------------------------===//

#include "llvm/MCA/HardwareUnits/RetireControlUnit.h"
#include "llvm/Support/Debug.h"

#define DEBUG_TYPE "llvm-mca"

namespace llvm {
namespace mca {

RetireControlUnit::RetireControlUnit(const MCSchedModel &SM)
    : NextAvailableSlotIdx(0), CurrentInstructionSlotIdx(0),
      NumROBEntries(SM.MicroOpBufferSize),
      AvailableEntries(SM.MicroOpBufferSize), MaxRetirePerCycle(0) {
  // Check if the scheduling model provides extra information about the machine
  // processor. If so, then use that information to set the reorder buffer size
  // and the maximum number of instructions retired per cycle.
  if (SM.hasExtraProcessorInfo()) {
    const MCExtraProcessorInfo &EPI = SM.getExtraProcessorInfo();
    if (EPI.ReorderBufferSize)
      AvailableEntries = EPI.ReorderBufferSize;
    MaxRetirePerCycle = EPI.MaxRetirePerCycle;
  }
  NumROBEntries = AvailableEntries;
  assert(NumROBEntries && "Invalid reorder buffer size!");
  Queue.resize(2 * NumROBEntries);
}

// Reserves a number of slots, and returns a new token.
unsigned RetireControlUnit::dispatch(const InstRef &IR) {
  const Instruction &Inst = *IR.getInstruction();
  unsigned Entries = normalizeQuantity(Inst.getNumMicroOps());
  assert((AvailableEntries >= Entries) && "Reorder Buffer unavailable!");

  unsigned TokenID = NextAvailableSlotIdx;
  Queue[NextAvailableSlotIdx] = {IR, Entries, false};
  NextAvailableSlotIdx += std::max(1U, Entries);
  NextAvailableSlotIdx %= Queue.size();

  AvailableEntries -= Entries;
  return TokenID;
}

const RetireControlUnit::RUToken &RetireControlUnit::getCurrentToken() const {
  const RetireControlUnit::RUToken &Current = Queue[CurrentInstructionSlotIdx];
#ifndef NDEBUG
  const Instruction *Inst = Current.IR.getInstruction();
  assert(Inst && "Invalid RUToken in the RCU queue.");
#endif
  return Current;
}

unsigned RetireControlUnit::computeNextSlotIdx() const {
  const RetireControlUnit::RUToken &Current = getCurrentToken();
  unsigned NextSlotIdx = CurrentInstructionSlotIdx + std::max(1U, Current.NumSlots);
  return NextSlotIdx % Queue.size();
}

const RetireControlUnit::RUToken &RetireControlUnit::peekNextToken() const {
  return Queue[computeNextSlotIdx()];
}

void RetireControlUnit::consumeCurrentToken() {
  RetireControlUnit::RUToken &Current = Queue[CurrentInstructionSlotIdx];
  Current.IR.getInstruction()->retire();

  // Update the slot index to be the next item in the circular queue.
  CurrentInstructionSlotIdx += std::max(1U, Current.NumSlots);
  CurrentInstructionSlotIdx %= Queue.size();
  AvailableEntries += Current.NumSlots;
  Current = { InstRef(), 0U, false };
}

void RetireControlUnit::onInstructionExecuted(unsigned TokenID) {
  assert(Queue.size() > TokenID);
  assert(Queue[TokenID].IR.getInstruction() && "Instruction was not dispatched!");
  assert(Queue[TokenID].Executed == false && "Instruction already executed!");
  Queue[TokenID].Executed = true;
}

#ifndef NDEBUG
void RetireControlUnit::dump() const {
  dbgs() << "Retire Unit: { Total ROB Entries =" << NumROBEntries
         << ", Available ROB entries=" << AvailableEntries << " }\n";
}
#endif

} // namespace mca
} // namespace llvm
