28#define DEBUG_TYPE "spirv-nonsemantic-debug-info"
40 bool IsGlobalDIEmitted =
false;
48 "SPIRV NonSemantic.Shader.DebugInfo.100 emitter",
false,
false)
97 IsGlobalDIEmitted =
false;
105 int64_t DwarfVersion = 0;
106 int64_t DebugInfoVersion = 0;
113 getAnalysis<MachineModuleInfoWrapperPass>().getMMI();
115 Context = &
M->getContext();
116 const NamedMDNode *DbgCu =
M->getNamedMetadata(
"llvm.dbg.cu");
124 File->getFilename());
128 const NamedMDNode *ModuleFlags =
M->getNamedMetadata(
"llvm.module.flags");
129 for (
const auto *
Op : ModuleFlags->
operands()) {
131 if (MaybeStrOp.
equalsStr(
"Dwarf Version"))
134 cast<ConstantAsMetadata>(
Op->getOperand(2))->getValue())
136 else if (MaybeStrOp.
equalsStr(
"Debug Info Version"))
139 cast<ConstantAsMetadata>(
Op->getOperand(2))->getValue())
150 if (
auto *BasicType =
151 dyn_cast<DIBasicType>(LocalVariable->
getType())) {
152 BasicTypes.
insert(BasicType);
153 }
else if (
auto *DerivedType =
154 dyn_cast<DIDerivedType>(LocalVariable->
getType())) {
155 if (DerivedType->getTag() == dwarf::DW_TAG_pointer_type) {
156 PointerDerivedTypes.
insert(DerivedType);
161 if (DerivedType->getBaseType())
163 cast<DIBasicType>(DerivedType->getBaseType()));
186 const auto EmitOpString = [&](
StringRef SR) {
187 const Register StrReg =
MRI.createVirtualRegister(&SPIRV::IDRegClass);
198 const auto EmitDIInstruction =
199 [&](SPIRV::NonSemanticExtInst::NonSemanticExtInst Inst,
200 std::initializer_list<Register>
Registers) {
202 MRI.createVirtualRegister(&SPIRV::IDRegClass);
205 MIRBuilder.buildInstr(SPIRV::OpExtInst)
208 .addImm(
static_cast<int64_t
>(
209 SPIRV::InstructionSet::NonSemantic_Shader_DebugInfo_100))
225 const Register DebugInfoVersionReg =
228 for (
unsigned Idx = 0;
Idx < LLVMSourceLanguages.
size(); ++
Idx) {
229 const Register FilePathStrReg = EmitOpString(FilePaths[
Idx]);
231 const Register DebugSourceResIdReg = EmitDIInstruction(
232 SPIRV::NonSemanticExtInst::DebugSource, {FilePathStrReg});
235 switch (LLVMSourceLanguages[
Idx]) {
236 case dwarf::DW_LANG_OpenCL:
237 SpirvSourceLanguage = SourceLanguage::OpenCL_C;
239 case dwarf::DW_LANG_OpenCL_CPP:
240 SpirvSourceLanguage = SourceLanguage::OpenCL_CPP;
242 case dwarf::DW_LANG_CPP_for_OpenCL:
243 SpirvSourceLanguage = SourceLanguage::CPP_for_OpenCL;
245 case dwarf::DW_LANG_GLSL:
246 SpirvSourceLanguage = SourceLanguage::GLSL;
248 case dwarf::DW_LANG_HLSL:
249 SpirvSourceLanguage = SourceLanguage::HLSL;
251 case dwarf::DW_LANG_SYCL:
252 SpirvSourceLanguage = SourceLanguage::SYCL;
254 case dwarf::DW_LANG_Zig:
255 SpirvSourceLanguage = SourceLanguage::Zig;
262 const Register DebugCompUnitResIdReg =
263 EmitDIInstruction(SPIRV::NonSemanticExtInst::DebugCompilationUnit,
264 {DebugInfoVersionReg, DwarfVersionReg,
265 DebugSourceResIdReg, SourceLanguageReg});
278 for (
auto *BasicType : BasicTypes) {
279 const Register BasicTypeStrReg = EmitOpString(BasicType->getName());
282 BasicType->getSizeInBits(), MIRBuilder, I32Ty,
false);
284 uint64_t AttributeEncoding = BaseTypeAttributeEncoding::Unspecified;
285 switch (BasicType->getEncoding()) {
286 case dwarf::DW_ATE_signed:
287 AttributeEncoding = BaseTypeAttributeEncoding::Signed;
289 case dwarf::DW_ATE_unsigned:
290 AttributeEncoding = BaseTypeAttributeEncoding::Unsigned;
292 case dwarf::DW_ATE_unsigned_char:
293 AttributeEncoding = BaseTypeAttributeEncoding::UnsignedChar;
295 case dwarf::DW_ATE_signed_char:
296 AttributeEncoding = BaseTypeAttributeEncoding::SignedChar;
298 case dwarf::DW_ATE_float:
299 AttributeEncoding = BaseTypeAttributeEncoding::Float;
301 case dwarf::DW_ATE_boolean:
302 AttributeEncoding = BaseTypeAttributeEncoding::Boolean;
304 case dwarf::DW_ATE_address:
305 AttributeEncoding = BaseTypeAttributeEncoding::Address;
308 const Register AttributeEncodingReg =
312 EmitDIInstruction(SPIRV::NonSemanticExtInst::DebugTypeBasic,
313 {BasicTypeStrReg, ConstIntBitwidthReg,
314 AttributeEncodingReg, I32ZeroReg});
315 BasicTypeRegPairs.
emplace_back(BasicType, BasicTypeReg);
318 if (PointerDerivedTypes.
size()) {
319 for (
const auto *PointerDerivedType : PointerDerivedTypes) {
321 assert(PointerDerivedType->getDWARFAddressSpace().has_value());
324 PointerDerivedType->getDWARFAddressSpace().value(),
326 MIRBuilder, I32Ty,
false);
330 const auto *MaybeNestedBasicType =
331 cast_or_null<DIBasicType>(PointerDerivedType->getBaseType());
332 if (MaybeNestedBasicType) {
333 for (
const auto &BasicTypeRegPair : BasicTypeRegPairs) {
334 const auto &[DefinedBasicType, BasicTypeReg] = BasicTypeRegPair;
335 if (DefinedBasicType == MaybeNestedBasicType) {
337 const Register DebugPointerTypeReg = EmitDIInstruction(
338 SPIRV::NonSemanticExtInst::DebugTypePointer,
339 {BasicTypeReg, StorageClassReg, I32ZeroReg});
344 EmitDIInstruction(SPIRV::NonSemanticExtInst::DebugInfoNone, {});
346 const Register DebugPointerTypeReg = EmitDIInstruction(
347 SPIRV::NonSemanticExtInst::DebugTypePointer,
348 {DebugInfoNoneReg, StorageClassReg, I32ZeroReg});
360 if (!IsGlobalDIEmitted) {
361 IsGlobalDIEmitted =
true;
362 Res = emitGlobalDI(MF);
unsigned const MachineRegisterInfo * MRI
Returns the sub type a function will return at a given Idx Should correspond to the result type of an ExtractValue instruction executed with just that one unsigned Idx
This file contains constants used for implementing Dwarf debug support.
const HexagonInstrInfo * TII
This file declares the MachineIRBuilder class.
unsigned const TargetRegisterInfo * TRI
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
SI Pre allocate WWM Registers
BaseTypeAttributeEncoding
This file defines the SmallPtrSet class.
This file defines the SmallString class.
This class represents an Operation in the Expression.
Record of a variable value-assignment, aka a non instruction representation of the dbg....
static constexpr LLT scalar(unsigned SizeInBits)
Get a low-level scalar or aggregate "bag of bits".
This is an important class for using LLVM in a threaded context.
Tracking metadata reference owned by Metadata.
bool equalsStr(StringRef Str) const
iterator getFirstTerminator()
Returns an iterator to the first terminator instruction of this basic block.
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Helper class to build MachineInstr.
bool constrainAllUses(const TargetInstrInfo &TII, const TargetRegisterInfo &TRI, const RegisterBankInfo &RBI) const
const MachineInstrBuilder & addUse(Register RegNo, unsigned Flags=0, unsigned SubReg=0) const
Add a virtual register use operand.
const MachineInstrBuilder & addDef(Register RegNo, unsigned Flags=0, unsigned SubReg=0) const
Add a virtual register definition operand.
Representation of each machine instruction.
This class contains meta information specific to a module.
const Module * getModule() const
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
A Module instance is used to store all the information related to an LLVM module.
iterator_range< op_iterator > operands()
static PassRegistry * getPassRegistry()
getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...
Holds all the information related to register banks.
Wrapper class representing virtual and physical registers.
void assignSPIRVTypeToVReg(SPIRVType *Type, Register VReg, const MachineFunction &MF)
Register getSPIRVTypeID(const SPIRVType *SpirvType) const
SPIRVType * getOrCreateSPIRVType(const Type *Type, MachineIRBuilder &MIRBuilder, SPIRV::AccessQualifier::AccessQualifier AQ=SPIRV::AccessQualifier::ReadWrite, bool EmitIR=true)
Register buildConstantInt(uint64_t Val, MachineIRBuilder &MIRBuilder, SPIRVType *SpvType, bool EmitIR=true, bool ZeroAsNull=true)
const SPIRVInstrInfo * getInstrInfo() const override
SPIRVGlobalRegistry * getSPIRVGlobalRegistry() const
const SPIRVRegisterInfo * getRegisterInfo() const override
const RegisterBankInfo * getRegBankInfo() const override
const SPIRVSubtarget * getSubtargetImpl() const
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
reference emplace_back(ArgTypes &&... Args)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
static Type * getVoidTy(LLVMContext &C)
static IntegerType * getInt32Ty(LLVMContext &C)
Stores all information relating to a compile unit, be it in its original instance in the object file ...
void append(SmallVectorImpl< char > &path, const Twine &a, const Twine &b="", const Twine &c="", const Twine &d="")
Append to path.
This is an optimization pass for GlobalISel generic memory operations.
MachineFunctionPass * createSPIRVEmitNonSemanticDIPass(SPIRVTargetMachine *TM)
SPIRV::StorageClass::StorageClass addressSpaceToStorageClass(unsigned AddrSpace, const SPIRVSubtarget &STI)
void initializeSPIRVEmitNonSemanticDIPass(PassRegistry &)
void addStringImm(const StringRef &Str, MCInst &Inst)
static auto filterDbgVars(iterator_range< simple_ilist< DbgRecord >::iterator > R)
Filter the DbgRecord range to DbgVariableRecord types only and downcast.
bool runOnMachineFunction(MachineFunction &MF) override
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...