[spirv-writer] Fixup generation of temporary variable.

When extracting values out of constant arrays we sometimes generate a
temporary variable. That generation was over eager in the creation of
the variable and was also creating it for constant vector extractions
where it was providing the wrong souce type.

Bug: tint:318
Change-Id: I8d16182fd1fcf7d7aba0b0e1b7d947137efc136b
Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/32801
Reviewed-by: Sarah Mashayekhi <sarahmashay@google.com>
Reviewed-by: Ryan Harrison <rharrison@chromium.org>
Auto-Submit: dan sinclair <dsinclair@chromium.org>
Commit-Queue: dan sinclair <dsinclair@chromium.org>
This commit is contained in:
dan sinclair 2020-11-16 15:34:07 +00:00 committed by Commit Bot service account
parent 307919dba9
commit 75b740c4ae
2 changed files with 52 additions and 4 deletions

View File

@ -978,13 +978,16 @@ uint32_t Builder::GenerateAccessorExpression(ast::Expression* expr) {
} }
info.source_type = source->result_type(); info.source_type = source->result_type();
// If our initial access in into an array, and that array is not a pointer, // If our initial access is into an array of non-scalar types, and that array
// then we need to load that array into a variable in order to be access // is not a pointer, then we need to load that array into a variable in order
// chain into the array // to access chain into the array.
if (accessors[0]->IsArrayAccessor()) { if (accessors[0]->IsArrayAccessor()) {
auto* ary_res_type = auto* ary_res_type =
accessors[0]->AsArrayAccessor()->array()->result_type(); accessors[0]->AsArrayAccessor()->array()->result_type();
if (!ary_res_type->IsPointer()) {
if (!ary_res_type->IsPointer() &&
(ary_res_type->IsArray() &&
!ary_res_type->AsArray()->type()->is_scalar())) {
ast::type::PointerType ptr(ary_res_type, ast::StorageClass::kFunction); ast::type::PointerType ptr(ary_res_type, ast::StorageClass::kFunction);
auto result_type_id = GenerateTypeIfNeeded(&ptr); auto result_type_id = GenerateTypeIfNeeded(&ptr);
if (result_type_id == 0) { if (result_type_id == 0) {

View File

@ -946,6 +946,51 @@ TEST_F(BuilderTest, Accessor_Array_Of_Vec) {
)"); )");
} }
TEST_F(BuilderTest, Accessor_Const_Vec) {
// const pos : vec2<f32> = vec2<f32>(0.0, 0.5);
// pos[1]
ast::type::F32Type f32;
ast::type::U32Type u32;
ast::type::VectorType vec(&f32, 2);
ast::ExpressionList vec_params;
vec_params.push_back(create<ast::ScalarConstructorExpression>(
create<ast::FloatLiteral>(&f32, 0.0)));
vec_params.push_back(create<ast::ScalarConstructorExpression>(
create<ast::FloatLiteral>(&f32, 0.5)));
ast::Variable var("pos", ast::StorageClass::kPrivate, &vec);
var.set_is_const(true);
var.set_constructor(
create<ast::TypeConstructorExpression>(&vec, std::move(vec_params)));
ast::ArrayAccessorExpression expr(create<ast::IdentifierExpression>("pos"),
create<ast::ScalarConstructorExpression>(
create<ast::UintLiteral>(&u32, 1)));
td.RegisterVariableForTesting(&var);
ASSERT_TRUE(td.DetermineResultType(var.constructor())) << td.error();
ASSERT_TRUE(td.DetermineResultType(&expr)) << td.error();
b.push_function(Function{});
ASSERT_TRUE(b.GenerateFunctionVariable(&var)) << b.error();
EXPECT_EQ(b.GenerateAccessorExpression(&expr), 8u) << b.error();
EXPECT_EQ(DumpInstructions(b.types()), R"(%2 = OpTypeFloat 32
%1 = OpTypeVector %2 2
%3 = OpConstant %2 0
%4 = OpConstant %2 0.5
%5 = OpConstantComposite %1 %3 %4
%6 = OpTypeInt 32 0
%7 = OpConstant %6 1
)");
EXPECT_EQ(DumpInstructions(b.functions()[0].variables()), "");
EXPECT_EQ(DumpInstructions(b.functions()[0].instructions()),
R"(%8 = OpVectorExtractDynamic %2 %5 %7
)");
}
TEST_F(BuilderTest, DISABLED_Accessor_Array_NonPointer) { TEST_F(BuilderTest, DISABLED_Accessor_Array_NonPointer) {
// const a : array<f32, 3>; // const a : array<f32, 3>;
// a[2] // a[2]