Skip to content

Commit ed45b14

Browse files
Fznamznonvmaksimo
authored andcommitted
Implement SPV_INTEL_debug_module extension (#1089)
* Implement SPV_INTEL_debug_module extension Spec #3976 Original commit: KhronosGroup/SPIRV-LLVM-Translator@2b3a2f3
1 parent ec4d77e commit ed45b14

14 files changed

+308
-6
lines changed

llvm-spirv/include/LLVMSPIRVExtensions.inc

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,3 +39,4 @@ EXT(SPV_INTEL_fpga_dsp_control)
3939
EXT(SPV_INTEL_memory_access_aliasing)
4040
EXT(SPV_INTEL_fpga_invocation_pipelining_attributes)
4141
EXT(SPV_INTEL_token_type)
42+
EXT(SPV_INTEL_debug_module)

llvm-spirv/lib/SPIRV/LLVMToSPIRVDbgTran.cpp

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -343,6 +343,12 @@ SPIRVEntry *LLVMToSPIRVDbgTran::transDbgEntryImpl(const MDNode *MDN) {
343343
case dwarf::DW_TAG_imported_declaration:
344344
return transDbgImportedEntry(cast<DIImportedEntity>(DIEntry));
345345

346+
case dwarf::DW_TAG_module: {
347+
if (BM->isAllowedToUseExtension(ExtensionID::SPV_INTEL_debug_module))
348+
return transDbgModule(cast<DIModule>(DIEntry));
349+
return getDebugInfoNone();
350+
}
351+
346352
default:
347353
return getDebugInfoNone();
348354
}
@@ -812,9 +818,10 @@ LLVMToSPIRVDbgTran::transDbgGlobalVariable(const DIGlobalVariable *GV) {
812818
// Parent scope
813819
DIScope *Context = GV->getScope();
814820
SPIRVEntry *Parent = SPIRVCU;
815-
// Global variable may be declared in scope of a namespace or it may be a
816-
// static variable declared in scope of a function
817-
if (Context && (isa<DINamespace>(Context) || isa<DISubprogram>(Context)))
821+
// Global variable may be declared in scope of a namespace or imported module,
822+
// it may also be a static variable declared in scope of a function.
823+
if (Context && (isa<DINamespace>(Context) || isa<DISubprogram>(Context) ||
824+
isa<DIModule>(Context)))
818825
Parent = transDbgEntry(Context);
819826
Ops[ParentIdx] = Parent->getId();
820827

@@ -1035,3 +1042,20 @@ LLVMToSPIRVDbgTran::transDbgImportedEntry(const DIImportedEntity *IE) {
10351042
Ops[ParentIdx] = getScope(IE->getScope())->getId();
10361043
return BM->addDebugInfo(SPIRVDebug::ImportedEntity, getVoidTy(), Ops);
10371044
}
1045+
1046+
SPIRVEntry *LLVMToSPIRVDbgTran::transDbgModule(const DIModule *Module) {
1047+
using namespace SPIRVDebug::Operand::ModuleINTEL;
1048+
SPIRVWordVec Ops(OperandCount);
1049+
Ops[NameIdx] = BM->getString(Module->getName().str())->getId();
1050+
Ops[SourceIdx] = getSource(Module->getFile())->getId();
1051+
Ops[LineIdx] = Module->getLineNo();
1052+
Ops[ParentIdx] = getScope(Module->getScope())->getId();
1053+
Ops[ConfigMacrosIdx] =
1054+
BM->getString(Module->getConfigurationMacros().str())->getId();
1055+
Ops[IncludePathIdx] = BM->getString(Module->getIncludePath().str())->getId();
1056+
Ops[ApiNotesIdx] = BM->getString(Module->getAPINotesFile().str())->getId();
1057+
Ops[IsDeclIdx] = Module->getIsDecl();
1058+
BM->addExtension(ExtensionID::SPV_INTEL_debug_module);
1059+
BM->addCapability(spv::internal::CapabilityDebugInfoModuleINTEL);
1060+
return BM->addDebugInfo(SPIRVDebug::ModuleINTEL, getVoidTy(), Ops);
1061+
}

llvm-spirv/lib/SPIRV/LLVMToSPIRVDbgTran.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,9 @@ class LLVMToSPIRVDbgTran {
143143
// Imported declarations and modules
144144
SPIRVEntry *transDbgImportedEntry(const DIImportedEntity *IE);
145145

146+
// A module in programming language. Example - Fortran module, clang module.
147+
SPIRVEntry *transDbgModule(const DIModule *IE);
148+
146149
SPIRVModule *BM;
147150
Module *M;
148151
LLVMToSPIRVBase *SPIRVWriter;

llvm-spirv/lib/SPIRV/SPIRVToLLVMDbgTran.cpp

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -782,6 +782,8 @@ DINode *SPIRVToLLVMDbgTran::transImportedEntry(const SPIRVExtInst *DebugInst) {
782782
if (!Entity)
783783
return Builder.createImportedModule(
784784
Scope, static_cast<DIImportedEntity *>(nullptr), File, Line);
785+
if (DIModule *DM = dyn_cast<DIModule>(Entity))
786+
return Builder.createImportedModule(Scope, DM, File, Line);
785787
if (DIImportedEntity *IE = dyn_cast<DIImportedEntity>(Entity))
786788
return Builder.createImportedModule(Scope, IE, File, Line);
787789
if (DINamespace *NS = dyn_cast<DINamespace>(Entity))
@@ -798,6 +800,23 @@ DINode *SPIRVToLLVMDbgTran::transImportedEntry(const SPIRVExtInst *DebugInst) {
798800
llvm_unreachable("Unexpected kind of imported entity!");
799801
}
800802

803+
DINode *SPIRVToLLVMDbgTran::transModule(const SPIRVExtInst *DebugInst) {
804+
using namespace SPIRVDebug::Operand::ModuleINTEL;
805+
const SPIRVWordVec &Ops = DebugInst->getArguments();
806+
assert(Ops.size() >= OperandCount && "Invalid number of operands");
807+
DIScope *Scope = getScope(BM->getEntry(Ops[ParentIdx]));
808+
unsigned Line = Ops[LineIdx];
809+
DIFile *File = getFile(Ops[SourceIdx]);
810+
StringRef Name = getString(Ops[NameIdx]);
811+
StringRef ConfigMacros = getString(Ops[ConfigMacrosIdx]);
812+
StringRef IncludePath = getString(Ops[IncludePathIdx]);
813+
StringRef ApiNotes = getString(Ops[ApiNotesIdx]);
814+
bool IsDecl = Ops[IsDeclIdx];
815+
816+
return Builder.createModule(Scope, Name, ConfigMacros, IncludePath, ApiNotes,
817+
File, Line, IsDecl);
818+
}
819+
801820
MDNode *SPIRVToLLVMDbgTran::transExpression(const SPIRVExtInst *DebugInst) {
802821
const SPIRVWordVec &Args = DebugInst->getArguments();
803822
std::vector<int64_t> Ops;
@@ -894,6 +913,9 @@ MDNode *SPIRVToLLVMDbgTran::transDebugInstImpl(const SPIRVExtInst *DebugInst) {
894913
case SPIRVDebug::ImportedEntity:
895914
return transImportedEntry(DebugInst);
896915

916+
case SPIRVDebug::ModuleINTEL:
917+
return transModule(DebugInst);
918+
897919
case SPIRVDebug::Operation: // To be translated with transExpression
898920
case SPIRVDebug::Source: // To be used by other instructions
899921
return nullptr;

llvm-spirv/lib/SPIRV/SPIRVToLLVMDbgTran.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,8 @@ class SPIRVToLLVMDbgTran {
143143

144144
DINode *transImportedEntry(const SPIRVExtInst *DebugInst);
145145

146+
DINode *transModule(const SPIRVExtInst *DebugInst);
147+
146148
MDNode *transExpression(const SPIRVExtInst *DebugInst);
147149

148150
SPIRVModule *BM;

llvm-spirv/lib/SPIRV/libSPIRV/SPIRV.debug.h

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,8 @@ enum Instruction {
4747
MacroUndef = 33,
4848
ImportedEntity = 34,
4949
Source = 35,
50-
InstCount = 36
50+
ModuleINTEL = 36,
51+
InstCount = 37
5152
};
5253

5354
enum Flag {
@@ -769,6 +770,20 @@ enum {
769770
};
770771
}
771772

773+
namespace ModuleINTEL {
774+
enum {
775+
NameIdx = 0,
776+
SourceIdx = 1,
777+
LineIdx = 2,
778+
ParentIdx = 3,
779+
ConfigMacrosIdx = 4,
780+
IncludePathIdx = 5,
781+
ApiNotesIdx = 6,
782+
IsDeclIdx = 7,
783+
OperandCount = 8
784+
};
785+
}
786+
772787
} // namespace Operand
773788
} // namespace SPIRVDebug
774789

llvm-spirv/lib/SPIRV/libSPIRV/SPIRVExtInst.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -253,6 +253,7 @@ template <> inline void SPIRVMap<SPIRVDebugExtOpKind, std::string>::init() {
253253
add(SPIRVDebug::NoScope, "DebugNoScope");
254254
add(SPIRVDebug::InlinedAt, "DebugInlinedAt");
255255
add(SPIRVDebug::ImportedEntity, "DebugImportedEntity");
256+
add(SPIRVDebug::ModuleINTEL, "DebugModuleINTEL");
256257
add(SPIRVDebug::Expression, "DebugExpression");
257258
add(SPIRVDebug::Operation, "DebugOperation");
258259
}

llvm-spirv/lib/SPIRV/libSPIRV/SPIRVNameMapEnum.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -573,8 +573,8 @@ template <> inline void SPIRVMap<Capability, std::string>::init() {
573573
add(internal::CapabilityFPGAInvocationPipeliningAttributesINTEL,
574574
"FPGAInvocationPipeliningAttributesINTEL");
575575
add(internal::CapabilityTokenTypeINTEL, "TokenTypeINTEL");
576-
577576
add(CapabilityMax, "Max");
577+
add(internal::CapabilityDebugInfoModuleINTEL, "DebugInfoModuleINTEL");
578578
}
579579
SPIRV_DEF_NAMEMAP(Capability, SPIRVCapabilityNameMap)
580580

llvm-spirv/lib/SPIRV/libSPIRV/spirv_internal.hpp

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,8 @@ enum InternalCapability {
6262
ICapFPGAInvocationPipeliningAttributesINTEL = 5916,
6363
ICapFastCompositeINTEL = 6093,
6464
ICapOptNoneINTEL = 6094,
65-
ICapTokenTypeINTEL = 6112
65+
ICapTokenTypeINTEL = 6112,
66+
ICapDebugInfoModuleINTEL = 6114
6667
};
6768

6869
enum InternalFunctionControlMask { IFunctionControlOptNoneINTELMask = 0x10000 };
@@ -115,6 +116,8 @@ constexpr Capability CapabilityFPGAInvocationPipeliningAttributesINTEL =
115116
static_cast<Capability>(ICapFPGAInvocationPipeliningAttributesINTEL);
116117
constexpr Capability CapabilityTokenTypeINTEL =
117118
static_cast<Capability>(ICapTokenTypeINTEL);
119+
constexpr Capability CapabilityDebugInfoModuleINTEL =
120+
static_cast<Capability>(ICapDebugInfoModuleINTEL);
118121

119122
constexpr FunctionControlMask FunctionControlOptNoneINTELMask =
120123
static_cast<FunctionControlMask>(IFunctionControlOptNoneINTELMask);

llvm-spirv/test/DebugInfo/DebugInfoNoneEntity.ll

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@
44
; RUN: llvm-spirv %t.bc -o %t.spv
55
; RUN: llvm-spirv -r %t.spv -o %t.rev.bc
66

7+
; RUN: llvm-spirv -spirv-ext=+SPV_INTEL_debug_module %t.bc -o %t.spv
8+
; RUN: llvm-spirv -r %t.spv -o %t.rev.bc
9+
710
source_filename = "llvm-link"
811
target datalayout = "e-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-n8:16:32:64"
912
target triple = "spir64"
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
; ModuleID = '/Volumes/Data/apple-internal/llvm/tools/clang/test/Modules/debug-info-moduleimport.m'
2+
; RUN: llvm-as < %s -o %t.bc
3+
; RUN: llvm-spirv --spirv-ext=+SPV_INTEL_debug_module %t.bc -o %t.spv
4+
; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o %t.ll
5+
6+
; RUN: llc -mtriple=x86_64-apple-macosx %t.ll -accel-tables=Dwarf -o %t -filetype=obj
7+
; RUN: llvm-dwarfdump -debug-info %t | FileCheck %s
8+
; RUN: llvm-dwarfdump -verify %t
9+
10+
; RUN: llvm-spirv --spirv-ext=+SPV_INTEL_debug_module %t.bc -spirv-text -o - | FileCheck %s --check-prefix CHECK-SPIRV
11+
12+
; CHECK: DW_TAG_compile_unit
13+
; CHECK-NOT: DW_TAG
14+
; CHECK: DW_TAG_module
15+
; CHECK-NEXT: DW_AT_name {{.*}}"DebugModule"
16+
; CHECK-NEXT: DW_AT_LLVM_config_macros {{.*}}"-DMODULES=0"
17+
; CHECK-NEXT: DW_AT_LLVM_include_path {{.*}}"/llvm/tools/clang/test/Modules/Inputs"
18+
; CHECK-NEXT: DW_AT_LLVM_apinotes {{.*}}"m.apinotes"
19+
20+
; CHECK-SPIRV: Capability DebugInfoModuleINTEL
21+
; CHECK-SPIRV: Extension "SPV_INTEL_debug_module"
22+
23+
target datalayout = "e-m:o-i64:64-f80:128-n8:16:32:64-S128"
24+
target triple = "spir64-unknown-unknown"
25+
26+
; CHECK-SPIRV: String [[FileName:[0-9]+]] "/llvm/tools/clang/test/Modules/<stdin>"
27+
; CHECK-SPIRV: String [[EmptyStr:[0-9]+]] ""
28+
; CHECK-SPIRV: String [[Name:[0-9]+]] "DebugModule"
29+
; CHECK-SPIRV: String [[Defines:[0-9]+]] "-DMODULES=0"
30+
; CHECK-SPIRV: String [[IncludePath:[0-9]+]] "/llvm/tools/clang/test/Modules/Inputs"
31+
; CHECK-SPIRV: String [[ApiNotes:[0-9]+]] "m.apinotes"
32+
33+
; CHECK-SPIRV: ExtInst {{[0-9]+}} [[Module:[0-9]+]] {{[0-9]+}} DebugModuleINTEL [[Name]] {{[0-9]+}} 0 {{[0-9]+}} [[Defines]] [[IncludePath]] [[ApiNotes]] 0
34+
; CHECK-SPIRV: ExtInst {{[0-9]+}} {{[0-9]+}} {{[0-9]+}} DebugImportedEntity {{[0-9]+}} {{[0-9]+}} {{[0-9]+}} {{[0-9]+}} [[Module]]
35+
36+
!llvm.dbg.cu = !{!0}
37+
!llvm.module.flags = !{!6, !7}
38+
!llvm.ident = !{!8}
39+
40+
!0 = distinct !DICompileUnit(language: DW_LANG_ObjC, file: !1, producer: "LLVM version 3.7.0", isOptimized: false, runtimeVersion: 2, emissionKind: FullDebug, enums: !2, retainedTypes: !2, globals: !2, imports: !3, sysroot: "/")
41+
!1 = !DIFile(filename: "/llvm/tools/clang/test/Modules/<stdin>", directory: "/")
42+
!2 = !{}
43+
!3 = !{!4}
44+
!4 = !DIImportedEntity(tag: DW_TAG_imported_declaration, scope: !0, entity: !5, file: !1, line: 5)
45+
!5 = !DIModule(scope: null, name: "DebugModule", configMacros: "-DMODULES=0", includePath: "/llvm/tools/clang/test/Modules/Inputs", apinotes: "m.apinotes")
46+
!6 = !{i32 2, !"Dwarf Version", i32 4}
47+
!7 = !{i32 2, !"Debug Info Version", i32 3}
48+
!8 = !{!"LLVM version 3.7.0"}
Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
; RUN: llvm-as < %s -o %t.bc
2+
; RUN: llvm-spirv --spirv-ext=+SPV_INTEL_debug_module %t.bc -o %t.spv
3+
; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o %t.ll
4+
5+
; RUN: llc -mtriple=x86_64-apple-macosx %t.ll -o - -filetype=obj \
6+
; RUN: | llvm-dwarfdump -debug-info - | FileCheck %s
7+
; CHECK: DW_TAG_module
8+
; CHECK-NOT: NULL
9+
; CHECK: DW_TAG_structure_type
10+
11+
; Hand-crafted based on
12+
; struct s;
13+
; struct s *s;
14+
15+
source_filename = "test/DebugInfo/X86/DIModuleContext.ll"
16+
target triple = "spir64-unknown-unknown"
17+
18+
%struct.s = type opaque
19+
20+
@i = common addrspace(1) global %struct.s* null, align 8, !dbg !0
21+
22+
!llvm.dbg.cu = !{!2}
23+
!llvm.module.flags = !{!11, !12}
24+
25+
!0 = !DIGlobalVariableExpression(var: !1, expr: !DIExpression())
26+
!1 = !DIGlobalVariable(name: "s", scope: !2, file: !3, line: 2, type: !9, isLocal: false, isDefinition: true)
27+
!2 = distinct !DICompileUnit(language: DW_LANG_C99, file: !3, producer: "clang", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug, enums: !4, globals: !5, imports: !6)
28+
!3 = !DIFile(filename: "test.c", directory: "/")
29+
!4 = !{}
30+
!5 = !{!0}
31+
!6 = !{!7}
32+
!7 = !DIImportedEntity(tag: DW_TAG_imported_declaration, scope: !2, entity: !8, file: !3, line: 11)
33+
!8 = !DIModule(scope: null, name: "Module", includePath: ".")
34+
!9 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: !10, size: 64, align: 64)
35+
!10 = !DICompositeType(tag: DW_TAG_structure_type, name: "s", scope: !8, file: !3, line: 1, flags: DIFlagFwdDecl)
36+
!11 = !{i32 2, !"Dwarf Version", i32 2}
37+
!12 = !{i32 2, !"Debug Info Version", i32 3}
38+
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
; This test checks attributes of a Fortran module.
2+
; RUN: llvm-as < %s -o %t.bc
3+
; RUN: llvm-spirv --spirv-ext=+SPV_INTEL_debug_module %t.bc -o %t.spv
4+
; RUN: llvm-spirv -r %t.spv -o - | llvm-dis -o %t.ll
5+
6+
; RUN: llc -mtriple=x86_64-unknown-linux-gnu %t.ll -filetype=obj -o - | \
7+
; RUN: llvm-dwarfdump - | FileCheck %s
8+
9+
; CHECK: DW_TAG_module
10+
; CHECK-NEXT: DW_AT_name ("dummy")
11+
; CHECK-NEXT: DW_AT_decl_file ("/fortran{{[/\\]}}module.f90")
12+
; CHECK-NEXT: DW_AT_decl_line (2)
13+
14+
; Generated from flang compiler, Fortran source to regenerate:
15+
; module dummy
16+
; integer :: foo
17+
; end module dummy
18+
19+
; ModuleID = '/tmp/module-b198fa.ll'
20+
source_filename = "/tmp/module-b198fa.ll"
21+
target datalayout = "e-m:e-p270:32:32-p271:32:32-p272:64:64-i64:64-f80:128-n8:16:32:64-S128"
22+
target triple = "spir64-unknown-unknown"
23+
24+
%struct_dummy_0_ = type <{ [4 x i8] }>
25+
26+
@_dummy_0_ = common addrspace(1) global %struct_dummy_0_ zeroinitializer, align 64, !dbg !0
27+
28+
; Function Attrs: noinline
29+
define float @dummy_() #0 {
30+
.L.entry:
31+
ret float undef
32+
}
33+
34+
attributes #0 = { noinline "target-cpu"="x86-64" "target-features"="+cx8,+fxsr,+mmx,+sse,+sse2,+x87" }
35+
36+
!llvm.module.flags = !{!8, !9}
37+
!llvm.dbg.cu = !{!3}
38+
39+
!0 = !DIGlobalVariableExpression(var: !1, expr: !DIExpression())
40+
!1 = distinct !DIGlobalVariable(name: "foo", scope: !2, file: !4, type: !7, isLocal: false, isDefinition: true)
41+
!2 = !DIModule(scope: !3, name: "dummy", file: !4, line: 2)
42+
!3 = distinct !DICompileUnit(language: DW_LANG_Fortran90, file: !4, producer: " F90 Flang - 1.5 2017-05-01", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug, enums: !5, retainedTypes: !5, globals: !6, imports: !5)
43+
!4 = !DIFile(filename: "module.f90", directory: "/fortran")
44+
!5 = !{}
45+
!6 = !{!0}
46+
!7 = !DIBasicType(name: "integer", size: 32, align: 32, encoding: DW_ATE_signed)
47+
!8 = !{i32 2, !"Dwarf Version", i32 4}
48+
!9 = !{i32 2, !"Debug Info Version", i32 3}

0 commit comments

Comments
 (0)