blob: 5530aaf90bd2d1cd6512acfd39073e0d63a27f3c [file] [log] [blame]
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +00001//===--------------------- Backend.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 implements an OoO backend for the llvm-mca tool.
12///
13//===----------------------------------------------------------------------===//
14
15#ifndef LLVM_TOOLS_LLVM_MCA_BACKEND_H
16#define LLVM_TOOLS_LLVM_MCA_BACKEND_H
17
18#include "Dispatch.h"
Matt Davis5d1cda12018-05-15 20:21:04 +000019#include "FetchStage.h"
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000020#include "InstrBuilder.h"
21#include "Scheduler.h"
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000022
23namespace mca {
24
Andrea Di Biagio3db1fd92018-03-08 16:34:19 +000025class HWEventListener;
Clement Courbet844f22d2018-03-13 13:11:01 +000026class HWInstructionEvent;
Andrea Di Biagio91ab2ee2018-03-19 13:23:07 +000027class HWStallEvent;
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000028
Adrian Prantl5f8f34e42018-05-01 15:54:18 +000029/// An out of order backend for a specific subtarget.
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000030///
31/// It emulates an out-of-order execution of instructions. Instructions are
Matt Davis5d1cda12018-05-15 20:21:04 +000032/// fetched from a MCInst sequence managed by an initial 'Fetch' stage.
33/// Instructions are firstly fetched, then dispatched to the schedulers, and
34/// then executed.
35///
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000036/// This class tracks the lifetime of an instruction from the moment where
37/// it gets dispatched to the schedulers, to the moment where it finishes
38/// executing and register writes are architecturally committed.
39/// In particular, it monitors changes in the state of every instruction
40/// in flight.
Matt Davis5d1cda12018-05-15 20:21:04 +000041///
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000042/// Instructions are executed in a loop of iterations. The number of iterations
Matt Davis5d1cda12018-05-15 20:21:04 +000043/// is defined by the SourceMgr object, which is managed by the initial stage
44/// of the instruction pipeline.
45///
46/// The Backend entry point is method 'run()' which executes cycles in a loop
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000047/// until there are new instructions to dispatch, and not every instruction
48/// has been retired.
Matt Davis5d1cda12018-05-15 20:21:04 +000049///
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000050/// Internally, the Backend collects statistical information in the form of
51/// histograms. For example, it tracks how the dispatch group size changes
52/// over time.
53class Backend {
54 const llvm::MCSubtargetInfo &STI;
55
Matt Davis5d1cda12018-05-15 20:21:04 +000056 /// This is the initial stage of the pipeline.
57 /// TODO: Eventually this will become a list of unique Stage* that this
58 /// backend pipeline executes.
59 std::unique_ptr<FetchStage> Fetch;
60
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000061 std::unique_ptr<Scheduler> HWS;
62 std::unique_ptr<DispatchUnit> DU;
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000063 std::set<HWEventListener *> Listeners;
Matt Davis5d1cda12018-05-15 20:21:04 +000064 unsigned Cycles;
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000065
66 void runCycle(unsigned Cycle);
67
68public:
Andrea Di Biagiob5088da2018-03-23 11:50:43 +000069 Backend(const llvm::MCSubtargetInfo &Subtarget,
Matt Davis5d1cda12018-05-15 20:21:04 +000070 const llvm::MCRegisterInfo &MRI,
71 std::unique_ptr<FetchStage> InitialStage, unsigned DispatchWidth = 0,
72 unsigned RegisterFileSize = 0, unsigned LoadQueueSize = 0,
73 unsigned StoreQueueSize = 0, bool AssumeNoAlias = false)
74 : STI(Subtarget), Fetch(std::move(InitialStage)),
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000075 HWS(llvm::make_unique<Scheduler>(this, Subtarget.getSchedModel(),
76 LoadQueueSize, StoreQueueSize,
77 AssumeNoAlias)),
Andrea Di Biagioc74ad502018-04-05 15:41:41 +000078 DU(llvm::make_unique<DispatchUnit>(this, Subtarget.getSchedModel(), MRI,
79 RegisterFileSize, DispatchWidth,
80 HWS.get())),
Matt Davis5d1cda12018-05-15 20:21:04 +000081 Cycles(0) {
Clement Courbet844f22d2018-03-13 13:11:01 +000082 HWS->setDispatchUnit(DU.get());
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000083 }
84
Matt Davis5d1cda12018-05-15 20:21:04 +000085 void run();
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000086 void addEventListener(HWEventListener *Listener);
87 void notifyCycleBegin(unsigned Cycle);
Clement Courbet844f22d2018-03-13 13:11:01 +000088 void notifyInstructionEvent(const HWInstructionEvent &Event);
Andrea Di Biagio91ab2ee2018-03-19 13:23:07 +000089 void notifyStallEvent(const HWStallEvent &Event);
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000090 void notifyResourceAvailable(const ResourceRef &RR);
Andrea Di Biagioa3f2e482018-03-20 18:20:39 +000091 void notifyReservedBuffers(llvm::ArrayRef<unsigned> Buffers);
92 void notifyReleasedBuffers(llvm::ArrayRef<unsigned> Buffers);
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000093 void notifyCycleEnd(unsigned Cycle);
94};
Andrea Di Biagio3a6b0922018-03-08 13:05:02 +000095} // namespace mca
96
97#endif