43#define DEBUG_TYPE "asm-printer"
52 std::unique_ptr<MCStreamer> Streamer)
53 :
AsmPrinter(TM, std::move(Streamer),
ID), ModuleSectionsEmitted(
false),
54 ST(
nullptr),
TII(
nullptr), MAI(
nullptr) {}
56 bool ModuleSectionsEmitted;
60 StringRef getPassName()
const override {
return "SPIRV Assembly Printer"; }
65 void outputMCInst(
MCInst &Inst);
68 void outputGlobalRequirements();
69 void outputEntryPoints();
70 void outputDebugSourceAndStrings(
const Module &M);
71 void outputOpExtInstImports(
const Module &M);
72 void outputOpMemoryModel();
73 void outputOpFunctionEnd();
74 void outputExtFuncDecls();
76 SPIRV::ExecutionMode::ExecutionMode EM,
77 unsigned ExpectMDOps, int64_t DefVal);
78 void outputExecutionModeFromNumthreadsAttribute(
80 SPIRV::ExecutionMode::ExecutionMode EM);
81 void outputExecutionMode(
const Module &M);
82 void outputAnnotations(
const Module &M);
83 void outputModuleSections();
84 void outputFPFastMathDefaultInfo();
86 return MF->getFunction()
92 void emitFunctionEntryLabel()
override {}
93 void emitFunctionHeader()
override;
94 void emitFunctionBodyStart()
override {}
95 void emitFunctionBodyEnd()
override;
100 void emitEndOfAsmFile(
Module &M)
override;
101 bool doInitialization(
Module &M)
override;
111void SPIRVAsmPrinter::getAnalysisUsage(
AnalysisUsage &AU)
const {
118void SPIRVAsmPrinter::emitEndOfAsmFile(
Module &M) {
119 if (ModuleSectionsEmitted ==
false) {
120 outputModuleSections();
121 ModuleSectionsEmitted =
true;
124 ST =
static_cast<const SPIRVTargetMachine &
>(
TM).getSubtargetImpl();
126 uint32_t Major = SPIRVVersion.
getMajor();
127 uint32_t Minor = SPIRVVersion.
getMinor().value_or(0);
130 unsigned Bound = 2 * (ST->
getBound() + 1) + NLabels;
131 if (MCAssembler *Asm = OutStreamer->getAssemblerPtr())
132 static_cast<SPIRVObjectWriter &
>(
Asm->getWriter())
133 .setBuildVersion(Major, Minor, Bound);
140void SPIRVAsmPrinter::cleanUp(
Module &M) {
142 for (StringRef GVName : {
"llvm.global_ctors",
"llvm.global_dtors",
143 "llvm.used",
"llvm.compiler.used"}) {
144 if (GlobalVariable *GV =
M.getNamedGlobal(GVName))
149void SPIRVAsmPrinter::emitFunctionHeader() {
150 if (ModuleSectionsEmitted ==
false) {
151 outputModuleSections();
152 ModuleSectionsEmitted =
true;
155 ST = &MF->getSubtarget<SPIRVSubtarget>();
159 if (isVerbose() && !isHidden()) {
160 OutStreamer->getCommentOS()
161 <<
"-- Begin function "
165 auto Section = getObjFileLowering().SectionForGlobal(&
F, TM);
166 MF->setSection(Section);
169void SPIRVAsmPrinter::outputOpFunctionEnd() {
170 MCInst FunctionEndInst;
171 FunctionEndInst.
setOpcode(SPIRV::OpFunctionEnd);
172 outputMCInst(FunctionEndInst);
175void SPIRVAsmPrinter::emitFunctionBodyEnd() {
177 outputOpFunctionEnd();
180void SPIRVAsmPrinter::emitOpLabel(
const MachineBasicBlock &
MBB) {
188 outputMCInst(LabelInst);
193void SPIRVAsmPrinter::emitBasicBlockStart(
const MachineBasicBlock &
MBB) {
201 for (
const MachineInstr &
MI :
MBB)
202 if (
MI.getOpcode() == SPIRV::OpFunction)
210void SPIRVAsmPrinter::printOperand(
const MachineInstr *
MI,
int OpNum,
212 const MachineOperand &MO =
MI->getOperand(OpNum);
252bool SPIRVAsmPrinter::PrintAsmOperand(
const MachineInstr *
MI,
unsigned OpNo,
253 const char *ExtraCode, raw_ostream &O) {
254 if (ExtraCode && ExtraCode[0])
263 return TII->isHeaderInstr(*
MI) ||
MI->getOpcode() == SPIRV::OpFunction ||
264 MI->getOpcode() == SPIRV::OpFunctionParameter;
267void SPIRVAsmPrinter::outputMCInst(MCInst &Inst) {
268 OutStreamer->emitInstruction(Inst, *OutContext.getSubtargetInfo());
271void SPIRVAsmPrinter::outputInstruction(
const MachineInstr *
MI) {
272 SPIRVMCInstLower MCInstLowering;
274 MCInstLowering.
lower(
MI, TmpInst, MAI);
275 outputMCInst(TmpInst);
278void SPIRVAsmPrinter::emitInstruction(
const MachineInstr *
MI) {
279 SPIRV_MC::verifyInstructionPredicates(
MI->getOpcode(),
280 getSubtargetInfo().getFeatureBits());
282 if (!MAI->getSkipEmission(
MI))
283 outputInstruction(
MI);
286 const MachineInstr *NextMI =
MI->getNextNode();
289 assert(
MI->getParent()->getNumber() == MF->front().getNumber() &&
290 "OpFunction is not in the front MBB of MF");
291 emitOpLabel(*
MI->getParent());
295void SPIRVAsmPrinter::outputModuleSection(SPIRV::ModuleSectionType MSType) {
296 for (
const MachineInstr *
MI : MAI->getMSInstrs(MSType))
297 outputInstruction(
MI);
300void SPIRVAsmPrinter::outputDebugSourceAndStrings(
const Module &M) {
302 for (
auto &Str : MAI->SrcExt) {
304 Inst.
setOpcode(SPIRV::OpSourceExtension);
309 outputModuleSection(SPIRV::MB_DebugStrings);
319void SPIRVAsmPrinter::outputOpExtInstImports(
const Module &M) {
320 for (
auto &CU : MAI->ExtInstSetMap) {
321 unsigned Set = CU.first;
322 MCRegister
Reg = CU.second;
327 static_cast<SPIRV::InstructionSet::InstructionSet
>(Set)),
333void SPIRVAsmPrinter::outputOpMemoryModel() {
345void SPIRVAsmPrinter::outputEntryPoints() {
347 DenseSet<MCRegister> InterfaceIDs;
348 for (
const MachineInstr *
MI : MAI->GlobalVarList) {
349 assert(
MI->getOpcode() == SPIRV::OpVariable);
350 auto SC =
static_cast<SPIRV::StorageClass::StorageClass
>(
357 SC == SPIRV::StorageClass::Input || SC == SPIRV::StorageClass::Output) {
358 const MachineFunction *MF =
MI->getMF();
359 MCRegister
Reg = MAI->getRegisterAlias(MF,
MI->getOperand(0).getReg());
365 for (
const MachineInstr *
MI : MAI->getMSInstrs(SPIRV::MB_EntryPoints)) {
366 SPIRVMCInstLower MCInstLowering;
368 MCInstLowering.
lower(
MI, TmpInst, MAI);
369 for (MCRegister
Reg : InterfaceIDs) {
373 outputMCInst(TmpInst);
378void SPIRVAsmPrinter::outputGlobalRequirements() {
380 MAI->Reqs.checkSatisfiable(*ST);
382 for (
const auto &Cap : MAI->Reqs.getMinimalCapabilities()) {
390 for (
const auto &Ext : MAI->Reqs.getExtensions()) {
394 SPIRV::OperandCategory::ExtensionOperand, Ext),
401void SPIRVAsmPrinter::outputExtFuncDecls() {
403 auto I = MAI->getMSInstrs(SPIRV::MB_ExtFuncDecls).begin(),
404 E = MAI->getMSInstrs(SPIRV::MB_ExtFuncDecls).end();
405 for (;
I !=
E; ++
I) {
406 outputInstruction(*
I);
407 if ((
I + 1) ==
E || (*(
I + 1))->
getOpcode() == SPIRV::OpFunction)
408 outputOpFunctionEnd();
418 if (Ty->isDoubleTy())
421 switch (IntTy->getIntegerBitWidth()) {
435 Type *EleTy = VecTy->getElementType();
436 unsigned Size = VecTy->getNumElements();
458void SPIRVAsmPrinter::outputExecutionModeFromMDNode(
459 MCRegister
Reg, MDNode *Node, SPIRV::ExecutionMode::ExecutionMode EM,
460 unsigned ExpectMDOps, int64_t DefVal) {
468 unsigned NodeSz =
Node->getNumOperands();
469 if (ExpectMDOps > 0 && NodeSz < ExpectMDOps)
470 for (
unsigned i = NodeSz; i < ExpectMDOps; ++i)
475void SPIRVAsmPrinter::outputExecutionModeFromNumthreadsAttribute(
477 SPIRV::ExecutionMode::ExecutionMode EM) {
478 assert(Attr.
isValid() &&
"Function called with an invalid attribute.");
487 assert(NumThreads.size() == 3 &&
"invalid numthreads");
488 for (uint32_t i = 0; i < 3; ++i) {
490 [[maybe_unused]]
bool Result = NumThreads[i].getAsInteger(10, V);
491 assert(!Result &&
"Failed to parse numthreads");
498void SPIRVAsmPrinter::outputExecutionMode(
const Module &M) {
499 NamedMDNode *
Node =
M.getNamedMetadata(
"spirv.ExecutionMode");
501 for (
unsigned i = 0; i <
Node->getNumOperands(); i++) {
511 if (EM == SPIRV::ExecutionMode::FPFastMathDefault ||
512 EM == SPIRV::ExecutionMode::ContractionOff ||
513 EM == SPIRV::ExecutionMode::SignedZeroInfNanPreserve)
522 outputFPFastMathDefaultInfo();
524 for (
auto FI =
M.begin(),
E =
M.end(); FI !=
E; ++FI) {
530 MCRegister FReg = MAI->getFuncReg(&
F);
543 static_cast<unsigned>(SPIRV::ExecutionMode::OriginUpperLeft);
548 if (MDNode *Node =
F.getMetadata(
"reqd_work_group_size"))
549 outputExecutionModeFromMDNode(FReg, Node, SPIRV::ExecutionMode::LocalSize,
552 outputExecutionModeFromNumthreadsAttribute(
553 FReg, Attr, SPIRV::ExecutionMode::LocalSize);
554 if (MDNode *Node =
F.getMetadata(
"work_group_size_hint"))
555 outputExecutionModeFromMDNode(FReg, Node,
556 SPIRV::ExecutionMode::LocalSizeHint, 3, 1);
557 if (MDNode *Node =
F.getMetadata(
"intel_reqd_sub_group_size"))
558 outputExecutionModeFromMDNode(FReg, Node,
559 SPIRV::ExecutionMode::SubgroupSize, 0, 0);
560 if (MDNode *Node =
F.getMetadata(
"vec_type_hint")) {
564 unsigned EM =
static_cast<unsigned>(SPIRV::ExecutionMode::VecTypeHint);
570 if (ST->
isKernel() && !
M.getNamedMetadata(
"spirv.ExecutionMode") &&
571 !
M.getNamedMetadata(
"opencl.enable.FP_CONTRACT")) {
589 std::vector<const MachineInstr *> SPIRVFloatTypes;
590 const MachineInstr *ConstZero =
nullptr;
591 for (
const MachineInstr *
MI :
592 MAI->getMSInstrs(SPIRV::MB_TypeConstVars)) {
595 if (OpCode != SPIRV::OpTypeFloat && OpCode != SPIRV::OpConstantNull)
599 if (OpCode == SPIRV::OpTypeFloat) {
601 const unsigned OpTypeFloatSize =
MI->getOperand(1).getImm();
602 if (OpTypeFloatSize != 16 && OpTypeFloatSize != 32 &&
603 OpTypeFloatSize != 64) {
606 SPIRVFloatTypes.push_back(
MI);
609 const MachineRegisterInfo &
MRI =
MI->getMF()->getRegInfo();
610 MachineInstr *TypeMI =
MRI.getVRegDef(
MI->getOperand(1).getReg());
624 for (
const MachineInstr *
MI : SPIRVFloatTypes) {
626 Inst.
setOpcode(SPIRV::OpExecutionModeId);
629 static_cast<unsigned>(SPIRV::ExecutionMode::FPFastMathDefault);
631 const MachineFunction *MF =
MI->getMF();
633 MAI->getRegisterAlias(MF,
MI->getOperand(0).getReg());
635 assert(ConstZero &&
"There should be a constant zero.");
636 MCRegister ConstReg = MAI->getRegisterAlias(
646 static_cast<unsigned>(SPIRV::ExecutionMode::ContractionOff);
654void SPIRVAsmPrinter::outputAnnotations(
const Module &M) {
655 outputModuleSection(SPIRV::MB_Annotations);
657 for (
auto F =
M.global_begin(),
E =
M.global_end();
F !=
E; ++
F) {
658 if ((*F).getName() !=
"llvm.global.annotations")
660 const GlobalVariable *
V = &(*F);
670 MCRegister
Reg = MAI->getFuncReg(Func);
673 raw_string_ostream OS(DiagMsg);
674 AnnotatedVar->
print(OS);
675 DiagMsg =
"Unknown function in llvm.global.annotations: " + DiagMsg;
683 StringRef AnnotationString;
684 [[maybe_unused]]
bool Success =
690 unsigned Dec =
static_cast<unsigned>(SPIRV::Decoration::UserSemantic);
698void SPIRVAsmPrinter::outputFPFastMathDefaultInfo() {
701 std::vector<const MachineInstr *> SPIRVFloatTypes;
703 std::unordered_map<int, const MachineInstr *>
ConstMap;
704 for (
const MachineInstr *
MI : MAI->getMSInstrs(SPIRV::MB_TypeConstVars)) {
707 if (OpCode != SPIRV::OpTypeFloat && OpCode != SPIRV::OpConstantI &&
708 OpCode != SPIRV::OpConstantNull)
712 if (OpCode == SPIRV::OpTypeFloat) {
713 SPIRVFloatTypes.push_back(
MI);
716 const MachineRegisterInfo &
MRI =
MI->getMF()->getRegInfo();
717 MachineInstr *TypeMI =
MRI.getVRegDef(
MI->getOperand(1).getReg());
718 if (!TypeMI || TypeMI->
getOpcode() != SPIRV::OpTypeInt ||
722 if (OpCode == SPIRV::OpConstantI)
729 for (
const auto &[Func, FPFastMathDefaultInfoVec] :
730 MAI->FPFastMathDefaultInfoMap) {
731 if (FPFastMathDefaultInfoVec.empty())
734 for (
const MachineInstr *
MI : SPIRVFloatTypes) {
735 unsigned OpTypeFloatSize =
MI->getOperand(1).getImm();
738 assert(Index < FPFastMathDefaultInfoVec.size() &&
739 "Index out of bounds for FPFastMathDefaultInfoVec");
740 const auto &FPFastMathDefaultInfo = FPFastMathDefaultInfoVec[
Index];
741 assert(FPFastMathDefaultInfo.Ty &&
742 "Expected target type for FPFastMathDefaultInfo");
743 assert(FPFastMathDefaultInfo.Ty->getScalarSizeInBits() ==
745 "Mismatched float type size");
747 Inst.
setOpcode(SPIRV::OpExecutionModeId);
748 MCRegister FuncReg = MAI->getFuncReg(Func);
754 MAI->getRegisterAlias(
MI->getMF(),
MI->getOperand(0).getReg());
756 unsigned Flags = FPFastMathDefaultInfo.FastMathFlags;
757 if (FPFastMathDefaultInfo.ContractionOff &&
758 (Flags & SPIRV::FPFastMathMode::AllowContract))
760 "Conflicting FPFastMathFlags: ContractionOff and AllowContract");
762 if (FPFastMathDefaultInfo.SignedZeroInfNanPreserve &&
764 (SPIRV::FPFastMathMode::NotNaN | SPIRV::FPFastMathMode::NotInf |
765 SPIRV::FPFastMathMode::NSZ))) {
766 if (FPFastMathDefaultInfo.FPFastMathDefault)
768 "SignedZeroInfNanPreserve but at least one of "
769 "NotNaN/NotInf/NSZ is enabled.");
773 if (Flags == SPIRV::FPFastMathMode::None &&
774 !FPFastMathDefaultInfo.ContractionOff &&
775 !FPFastMathDefaultInfo.SignedZeroInfNanPreserve &&
776 !FPFastMathDefaultInfo.FPFastMathDefault)
783 "Mode operand of FPFastMathDefault execution mode.");
784 const MachineInstr *ConstMI = It->second;
785 MCRegister ConstReg = MAI->getRegisterAlias(
793void SPIRVAsmPrinter::outputModuleSections() {
794 const Module *
M = MMI->getModule();
796 ST =
static_cast<const SPIRVTargetMachine &
>(
TM).getSubtargetImpl();
799 assert(ST &&
TII && MAI && M &&
"Module analysis is required");
803 outputGlobalRequirements();
805 outputOpExtInstImports(*M);
807 outputOpMemoryModel();
812 outputExecutionMode(*M);
815 outputDebugSourceAndStrings(*M);
817 outputModuleSection(SPIRV::MB_DebugNames);
819 outputModuleSection(SPIRV::MB_DebugModuleProcessed);
822 outputModuleSection(SPIRV::MB_AliasingInsts);
824 outputAnnotations(*M);
829 outputModuleSection(SPIRV::MB_TypeConstVars);
831 outputModuleSection(SPIRV::MB_NonSemanticGlobalDI);
833 outputExtFuncDecls();
838bool SPIRVAsmPrinter::doInitialization(
Module &M) {
839 ModuleSectionsEmitted =
false;
844char SPIRVAsmPrinter::ID = 0;
851LLVMInitializeSPIRVAsmPrinter() {
unsigned const MachineRegisterInfo * MRI
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
#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")
static TableGen::Emitter::OptClass< SkeletonEmitter > X("gen-skeleton-class", "Generate example skeleton class")
static std::optional< unsigned > getOpcode(ArrayRef< VPValue * > Values)
Returns the opcode of Values or ~0 if they do not all agree.
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 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.
A Module instance is used to store all the information related to an LLVM module.
constexpr bool isValid() const
static const char * getRegisterName(MCRegister Reg)
void lower(const MachineInstr *MI, MCInst &OutMI, SPIRV::ModuleAnalysisInfo *MAI) const
const SPIRVInstrInfo * getInstrInfo() const override
bool isAtLeastSPIRVVer(VersionTuple VerToCompareTo) 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.
StringRef - 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.
@ C
The default llvm calling convention, compatible with C.
NodeAddr< NodeBase * > Node
NodeAddr< FuncNode * > Func
This is an optimization pass for GlobalISel generic memory operations.
FunctionAddr VTableAddr Value
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)
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...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
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)
void addStringImm(const StringRef &Str, MCInst &Inst)
RegisterAsmPrinter - Helper template for registering a target specific assembly printer,...
static struct SPIRV::ModuleAnalysisInfo MAI
static size_t computeFPFastMathDefaultInfoVecIndex(size_t BitWidth)
MCRegister getFuncReg(const Function *F)