spirv-reader: test conditional address-of on function call

Bug: tint:804
Change-Id: I7178270fcd8487a20a4e25a2e5389a07e22b4dd6
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/55363
Auto-Submit: David Neto <dneto@google.com>
Reviewed-by: Ben Clayton <bclayton@google.com>
Commit-Queue: David Neto <dneto@google.com>
Kokoro: Kokoro <noreply+kokoro@google.com>
This commit is contained in:
David Neto 2021-06-22 15:48:31 +00:00 committed by Tint LUCI CQ
parent 3c9086d6a5
commit 35b514ff06
1 changed files with 150 additions and 0 deletions

View File

@ -2682,6 +2682,156 @@ Return{}
EXPECT_EQ(got, expected) << got; EXPECT_EQ(got, expected) << got;
} }
TEST_F(SpvParserFunctionVarTest, EmitStatement_Hoist_UsedAsNonPtrArg) {
// Spawned from crbug.com/tint/804
const auto assembly = Preamble() + R"(
%fn_int = OpTypeFunction %void %int
%500 = OpFunction %void None %fn_int
%501 = OpFunctionParameter %int
%502 = OpLabel
OpReturn
OpFunctionEnd
%100 = OpFunction %void None %voidfn
%10 = OpLabel
OpSelectionMerge %50 None
OpBranchConditional %true %20 %30
%20 = OpLabel
%200 = OpCopyObject %int %int_1
OpBranch %50
%30 = OpLabel
OpReturn
%50 = OpLabel ; dominated by %20, but %200 needs to be hoisted
%201 = OpFunctionCall %void %500 %200
OpReturn
OpFunctionEnd
)";
auto p = parser(test::Assemble(assembly));
ASSERT_TRUE(p->BuildAndParseInternalModule()) << p->error() << assembly;
auto fe = p->function_emitter(100);
EXPECT_TRUE(fe.EmitBody()) << p->error();
const auto got = ToString(p->builder(), fe.ast_body());
const auto* expected = R"(VariableDeclStatement{
Variable{
x_200
none
undefined
__i32
}
}
If{
(
ScalarConstructor[not set]{true}
)
{
Assignment{
Identifier[not set]{x_200}
ScalarConstructor[not set]{1}
}
}
}
Else{
{
Return{}
}
}
Call[not set]{
Identifier[not set]{x_500}
(
Identifier[not set]{x_200}
)
}
Return{}
)";
EXPECT_EQ(got, expected) << got;
}
TEST_F(SpvParserFunctionVarTest, DISABLED_EmitStatement_Hoist_UsedAsPtrArg) {
// Spawned from crbug.com/tint/804
// Blocked by crbug.com/tint/98: hoisting pointer types
const auto assembly = Preamble() + R"(
%fn_int = OpTypeFunction %void %ptr_int
%500 = OpFunction %void None %fn_int
%501 = OpFunctionParameter %ptr_int
%502 = OpLabel
OpReturn
OpFunctionEnd
%100 = OpFunction %void None %voidfn
%10 = OpLabel
%199 = OpVariable %ptr_int Function
OpSelectionMerge %50 None
OpBranchConditional %true %20 %30
%20 = OpLabel
%200 = OpCopyObject %ptr_int %199
OpBranch %50
%30 = OpLabel
OpReturn
%50 = OpLabel ; dominated by %20, but %200 needs to be hoisted
%201 = OpFunctionCall %void %500 %200
OpReturn
OpFunctionEnd
)";
std::cout << assembly << std::endl;
auto p = parser(test::Assemble(assembly));
ASSERT_TRUE(p->BuildAndParseInternalModule()) << p->error() << assembly;
auto fe = p->function_emitter(100);
EXPECT_TRUE(fe.EmitBody()) << p->error();
const auto got = ToString(p->builder(), fe.ast_body());
const auto* expected = R"(VariableDeclStatement{
Variable{
x_200
none
undefined
__i32
}
Variable{
x_199
none
undefined
__i32
}
}
If{
(
ScalarConstructor[not set]{true}
)
{
Assignment{
Identifier[not set]{x_200}
ScalarConstructor[not set]{1}
}
}
}
Else{
{
Return{}
}
}
Call[not set]{
Identifier[not set]{x_500}
(
Identifier[not set]{x_200}
)
}
Return{}
)";
EXPECT_EQ(got, expected) << got;
}
} // namespace } // namespace
} // namespace spirv } // namespace spirv
} // namespace reader } // namespace reader