1 //===--------------------- InstrBuilder.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 /// A builder class for instructions that are statically analyzed by llvm-mca. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_MCA_INSTRBUILDER_H 15 #define LLVM_MCA_INSTRBUILDER_H 16 17 #include "llvm/ADT/Hashing.h" 18 #include "llvm/ADT/STLExtras.h" 19 #include "llvm/MC/MCInstrAnalysis.h" 20 #include "llvm/MC/MCInstrInfo.h" 21 #include "llvm/MC/MCRegisterInfo.h" 22 #include "llvm/MC/MCSubtargetInfo.h" 23 #include "llvm/MCA/CustomBehaviour.h" 24 #include "llvm/MCA/Instruction.h" 25 #include "llvm/MCA/Support.h" 26 #include "llvm/Support/Compiler.h" 27 #include "llvm/Support/Error.h" 28 29 namespace llvm { 30 namespace mca { 31 32 class RecycledInstErr : public ErrorInfo<RecycledInstErr> { 33 Instruction *RecycledInst; 34 35 public: 36 LLVM_ABI static char ID; 37 RecycledInstErr(Instruction * Inst)38 explicit RecycledInstErr(Instruction *Inst) : RecycledInst(Inst) {} 39 // Always need to carry an Instruction 40 RecycledInstErr() = delete; 41 getInst()42 Instruction *getInst() const { return RecycledInst; } 43 log(raw_ostream & OS)44 void log(raw_ostream &OS) const override { 45 OS << "Instruction is recycled\n"; 46 } 47 convertToErrorCode()48 std::error_code convertToErrorCode() const override { 49 return llvm::inconvertibleErrorCode(); 50 } 51 }; 52 53 /// A builder class that knows how to construct Instruction objects. 54 /// 55 /// Every llvm-mca Instruction is described by an object of class InstrDesc. 56 /// An InstrDesc describes which registers are read/written by the instruction, 57 /// as well as the instruction latency and hardware resources consumed. 58 /// 59 /// This class is used by the tool to construct Instructions and instruction 60 /// descriptors (i.e. InstrDesc objects). 61 /// Information from the machine scheduling model is used to identify processor 62 /// resources that are consumed by an instruction. 63 class InstrBuilder { 64 const MCSubtargetInfo &STI; 65 const MCInstrInfo &MCII; 66 const MCRegisterInfo &MRI; 67 const MCInstrAnalysis *MCIA; 68 const InstrumentManager &IM; 69 SmallVector<uint64_t, 8> ProcResourceMasks; 70 71 // Key is the MCI.Opcode and SchedClassID the describe the value InstrDesc 72 DenseMap<std::pair<unsigned short, unsigned>, 73 std::unique_ptr<const InstrDesc>> 74 Descriptors; 75 76 // Key is a hash of the MCInstruction and a SchedClassID that describe the 77 // value InstrDesc 78 DenseMap<std::pair<hash_code, unsigned>, std::unique_ptr<const InstrDesc>> 79 VariantDescriptors; 80 81 bool FirstCallInst; 82 bool FirstReturnInst; 83 unsigned CallLatency; 84 85 using InstRecycleCallback = std::function<Instruction *(const InstrDesc &)>; 86 InstRecycleCallback InstRecycleCB; 87 88 Expected<unsigned> getVariantSchedClassID(const MCInst &MCI, unsigned SchedClassID); 89 Expected<const InstrDesc &> 90 createInstrDescImpl(const MCInst &MCI, const SmallVector<Instrument *> &IVec); 91 Expected<const InstrDesc &> 92 getOrCreateInstrDesc(const MCInst &MCI, 93 const SmallVector<Instrument *> &IVec); 94 95 InstrBuilder(const InstrBuilder &) = delete; 96 InstrBuilder &operator=(const InstrBuilder &) = delete; 97 98 void populateWrites(InstrDesc &ID, const MCInst &MCI, unsigned SchedClassID); 99 void populateReads(InstrDesc &ID, const MCInst &MCI, unsigned SchedClassID); 100 Error verifyInstrDesc(const InstrDesc &ID, const MCInst &MCI) const; 101 102 public: 103 LLVM_ABI InstrBuilder(const MCSubtargetInfo &STI, const MCInstrInfo &MCII, 104 const MCRegisterInfo &RI, const MCInstrAnalysis *IA, 105 const InstrumentManager &IM, unsigned CallLatency); 106 clear()107 void clear() { 108 Descriptors.clear(); 109 VariantDescriptors.clear(); 110 FirstCallInst = true; 111 FirstReturnInst = true; 112 } 113 114 /// Set a callback which is invoked to retrieve a recycled mca::Instruction 115 /// or null if there isn't any. setInstRecycleCallback(InstRecycleCallback CB)116 void setInstRecycleCallback(InstRecycleCallback CB) { InstRecycleCB = CB; } 117 118 LLVM_ABI Expected<std::unique_ptr<Instruction>> 119 createInstruction(const MCInst &MCI, const SmallVector<Instrument *> &IVec); 120 }; 121 } // namespace mca 122 } // namespace llvm 123 124 #endif // LLVM_MCA_INSTRBUILDER_H 125