Skip to content

Commit 19b6261

Browse files
authored
opt: Fix crash in strip-debug with non-semantic info (KhronosGroup#6797)
Clears the DebugScope of all instructions during StripDebugInfoPass to prevent out-of-bounds assertions when writing back instructions that reference dead debug instructions. Also resets the FeatureManager when OpExtInstImport is killed to maintain context consistency if imports are removed by other passes. Adds a unit test to verify the fix. Fixes KhronosGroup#6796 Assisted-by: Antigravity
1 parent 4f97d7d commit 19b6261

3 files changed

Lines changed: 66 additions & 3 deletions

File tree

source/opt/ir_context.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -226,7 +226,8 @@ Instruction* IRContext::KillInst(Instruction* inst) {
226226
if (inst->opcode() == spv::Op::OpCapability ||
227227
inst->opcode() == spv::Op::OpConditionalCapabilityINTEL ||
228228
inst->opcode() == spv::Op::OpExtension ||
229-
inst->opcode() == spv::Op::OpConditionalExtensionINTEL) {
229+
inst->opcode() == spv::Op::OpConditionalExtensionINTEL ||
230+
inst->opcode() == spv::Op::OpExtInstImport) {
230231
// We reset the feature manager, instead of updating it, because it is just
231232
// as much work. We would have to remove all capabilities implied by this
232233
// capability that are not also implied by the remaining OpCapability

source/opt/strip_debug_info_pass.cpp

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -95,8 +95,14 @@ Pass::Status StripDebugInfoPass::Process() {
9595

9696
// clear OpLine information
9797
context()->module()->ForEachInst([&modified](Instruction* inst) {
98-
modified |= !inst->dbg_line_insts().empty();
99-
inst->dbg_line_insts().clear();
98+
if (!inst->dbg_line_insts().empty()) {
99+
modified = true;
100+
inst->dbg_line_insts().clear();
101+
}
102+
if (inst->GetDebugScope().GetLexicalScope() != kNoDebugScope) {
103+
modified = true;
104+
inst->SetDebugScope({kNoDebugScope, kNoInlinedAt});
105+
}
100106
});
101107

102108
if (!get_module()->trailing_dbg_line_info().empty()) {

test/opt/strip_debug_info_test.cpp

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -227,6 +227,62 @@ INSTANTIATE_TEST_SUITE_P(
227227
})));
228228
// clang-format on
229229

230+
TEST_F(StripDebugInfoTest, NonSemanticShaderDebugInfoWithDebugScope) {
231+
std::vector<const char*> input = {
232+
// clang-format off
233+
"OpCapability Shader",
234+
"OpExtension \"SPV_KHR_non_semantic_info\"",
235+
"%1 = OpExtInstImport \"NonSemantic.Shader.DebugInfo.100\"",
236+
"OpMemoryModel Logical GLSL450",
237+
"OpEntryPoint GLCompute %main \"main\"",
238+
"OpExecutionMode %main LocalSize 1 1 1",
239+
"%file_name = OpString \"dummy.slang\"",
240+
"%source_text = OpString \"void main() {}\"",
241+
"%void = OpTypeVoid",
242+
"%4 = OpTypeFunction %void",
243+
"%uint = OpTypeInt 32 0",
244+
"%uint_100 = OpConstant %uint 100",
245+
"%uint_5 = OpConstant %uint 5",
246+
"%uint_11 = OpConstant %uint 11",
247+
"%source = OpExtInst %void %1 DebugSource %file_name %source_text",
248+
"%scope = OpExtInst %void %1 DebugCompilationUnit %uint_100 %uint_5 %source %uint_11",
249+
"%main = OpFunction %void None %4",
250+
"%5 = OpLabel",
251+
"%dbg_scope_inst = OpExtInst %void %1 DebugScope %scope",
252+
"OpReturn",
253+
"OpFunctionEnd"
254+
// clang-format on
255+
};
256+
257+
std::vector<const char*> expected = {
258+
// clang-format off
259+
"OpCapability Shader",
260+
"OpExtension \"SPV_KHR_non_semantic_info\"",
261+
"%1 = OpExtInstImport \"NonSemantic.Shader.DebugInfo.100\"",
262+
"OpMemoryModel Logical GLSL450",
263+
"OpEntryPoint GLCompute %2 \"main\"",
264+
"OpExecutionMode %2 LocalSize 1 1 1",
265+
"%3 = OpString \"dummy.slang\"",
266+
"%4 = OpString \"void main() {}\"",
267+
"%void = OpTypeVoid",
268+
"%6 = OpTypeFunction %void",
269+
"%uint = OpTypeInt 32 0",
270+
"%uint_100 = OpConstant %uint 100",
271+
"%uint_5 = OpConstant %uint 5",
272+
"%uint_11 = OpConstant %uint 11",
273+
"%2 = OpFunction %void None %6",
274+
"%13 = OpLabel",
275+
"OpReturn",
276+
"OpFunctionEnd"
277+
// clang-format on
278+
};
279+
280+
SinglePassRunAndCheck<StripDebugInfoPass>(JoinAllInsts(input),
281+
JoinAllInsts(expected),
282+
/* skip_nop = */ false,
283+
/* do_validation */ true);
284+
}
285+
230286
} // namespace
231287
} // namespace opt
232288
} // namespace spvtools

0 commit comments

Comments
 (0)