}
SPIRVEntry *LLVMToSPIRVDbgTran::transDbgInlinedAt(const DILocation *Loc) {
- using namespace SPIRVDebug::Operand::InlinedAt;
+ // There is a Column operand in NonSemantic.Shader.200 spec
+ if (BM->getDebugInfoEIS() == SPIRVEIS_NonSemantic_Shader_DebugInfo_200)
+ return transDbgInlinedAtNonSemanticShader200(Loc);
+ using namespace SPIRVDebug::Operand::InlinedAt::OpenCL;
SPIRVWordVec Ops(MinOperandCount);
Ops[LineIdx] = Loc->getLine();
Ops[ScopeIdx] = getScope(Loc->getScope())->getId();
return BM->addDebugInfo(SPIRVDebug::InlinedAt, getVoidTy(), Ops);
}
+SPIRVEntry *LLVMToSPIRVDbgTran::transDbgInlinedAtNonSemanticShader200(
+ const DILocation *Loc) {
+ using namespace SPIRVDebug::Operand::InlinedAt::NonSemantic;
+ SPIRVWordVec Ops(MinOperandCount);
+ Ops[LineIdx] = Loc->getLine();
+ Ops[ColumnIdx] = Loc->getColumn();
+ transformToConstant(Ops, {LineIdx, ColumnIdx});
+ Ops[ScopeIdx] = getScope(Loc->getScope())->getId();
+ if (DILocation *IA = Loc->getInlinedAt())
+ Ops.push_back(transDbgEntry(IA)->getId());
+ return BM->addDebugInfo(SPIRVDebug::InlinedAt, getVoidTy(), Ops);
+}
+
template <class T>
SPIRVExtInst *LLVMToSPIRVDbgTran::getSource(const T *DIEntry) {
const std::string FileName = getFullPath(DIEntry);
SPIRVEntry *transDebugLoc(const DebugLoc &Loc, SPIRVBasicBlock *BB,
SPIRVInstruction *InsertBefore = nullptr);
SPIRVEntry *transDbgInlinedAt(const DILocation *D);
+ SPIRVEntry *transDbgInlinedAtNonSemanticShader200(const DILocation *D);
template <class T> SPIRVExtInst *getSource(const T *DIEntry);
SPIRVEntry *transDbgFileType(const DIFile *F);
}
MDNode *SPIRVToLLVMDbgTran::transDebugInlined(const SPIRVExtInst *DebugInst) {
- using namespace SPIRVDebug::Operand::InlinedAt;
+ // There is a Column operand in NonSemantic.Shader.200 spec
+ if (DebugInst->getExtSetKind() ==
+ SPIRV::SPIRVEIS_NonSemantic_Shader_DebugInfo_200)
+ return transDebugInlinedNonSemanticShader200(DebugInst);
+
+ using namespace SPIRVDebug::Operand::InlinedAt::OpenCL;
SPIRVWordVec Ops = DebugInst->getArguments();
assert(Ops.size() >= MinOperandCount && "Invalid number of operands");
SPIRVWord Line =
return DILocation::getDistinct(M->getContext(), Line, Col, Scope, InlinedAt);
}
+MDNode *SPIRVToLLVMDbgTran::transDebugInlinedNonSemanticShader200(
+ const SPIRVExtInst *DebugInst) {
+ using namespace SPIRVDebug::Operand::InlinedAt::NonSemantic;
+ SPIRVWordVec Ops = DebugInst->getArguments();
+ assert(Ops.size() >= MinOperandCount && "Invalid number of operands");
+ SPIRVWord Line =
+ getConstantValueOrLiteral(Ops, LineIdx, DebugInst->getExtSetKind());
+ unsigned Col =
+ getConstantValueOrLiteral(Ops, ColumnIdx, DebugInst->getExtSetKind());
+ DILocalScope *Scope =
+ cast<DILocalScope>(getScope(BM->getEntry(Ops[ScopeIdx])));
+ DILocation *InlinedAt = nullptr;
+ if (Ops.size() > InlinedIdx) {
+ InlinedAt =
+ transDebugInst<DILocation>(BM->get<SPIRVExtInst>(Ops[InlinedIdx]));
+ }
+ return DILocation::getDistinct(M->getContext(), Line, Col, Scope, InlinedAt);
+}
+
void SPIRVToLLVMDbgTran::finalize() {
if (!Enable)
return;
return *BuilderMap.begin()->second;
const SPIRVWordVec &Ops = DebugInst->getArguments();
SPIRVWord ParentScopeIdx = 0;
- if (!hasDbgInstParentScopeIdx(DebugInst->getExtOp(), ParentScopeIdx))
+ if (!hasDbgInstParentScopeIdx(DebugInst->getExtOp(), ParentScopeIdx,
+ DebugInst->getExtSetKind()))
return *BuilderMap.begin()->second;
if (SPIRVEntry *Scope = BM->getEntry(Ops[ParentScopeIdx])) {
DebugInst = static_cast<SPIRVExtInst *>(Scope);
llvm::DebugLoc transDebugScope(const SPIRVInstruction *Inst);
MDNode *transDebugInlined(const SPIRVExtInst *Inst);
+ MDNode *transDebugInlinedNonSemanticShader200(const SPIRVExtInst *Inst);
DICompileUnit *transCompilationUnit(const SPIRVExtInst *DebugInst,
const std::string CompilerVersion = "",
#ifndef SPIRV_DEBUG_H
#define SPIRV_DEBUG_H
+#include "SPIRVEnum.h"
#include "SPIRVUtil.h"
#include "spirv/unified1/spirv.hpp"
#include "spirv_internal.hpp"
}
namespace InlinedAt {
+namespace OpenCL {
enum {
LineIdx = 0,
ScopeIdx = 1,
InlinedIdx = 2,
MinOperandCount = 2
};
-}
+} // namespace OpenCL
+
+namespace NonSemantic {
+enum {
+ LineIdx = 0,
+ ColumnIdx = 1,
+ ScopeIdx = 2,
+ InlinedIdx = 3,
+ MinOperandCount = 3
+};
+} // namespace NonSemantic
+} // namespace ImportedEntity
namespace LocalVariable {
enum {
// helper function to get parent scope of debug instruction, to be used
// to determine with which compile unit the particular instruction relates
inline bool hasDbgInstParentScopeIdx(const uint32_t Kind,
- uint32_t &ParentScopeIdx) {
+ uint32_t &ParentScopeIdx,
+ const SPIRV::SPIRVExtInstSetKind ExtKind = SPIRV::SPIRVEIS_OpenCL) {
switch (Kind) {
case SPIRVDebug::Typedef:
ParentScopeIdx = Typedef::ParentIdx;
ParentScopeIdx = Scope::ScopeIdx;
return true;
case SPIRVDebug::InlinedAt:
- ParentScopeIdx = InlinedAt::ScopeIdx;
+ if (ExtKind == SPIRV::SPIRVEIS_NonSemantic_Shader_DebugInfo_200)
+ ParentScopeIdx = InlinedAt::NonSemantic::ScopeIdx;
+ else
+ ParentScopeIdx = InlinedAt::OpenCL::ScopeIdx;
return true;
case SPIRVDebug::LocalVariable:
ParentScopeIdx = LocalVariable::ParentIdx;
; RUN: llvm-as < %s -o %t.bc
; RUN: llvm-spirv %t.bc -o %t.spv
-; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o - | FileCheck %s
+; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o - | FileCheck %s --check-prefixes=CHECK,CHECK-DEFAULT
+
+; RUN: llvm-spirv %t.bc --spirv-debug-info-version=nonsemantic-shader-200 -o %t.spv
+; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o - | FileCheck %s --check-prefixes=CHECK,CHECK-200
; Check that the "inlinedAt" attribute of a DILocation references another
; DILocation that is marked as distinct. Note that the checks for distinct
; DILocations do not include the column number as SPIR-V does not allow for
-; representing this info.
+; representing this info (except for NonSemantic.Shader.DebugInfo.200). For
+; this specification we check that the column number is preserved during
+; translation.
; Built with clang -O -g from the source:
; bool f();
!16 = !DILocalVariable(name: "b", scope: !12, file: !1, line: 3, type: !17)
!17 = !DIBasicType(name: "bool", size: 8, encoding: DW_ATE_boolean)
!18 = distinct !DILocation(line: 9, column: 15, scope: !19, inlinedAt: !23)
-; CHECK: ![[loc1]] = distinct !DILocation(line: 9, scope: !{{.*}}, inlinedAt: ![[loc2:[0-9]+]])
+; CHECK-DEFAULT: ![[loc1]] = distinct !DILocation(line: 9, scope: !{{.*}}, inlinedAt: ![[loc2:[0-9]+]])
+; CHECK-200: ![[loc1]] = distinct !DILocation(line: 9, column: 15, scope: !{{.*}}, inlinedAt: ![[loc2:[0-9]+]])
!19 = distinct !DILexicalBlock(scope: !20, file: !1, line: 9, column: 11)
!20 = distinct !DISubprogram(name: "f2", linkageName: "_Z2f2v", scope: !1, file: !1, line: 8, type: !14, scopeLine: 8, flags: DIFlagPrototyped, spFlags: DISPFlagDefinition | DISPFlagOptimized, unit: !0, retainedNodes: !21)
!21 = !{!22}
!22 = !DILocalVariable(name: "i", scope: !19, file: !1, line: 9, type: !10)
!23 = distinct !DILocation(line: 15, column: 3, scope: !7)
-; CHECK: ![[loc2]] = distinct !DILocation(line: 15, scope: !{{.*}})
+; CHECK-DEFAULT: ![[loc2]] = distinct !DILocation(line: 15, scope: !{{.*}})
+; CHECK-200: ![[loc2]] = distinct !DILocation(line: 15, column: 3, scope: !{{.*}})
!24 = !DILocation(line: 3, column: 12, scope: !12, inlinedAt: !18)
; CHECK: !{{.*}} = !DILocation(line: 3, column: 12, scope: !{{.*}}, inlinedAt: ![[loc1]])
!25 = !DILocation(line: 16, column: 1, scope: !7)