Skip to content

Commit 7058842

Browse files
authored
Fix UAF in eliminate dead functions (KhronosGroup#6799)
Do not collect DebugLine instructions when collecting the non-semantic tree of instructions to kill.
1 parent 19b6261 commit 7058842

2 files changed

Lines changed: 75 additions & 1 deletion

File tree

source/opt/ir_context.cpp

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -287,7 +287,8 @@ void IRContext::CollectNonSemanticTree(
287287
work_list.pop_back();
288288
get_def_use_mgr()->ForEachUser(
289289
i, [&work_list, to_kill, &seen](Instruction* user) {
290-
if (user->IsNonSemanticInstruction() && seen.insert(user).second) {
290+
if (user->IsNonSemanticInstruction() && !user->IsDebugLineInst() &&
291+
seen.insert(user).second) {
291292
work_list.push_back(user);
292293
to_kill->insert(user);
293294
}

test/opt/eliminate_dead_functions_test.cpp

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -550,6 +550,79 @@ OpFunctionEnd
550550
SinglePassRunAndMatch<EliminateDeadFunctionsPass>(text, true);
551551
}
552552

553+
TEST_F(EliminateDeadFunctionsBasicTest, UAF_DebugLine) {
554+
const std::string text = R"(
555+
; CHECK: OpEntryPoint Vertex [[main:%\w+]]
556+
; CHECK: [[main]] = OpFunction
557+
; CHECK: OpFunctionEnd
558+
; CHECK-NOT: = OpFunction
559+
OpCapability Shader
560+
OpExtension "SPV_KHR_non_semantic_info"
561+
%nsdi = OpExtInstImport "NonSemantic.Shader.DebugInfo.9999"
562+
OpMemoryModel Logical GLSL450
563+
OpEntryPoint Vertex %main "main"
564+
%file = OpString "poc.hlsl"
565+
%void = OpTypeVoid
566+
%fn = OpTypeFunction %void
567+
%uint = OpTypeInt 32 0
568+
%u1 = OpConstant %uint 1
569+
%src = OpExtInst %void %nsdi DebugSource %file
570+
%main = OpFunction %void None %fn
571+
%main_l = OpLabel
572+
OpReturn
573+
OpFunctionEnd
574+
%F = OpFunction %void None %fn
575+
%F_l = OpLabel
576+
%x = OpIAdd %uint %u1 %u1
577+
%dl = OpExtInst %void %nsdi DebugLine %src %u1 %u1 %u1 %u1 %x
578+
%y = OpIAdd %uint %u1 %u1
579+
%dnl = OpExtInst %void %nsdi DebugNoLine
580+
OpReturn
581+
OpFunctionEnd
582+
)";
583+
584+
SinglePassRunAndMatch<EliminateDeadFunctionsPass>(text, true);
585+
}
586+
587+
TEST_F(EliminateDeadFunctionsBasicTest, NonSemanticDebugFunctionRemoved) {
588+
const std::string text = R"(
589+
; CHECK: OpEntryPoint Vertex [[main:%\w+]]
590+
; CHECK: [[main]] = OpFunction
591+
; CHECK: OpFunctionEnd
592+
; CHECK-NOT: DebugFunction
593+
; CHECK-NOT: DebugFunctionDefinition
594+
OpCapability Shader
595+
OpExtension "SPV_KHR_non_semantic_info"
596+
%nsdi = OpExtInstImport "NonSemantic.Shader.DebugInfo.100"
597+
OpMemoryModel Logical GLSL450
598+
OpEntryPoint Vertex %main "main"
599+
%file = OpString "poc.hlsl"
600+
%void = OpTypeVoid
601+
%fn = OpTypeFunction %void
602+
%name = OpString "foo"
603+
%uint = OpTypeInt 32 0
604+
%uint_1 = OpConstant %uint 1
605+
%uint_3 = OpConstant %uint 3
606+
%uint_4 = OpConstant %uint 4
607+
%uint_5 = OpConstant %uint 5
608+
%src = OpExtInst %void %nsdi DebugSource %file
609+
%cu = OpExtInst %void %nsdi DebugCompilationUnit %uint_1 %uint_4 %src %uint_5
610+
%type_fn = OpExtInst %void %nsdi DebugTypeFunction %uint_3 %void
611+
%dbg_fn = OpExtInst %void %nsdi DebugFunction %name %type_fn %src %uint_1 %uint_1 %cu %name %uint_3 %uint_1
612+
%main = OpFunction %void None %fn
613+
%main_l = OpLabel
614+
OpReturn
615+
OpFunctionEnd
616+
%F = OpFunction %void None %fn
617+
%F_l = OpLabel
618+
%dbg_def = OpExtInst %void %nsdi DebugFunctionDefinition %dbg_fn %F
619+
OpReturn
620+
OpFunctionEnd
621+
)";
622+
623+
SinglePassRunAndMatch<EliminateDeadFunctionsPass>(text, true);
624+
}
625+
553626
} // namespace
554627
} // namespace opt
555628
} // namespace spvtools

0 commit comments

Comments
 (0)