46#define DEBUG_TYPE "asm-printer"
49enum class SPIRVFPContractMode { On, Off,
Fast };
53 cl::desc(
"Override FP contraction policy for SPIR-V kernel entry points"),
56 "Follow IR metadata (default)"),
58 "Force ContractionOff on all kernel entry points"),
60 "Suppress ContractionOff on all kernel entry points")),
69 std::unique_ptr<MCStreamer> Streamer)
70 :
AsmPrinter(TM, std::move(Streamer),
ID), ModuleSectionsEmitted(
false),
71 ST(
nullptr),
TII(
nullptr), MAI(
nullptr) {}
73 bool ModuleSectionsEmitted;
77 StringRef getPassName()
const override {
return "SPIRV Assembly Printer"; }
82 void outputMCInst(
MCInst &Inst);
85 void outputGlobalRequirements();
86 void outputEntryPoints();
87 void outputDebugSourceAndStrings(
const Module &M);
88 void outputOpExtInstImports(
const Module &M);
89 void outputOpMemoryModel();
90 void outputOpFunctionEnd();
91 void outputExtFuncDecls();
93 SPIRV::ExecutionMode::ExecutionMode EM,
94 unsigned ExpectMDOps, int64_t DefVal);
95 void outputExecutionModeFromNumthreadsAttribute(
97 SPIRV::ExecutionMode::ExecutionMode EM);
98 void outputExecutionModeFromEnableMaximalReconvergenceAttr(
101 SPIRV::ExecutionMode::ExecutionMode EM);
102 void outputExecutionMode(
const Module &M);
103 void outputAnnotations(
const Module &M);
104 void outputModuleSections();
105 void outputFPFastMathDefaultInfo();
107 return MF->getFunction()
113 void emitFunctionEntryLabel()
override {}
114 void emitFunctionHeader()
override;
115 void emitFunctionBodyStart()
override {}
116 void emitFunctionBodyEnd()
override;
121 void emitEndOfAsmFile(
Module &M)
override;
122 bool doInitialization(
Module &M)
override;
132 std::unique_ptr<SPIRVAuxDataHandler> AuxDataHandler;
139void SPIRVAsmPrinter::getAnalysisUsage(
AnalysisUsage &AU)
const {
146void SPIRVAsmPrinter::emitEndOfAsmFile(
Module &M) {
147 if (!ModuleSectionsEmitted) {
148 outputModuleSections();
149 ModuleSectionsEmitted =
true;
152 ST =
static_cast<const SPIRVTargetMachine &
>(TM).getSubtargetImpl();
160 uint32_t Major = SPIRVVersion.
getMajor();
161 uint32_t Minor = SPIRVVersion.
getMinor().value_or(0);
164 unsigned Bound = 2 * (ST->
getBound() + 1) + NLabels;
165 if (MCAssembler *Asm = OutStreamer->getAssemblerPtr())
166 static_cast<SPIRVObjectWriter &
>(
Asm->getWriter())
167 .setBuildVersion(Major, Minor, Bound);
174void SPIRVAsmPrinter::cleanUp(
Module &M) {
176 for (StringRef GVName :
177 {
"llvm.global_ctors",
"llvm.global_dtors",
"llvm.used"}) {
178 if (GlobalVariable *GV =
M.getNamedGlobal(GVName))
183void SPIRVAsmPrinter::emitFunctionHeader() {
184 if (!ModuleSectionsEmitted) {
185 outputModuleSections();
186 ModuleSectionsEmitted =
true;
189 ST = &MF->getSubtarget<SPIRVSubtarget>();
193 if (isVerbose() && !isHidden()) {
194 OutStreamer->getCommentOS()
195 <<
"-- Begin function "
199 auto Section = getObjFileLowering().SectionForGlobal(&
F, TM);
200 MF->setSection(Section);
206 for (
auto &Handler : Handlers) {
207 Handler->beginFunction(MF);
208 Handler->beginBasicBlockSection(MF->front());
212void SPIRVAsmPrinter::outputOpFunctionEnd() {
213 MCInst FunctionEndInst;
214 FunctionEndInst.
setOpcode(SPIRV::OpFunctionEnd);
215 outputMCInst(FunctionEndInst);
218void SPIRVAsmPrinter::emitFunctionBodyEnd() {
220 outputOpFunctionEnd();
223void SPIRVAsmPrinter::emitOpLabel(
const MachineBasicBlock &
MBB) {
231 outputMCInst(LabelInst);
236void SPIRVAsmPrinter::emitBasicBlockStart(
const MachineBasicBlock &
MBB) {
244 for (
const MachineInstr &
MI :
MBB)
245 if (
MI.getOpcode() == SPIRV::OpFunction)
253void SPIRVAsmPrinter::printOperand(
const MachineInstr *
MI,
int OpNum,
255 const MachineOperand &MO =
MI->getOperand(OpNum);
295bool SPIRVAsmPrinter::PrintAsmOperand(
const MachineInstr *
MI,
unsigned OpNo,
296 const char *ExtraCode, raw_ostream &O) {
297 if (ExtraCode && ExtraCode[0])
306 return TII->isHeaderInstr(*
MI) ||
MI->getOpcode() == SPIRV::OpFunction ||
307 MI->getOpcode() == SPIRV::OpFunctionParameter;
310void SPIRVAsmPrinter::outputMCInst(MCInst &Inst) {
311 OutStreamer->emitInstruction(Inst, *OutContext.getSubtargetInfo());
314void SPIRVAsmPrinter::outputInstruction(
const MachineInstr *
MI) {
315 SPIRVMCInstLower MCInstLowering;
317 MCInstLowering.
lower(
MI, TmpInst, MAI);
318 outputMCInst(TmpInst);
321void SPIRVAsmPrinter::emitInstruction(
const MachineInstr *
MI) {
322 SPIRV_MC::verifyInstructionPredicates(
MI->getOpcode(),
323 getSubtargetInfo().getFeatureBits());
325 if (!MAI->getSkipEmission(
MI))
326 outputInstruction(
MI);
329 const MachineInstr *NextMI =
MI->getNextNode();
332 assert(
MI->getParent()->getNumber() == MF->front().getNumber() &&
333 "OpFunction is not in the front MBB of MF");
334 emitOpLabel(*
MI->getParent());
338void SPIRVAsmPrinter::outputModuleSection(SPIRV::ModuleSectionType MSType) {
339 for (
const MachineInstr *
MI : MAI->getMSInstrs(MSType))
340 outputInstruction(
MI);
343void SPIRVAsmPrinter::outputDebugSourceAndStrings(
const Module &M) {
345 for (
auto &Str : MAI->SrcExt) {
347 Inst.
setOpcode(SPIRV::OpSourceExtension);
352 outputModuleSection(SPIRV::MB_DebugStrings);
368 AuxDataHandler->emitAuxDataStrings(*MAI);
371void SPIRVAsmPrinter::outputOpExtInstImports(
const Module &M) {
372 for (
auto &CU : MAI->ExtInstSetMap) {
373 unsigned Set = CU.first;
374 MCRegister
Reg = CU.second;
379 static_cast<SPIRV::InstructionSet::InstructionSet
>(Set)),
385void SPIRVAsmPrinter::outputOpMemoryModel() {
397void SPIRVAsmPrinter::outputEntryPoints() {
399 DenseSet<MCRegister> InterfaceIDs;
400 for (
const MachineInstr *
MI : MAI->GlobalVarList) {
401 assert(
MI->getOpcode() == SPIRV::OpVariable);
402 auto SC =
static_cast<SPIRV::StorageClass::StorageClass
>(
409 SC == SPIRV::StorageClass::Input || SC == SPIRV::StorageClass::Output) {
410 const MachineFunction *MF =
MI->getMF();
411 MCRegister
Reg = MAI->getRegisterAlias(MF,
MI->getOperand(0).getReg());
417 for (
const MachineInstr *
MI : MAI->getMSInstrs(SPIRV::MB_EntryPoints)) {
418 SPIRVMCInstLower MCInstLowering;
420 MCInstLowering.
lower(
MI, TmpInst, MAI);
421 for (MCRegister
Reg : InterfaceIDs) {
425 outputMCInst(TmpInst);
430void SPIRVAsmPrinter::outputGlobalRequirements() {
432 MAI->Reqs.checkSatisfiable(*ST);
434 for (
const auto &Cap : MAI->Reqs.getMinimalCapabilities()) {
442 for (
const auto &Ext : MAI->Reqs.getExtensions()) {
446 SPIRV::OperandCategory::ExtensionOperand, Ext),
453void SPIRVAsmPrinter::outputExtFuncDecls() {
455 auto I = MAI->getMSInstrs(SPIRV::MB_ExtFuncDecls).begin(),
456 E = MAI->getMSInstrs(SPIRV::MB_ExtFuncDecls).end();
457 for (;
I !=
E; ++
I) {
458 outputInstruction(*
I);
459 if ((
I + 1) ==
E || (*(
I + 1))->getOpcode() == SPIRV::OpFunction)
460 outputOpFunctionEnd();
470 if (Ty->isDoubleTy())
473 switch (IntTy->getIntegerBitWidth()) {
487 Type *EleTy = VecTy->getElementType();
488 unsigned Size = VecTy->getNumElements();
510void SPIRVAsmPrinter::outputExecutionModeFromMDNode(
511 MCRegister
Reg, MDNode *Node, SPIRV::ExecutionMode::ExecutionMode EM,
512 unsigned ExpectMDOps, int64_t DefVal) {
520 unsigned NodeSz =
Node->getNumOperands();
521 if (ExpectMDOps > 0 && NodeSz < ExpectMDOps)
522 for (
unsigned i = NodeSz; i < ExpectMDOps; ++i)
527void SPIRVAsmPrinter::outputExecutionModeFromNumthreadsAttribute(
529 SPIRV::ExecutionMode::ExecutionMode EM) {
530 assert(Attr.
isValid() &&
"Function called with an invalid attribute.");
539 assert(NumThreads.size() == 3 &&
"invalid numthreads");
540 for (uint32_t i = 0; i < 3; ++i) {
542 [[maybe_unused]]
bool Result = NumThreads[i].getAsInteger(10, V);
543 assert(!Result &&
"Failed to parse numthreads");
550void SPIRVAsmPrinter::emitSimpleExecutionMode(
551 MCRegister
Reg, SPIRV::ExecutionMode::ExecutionMode EM) {
559void SPIRVAsmPrinter::outputExecutionModeFromEnableMaximalReconvergenceAttr(
560 const MCRegister &
Reg,
const SPIRVSubtarget &ST) {
561 assert(
ST.canUseExtension(SPIRV::Extension::SPV_KHR_maximal_reconvergence) &&
562 "Function called when SPV_KHR_maximal_reconvergence is not enabled.");
564 emitSimpleExecutionMode(
Reg, SPIRV::ExecutionMode::MaximallyReconvergesKHR);
567void SPIRVAsmPrinter::outputExecutionMode(
const Module &M) {
568 NamedMDNode *
Node =
M.getNamedMetadata(
"spirv.ExecutionMode");
570 for (
unsigned i = 0; i <
Node->getNumOperands(); i++) {
577 if (EM == SPIRV::ExecutionMode::ArithmeticPoisonKHR)
583 if (EM == SPIRV::ExecutionMode::FPFastMathDefault ||
584 EM == SPIRV::ExecutionMode::ContractionOff ||
585 EM == SPIRV::ExecutionMode::SignedZeroInfNanPreserve)
594 outputFPFastMathDefaultInfo();
596 for (
auto FI =
M.begin(),
E =
M.end(); FI !=
E; ++FI) {
602 MCRegister FReg = MAI->getGlobalObjReg(&
F);
611 emitSimpleExecutionMode(FReg, SPIRV::ExecutionMode::OriginUpperLeft);
614 if (MDNode *Node =
F.getMetadata(
"reqd_work_group_size"))
615 outputExecutionModeFromMDNode(FReg, Node, SPIRV::ExecutionMode::LocalSize,
618 outputExecutionModeFromNumthreadsAttribute(
619 FReg, Attr, SPIRV::ExecutionMode::LocalSize);
620 if (
Attribute Attr =
F.getFnAttribute(
"enable-maximal-reconvergence");
622 outputExecutionModeFromEnableMaximalReconvergenceAttr(FReg, *ST);
624 if (MDNode *Node =
F.getMetadata(
"work_group_size_hint"))
625 outputExecutionModeFromMDNode(FReg, Node,
626 SPIRV::ExecutionMode::LocalSizeHint, 3, 1);
627 if (MDNode *Node =
F.getMetadata(
"reqd_sub_group_size"))
628 outputExecutionModeFromMDNode(FReg, Node,
629 SPIRV::ExecutionMode::SubgroupSize, 0, 0);
630 if (MDNode *Node =
F.getMetadata(
"intel_reqd_sub_group_size"))
631 outputExecutionModeFromMDNode(FReg, Node,
632 SPIRV::ExecutionMode::SubgroupSize, 0, 0);
633 if (MDNode *Node =
F.getMetadata(
"max_work_group_size")) {
634 if (ST->
canUseExtension(SPIRV::Extension::SPV_INTEL_kernel_attributes))
635 outputExecutionModeFromMDNode(
636 FReg, Node, SPIRV::ExecutionMode::MaxWorkgroupSizeINTEL, 3, 1);
638 if (MDNode *Node =
F.getMetadata(
"vec_type_hint")) {
642 unsigned EM =
static_cast<unsigned>(SPIRV::ExecutionMode::VecTypeHint);
651 SPIRV::Capability::PoisonFreezeKHR)) {
652 emitSimpleExecutionMode(FReg, SPIRV::ExecutionMode::ArithmeticPoisonKHR);
656 bool EmitContractionOff =
657 ST->
isKernel() && !
M.getNamedMetadata(
"spirv.ExecutionMode") &&
658 SPIRVFPContract != SPIRVFPContractMode::Fast &&
659 (SPIRVFPContract == SPIRVFPContractMode::Off ||
660 !
M.getNamedMetadata(
"opencl.enable.FP_CONTRACT"));
661 if (EmitContractionOff) {
679 std::vector<const MachineInstr *> SPIRVFloatTypes;
680 const MachineInstr *ConstZeroInt32 =
nullptr;
681 for (
const MachineInstr *
MI :
682 MAI->getMSInstrs(SPIRV::MB_TypeConstVars)) {
686 if (OpCode == SPIRV::OpTypeFloat) {
688 const unsigned OpTypeFloatSize =
MI->getOperand(1).getImm();
689 if (OpTypeFloatSize != 16 && OpTypeFloatSize != 32 &&
690 OpTypeFloatSize != 64) {
693 SPIRVFloatTypes.push_back(
MI);
697 if (OpCode == SPIRV::OpConstantNull) {
699 const MachineRegisterInfo &MRI =
MI->getMF()->getRegInfo();
700 MachineInstr *TypeMI = MRI.
getVRegDef(
MI->getOperand(1).getReg());
701 bool IsInt32Ty = TypeMI &&
702 TypeMI->
getOpcode() == SPIRV::OpTypeInt &&
715 for (
const MachineInstr *
MI : SPIRVFloatTypes) {
717 Inst.
setOpcode(SPIRV::OpExecutionModeId);
720 static_cast<unsigned>(SPIRV::ExecutionMode::FPFastMathDefault);
722 const MachineFunction *MF =
MI->getMF();
724 MAI->getRegisterAlias(MF,
MI->getOperand(0).getReg());
726 assert(ConstZeroInt32 &&
"There should be a constant zero.");
727 MCRegister ConstReg = MAI->getRegisterAlias(
733 emitSimpleExecutionMode(FReg, SPIRV::ExecutionMode::ContractionOff);
739void SPIRVAsmPrinter::outputAnnotations(
const Module &M) {
740 outputModuleSection(SPIRV::MB_Annotations);
742 for (
auto F =
M.global_begin(),
E =
M.global_end();
F !=
E; ++
F) {
743 if ((*F).getName() !=
"llvm.global.annotations")
745 const GlobalVariable *
V = &(*F);
753 MCRegister
Reg = GO ? MAI->getGlobalObjReg(GO) : MCRegister();
756 raw_string_ostream OS(DiagMsg);
757 AnnotatedVar->
print(OS);
758 DiagMsg =
"Unsupported value in llvm.global.annotations: " + DiagMsg;
766 StringRef AnnotationString;
767 [[maybe_unused]]
bool Success =
773 unsigned Dec =
static_cast<unsigned>(SPIRV::Decoration::UserSemantic);
781void SPIRVAsmPrinter::outputFPFastMathDefaultInfo() {
784 std::vector<const MachineInstr *> SPIRVFloatTypes;
786 DenseMap<int, const MachineInstr *>
ConstMap;
787 for (
const MachineInstr *
MI : MAI->getMSInstrs(SPIRV::MB_TypeConstVars)) {
790 if (OpCode != SPIRV::OpTypeFloat && OpCode != SPIRV::OpConstantI &&
791 OpCode != SPIRV::OpConstantNull)
795 if (OpCode == SPIRV::OpTypeFloat) {
796 SPIRVFloatTypes.push_back(
MI);
799 const MachineRegisterInfo &MRI =
MI->getMF()->getRegInfo();
800 MachineInstr *TypeMI = MRI.
getVRegDef(
MI->getOperand(1).getReg());
801 if (!TypeMI || TypeMI->
getOpcode() != SPIRV::OpTypeInt ||
805 if (OpCode == SPIRV::OpConstantI)
812 for (
const auto &[Func, FPFastMathDefaultInfoVec] :
813 MAI->FPFastMathDefaultInfoMap) {
814 if (FPFastMathDefaultInfoVec.empty())
817 for (
const MachineInstr *
MI : SPIRVFloatTypes) {
818 unsigned OpTypeFloatSize =
MI->getOperand(1).getImm();
821 assert(Index < FPFastMathDefaultInfoVec.size() &&
822 "Index out of bounds for FPFastMathDefaultInfoVec");
823 const auto &FPFastMathDefaultInfo = FPFastMathDefaultInfoVec[
Index];
824 assert(FPFastMathDefaultInfo.Ty &&
825 "Expected target type for FPFastMathDefaultInfo");
826 assert(FPFastMathDefaultInfo.Ty->getScalarSizeInBits() ==
828 "Mismatched float type size");
830 Inst.
setOpcode(SPIRV::OpExecutionModeId);
831 MCRegister FuncReg = MAI->getGlobalObjReg(Func);
837 MAI->getRegisterAlias(
MI->getMF(),
MI->getOperand(0).getReg());
839 unsigned Flags = FPFastMathDefaultInfo.FastMathFlags;
840 if (FPFastMathDefaultInfo.ContractionOff &&
841 (Flags & SPIRV::FPFastMathMode::AllowContract))
843 "Conflicting FPFastMathFlags: ContractionOff and AllowContract");
845 if (FPFastMathDefaultInfo.SignedZeroInfNanPreserve &&
847 (SPIRV::FPFastMathMode::NotNaN | SPIRV::FPFastMathMode::NotInf |
848 SPIRV::FPFastMathMode::NSZ))) {
849 if (FPFastMathDefaultInfo.FPFastMathDefault)
851 "SignedZeroInfNanPreserve but at least one of "
852 "NotNaN/NotInf/NSZ is enabled.");
856 if (Flags == SPIRV::FPFastMathMode::None &&
857 !FPFastMathDefaultInfo.ContractionOff &&
858 !FPFastMathDefaultInfo.SignedZeroInfNanPreserve &&
859 !FPFastMathDefaultInfo.FPFastMathDefault)
866 "Mode operand of FPFastMathDefault execution mode.");
867 const MachineInstr *ConstMI = It->second;
868 MCRegister ConstReg = MAI->getRegisterAlias(
876void SPIRVAsmPrinter::outputModuleSections() {
877 const Module *
M = MMI->getModule();
879 ST =
static_cast<const SPIRVTargetMachine &
>(TM).getSubtargetImpl();
881 MAI = &getAnalysis<SPIRVModuleAnalysis>().MAI;
882 assert(ST &&
TII && MAI && M &&
"Module analysis is required");
884 if (!AuxDataHandler) {
885 auto Handler = std::make_unique<SPIRVAuxDataHandler>(*
this, *M);
886 if (Handler->hasWork())
887 AuxDataHandler = std::move(Handler);
895 AuxDataHandler->prepareModuleOutput(*ST, *MAI);
900 outputGlobalRequirements();
902 outputOpExtInstImports(*M);
904 outputOpMemoryModel();
909 outputExecutionMode(*M);
912 outputDebugSourceAndStrings(*M);
914 outputModuleSection(SPIRV::MB_DebugNames);
916 outputModuleSection(SPIRV::MB_DebugModuleProcessed);
919 outputModuleSection(SPIRV::MB_AliasingInsts);
921 outputAnnotations(*M);
926 outputModuleSection(SPIRV::MB_TypeConstVars);
933 AuxDataHandler->emitAuxData(*MAI);
935 outputExtFuncDecls();
940bool SPIRVAsmPrinter::doInitialization(
Module &M) {
941 ModuleSectionsEmitted =
false;
942 if (!
M.getModuleInlineAsm().empty()) {
943 M.getContext().emitError(
944 "SPIR-V does not support module-level inline assembly");
945 M.removeModuleInlineAsm();
950 if (
M.getNamedMetadata(
"llvm.dbg.cu")) {
951 auto Handler = std::make_unique<SPIRVNonSemanticDebugHandler>(*
this);
952 NSDebugHandler = Handler.get();
953 addAsmPrinterHandler(std::move(Handler));
959char SPIRVAsmPrinter::ID = 0;
966LLVMInitializeSPIRVAsmPrinter() {
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
#define clEnumValN(ENUMVAL, FLAGNAME, DESC)
#define LLVM_EXTERNAL_VISIBILITY
This file defines the DenseMap class.
const HexagonInstrInfo * TII
Machine Check Debug Module
This file declares the MachineConstantPool class which is an abstract constant pool to keep track of ...
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
static void addOpsFromMDNode(MDNode *MDN, MCInst &Inst, SPIRV::ModuleAnalysisInfo *MAI)
static bool isFuncOrHeaderInstr(const MachineInstr *MI, const SPIRVInstrInfo *TII)
static unsigned encodeVecTypeHint(Type *Ty)
#define SPIRV_BACKEND_SERVICE_FUN_NAME
static bool printOperand(raw_ostream &OS, const SelectionDAG *G, const SDValue Value)
static TableGen::Emitter::Opt Y("gen-skeleton-entry", EmitSkeleton, "Generate example skeleton entry")
Represent the analysis usage information of a pass.
AnalysisUsage & addRequired()
AnalysisUsage & addPreserved()
Add the specified Pass class to the set of analyses preserved by this pass.
This class is intended to be used as a driving class for all asm writers.
bool doInitialization(Module &M) override
Set up the AsmPrinter when we are working on a new module.
void getAnalysisUsage(AnalysisUsage &AU) const override
Record analysis usage.
Functions, function parameters, and return types can have attributes to indicate how they should be t...
LLVM_ABI bool getValueAsBool() const
Return the attribute's value as a boolean.
LLVM_ABI StringRef getValueAsString() const
Return the attribute's value as a string.
bool isValid() const
Return true if the attribute is any kind of attribute.
This is the shared class of boolean and integer constants.
This is an important base class in LLVM.
iterator find(const_arg_type_t< KeyT > Val)
Class to represent fixed width SIMD vectors.
static StringRef dropLLVMManglingEscape(StringRef Name)
If the given string begins with the GlobalValue name mangling escape character '\1',...
Class to represent integer types.
Instances of this class represent a single low-level machine instruction.
void addOperand(const MCOperand Op)
void setOpcode(unsigned Op)
static MCOperand createReg(MCRegister Reg)
static MCOperand createImm(int64_t Val)
Wrapper class representing physical registers. Should be passed by value.
constexpr bool isValid() const
StringRef getName() const
getName - Get the symbol name.
ArrayRef< MDOperand > operands() const
Tracking metadata reference owned by Metadata.
LLVM_ABI MCSymbol * getSymbol() const
Return the MCSymbol for this basic block.
int getNumber() const
MachineBasicBlocks are uniquely numbered at the function level, unless they're not in a MachineFuncti...
Representation of each machine instruction.
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
LLVM_ABI const MachineFunction * getMF() const
Return the function that contains the basic block that this instruction belongs to.
const MachineOperand & getOperand(unsigned i) const
const GlobalValue * getGlobal() const
MachineBasicBlock * getMBB() const
const BlockAddress * getBlockAddress() const
MachineOperandType getType() const
getType - Returns the MachineOperandType for this operand.
const char * getSymbolName() const
Register getReg() const
getReg - Returns the register number.
const ConstantFP * getFPImm() const
@ MO_Immediate
Immediate operand.
@ MO_ConstantPoolIndex
Address of indexed Constant in Constant Pool.
@ MO_GlobalAddress
Address of a global value.
@ MO_BlockAddress
Address of a basic block.
@ MO_MachineBasicBlock
MachineBasicBlock reference.
@ MO_Register
Register operand.
@ MO_ExternalSymbol
Name of external global symbol.
@ MO_JumpTableIndex
Address of indexed Jump Table for switch.
@ MO_FPImmediate
Floating-point immediate operand.
LLVM_ABI MachineInstr * getVRegDef(Register Reg) const
getVRegDef - Return the machine instr that defines the specified virtual register or null if none is ...
A Module instance is used to store all the information related to an LLVM module.
constexpr bool isValid() const
void setBound(unsigned V)
static const char * getRegisterName(MCRegister Reg)
void lower(const MachineInstr *MI, MCInst &OutMI, SPIRV::ModuleAnalysisInfo *MAI) const
AsmPrinter handler that emits NonSemantic.Shader.DebugInfo.100 (NSDI) instructions for the SPIR-V bac...
void emitNonSemanticDebugStrings(SPIRV::ModuleAnalysisInfo &MAI)
Emit OpString instructions for all NSDI file paths and basic type names into the debug section (secti...
void emitNonSemanticGlobalDebugInfo(SPIRV::ModuleAnalysisInfo &MAI)
Emit module-scope NSDI instructions (DebugSource, DebugCompilationUnit, DebugTypeBasic,...
void prepareModuleOutput(const SPIRVSubtarget &ST, SPIRV::ModuleAnalysisInfo &MAI)
Add SPV_KHR_non_semantic_info extension and NonSemantic.Shader.DebugInfo.100 ext inst set entry to MA...
const SPIRVInstrInfo * getInstrInfo() const override
bool isAtLeastSPIRVVer(VersionTuple VerToCompareTo) const
SPIRVGlobalRegistry * getSPIRVGlobalRegistry() const
VersionTuple getSPIRVVersion() const
unsigned getBound() const
bool canUseExtension(SPIRV::Extension::Extension E) const
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
bool contains(ConstPtrType Ptr) const
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
Represent a constant reference to a string, i.e.
std::pair< StringRef, StringRef > split(char Separator) const
Split into two substrings around the first occurrence of a separator character.
Primary interface to the complete machine description for the target machine.
The instances of the Type class are immutable: once they are created, they are never changed.
Value * getOperand(unsigned i) const
LLVM_ABI void print(raw_ostream &O, bool IsForDebug=false) const
Implement operator<< on Value.
LLVM_ABI const Value * stripPointerCasts() const
Strip off pointer casts, all-zero GEPs and address space casts.
unsigned getMajor() const
Retrieve the major version number.
std::optional< unsigned > getMinor() const
Retrieve the minor version number, if provided.
std::pair< iterator, bool > insert(const ValueT &V)
This class implements an extremely fast bulk output stream that can only output to a stream.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
@ Fast
Attempts to make calls as fast as possible (e.g.
@ C
The default llvm calling convention, compatible with C.
ValuesClass values(OptsTy... Options)
Helper to build a ValuesClass by forwarding a variable number of arguments as an initializer list to ...
initializer< Ty > init(const Ty &Val)
NodeAddr< NodeBase * > Node
This is an optimization pass for GlobalISel generic memory operations.
void addStringImm(StringRef Str, MCInst &Inst)
Target & getTheSPIRV32Target()
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
DenseMap< Value *, Constant * > ConstMap
LLVM_ABI bool getConstantStringInfo(const Value *V, StringRef &Str, bool TrimAtNul=true)
This function computes the length of a null-terminated C string pointed to by V.
std::string getExtInstSetName(SPIRV::InstructionSet::InstructionSet Set)
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Value
MachineInstr * getImm(const MachineOperand &MO, const MachineRegisterInfo *MRI)
LLVM_ABI void report_fatal_error(Error Err, bool gen_crash_diag=true)
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
std::string getSymbolicOperandMnemonic(SPIRV::OperandCategory::OperandCategory Category, int32_t Value)
bool isEntryPoint(const Function &F)
Target & getTheSPIRV64Target()
Target & getTheSPIRVLogicalTarget()
DWARFExpression::Operation Op
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Type * getMDOperandAsType(const MDNode *N, unsigned I)
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
RegisterAsmPrinter - Helper template for registering a target specific assembly printer,...
static size_t computeFPFastMathDefaultInfoVecIndex(size_t BitWidth)
MCRegister getGlobalObjReg(const GlobalObject *GO)