writer/hlsl: Move the coord/arrayidx packing to utility function
So we can also use this for the `spirv` backend Bug: tint:146 Change-Id: I26f70125a5015946d2428a6e669da32bdea23bcd Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/33780 Reviewed-by: David Neto <dneto@google.com> Commit-Queue: Ben Clayton <bclayton@google.com> Auto-Submit: Ben Clayton <bclayton@google.com>
This commit is contained in:
parent
8ad2c91c60
commit
41c8cd3e68
2
BUILD.gn
2
BUILD.gn
|
@ -426,6 +426,8 @@ source_set("libtint_core_src") {
|
|||
"src/validator/validator_test_helper.h",
|
||||
"src/writer/float_to_string.cc",
|
||||
"src/writer/float_to_string.h",
|
||||
"src/writer/pack_coord_arrayidx.cc",
|
||||
"src/writer/pack_coord_arrayidx.h",
|
||||
"src/writer/text.cc",
|
||||
"src/writer/text.h",
|
||||
"src/writer/text_generator.cc",
|
||||
|
|
|
@ -247,6 +247,8 @@ set(TINT_LIB_SRCS
|
|||
validator/validator_test_helper.h
|
||||
writer/float_to_string.cc
|
||||
writer/float_to_string.h
|
||||
writer/pack_coord_arrayidx.cc
|
||||
writer/pack_coord_arrayidx.h
|
||||
writer/text.cc
|
||||
writer/text.h
|
||||
writer/text_generator.cc
|
||||
|
|
|
@ -52,6 +52,7 @@
|
|||
#include "src/ast/unary_op_expression.h"
|
||||
#include "src/ast/variable_decl_statement.h"
|
||||
#include "src/writer/float_to_string.h"
|
||||
#include "src/writer/pack_coord_arrayidx.h"
|
||||
|
||||
namespace tint {
|
||||
namespace writer {
|
||||
|
@ -103,20 +104,6 @@ uint32_t convert_swizzle_to_index(const std::string& swizzle) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
ast::TypeConstructorExpression* AsVectorConstructor(ast::Expression* expr) {
|
||||
if (!expr->IsConstructor())
|
||||
return nullptr;
|
||||
auto* constructor = expr->AsConstructor();
|
||||
if (!constructor->IsTypeConstructor()) {
|
||||
return nullptr;
|
||||
}
|
||||
auto* type_constructor = constructor->AsTypeConstructor();
|
||||
if (!type_constructor->type()->IsVector()) {
|
||||
return nullptr;
|
||||
}
|
||||
return type_constructor;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
GeneratorImpl::GeneratorImpl(Context* ctx, ast::Module* module)
|
||||
|
@ -775,41 +762,12 @@ bool GeneratorImpl::EmitTextureCall(std::ostream& pre,
|
|||
// Array index needs to be appended to the coordinates.
|
||||
auto* param_coords = params[pidx.coords];
|
||||
auto* param_array_index = params[pidx.array_index];
|
||||
|
||||
uint32_t packed_coords_size;
|
||||
ast::type::Type* packed_coords_el_ty; // Currenly must be f32.
|
||||
if (param_coords->result_type()->IsVector()) {
|
||||
auto* vec = param_coords->result_type()->AsVector();
|
||||
packed_coords_size = vec->size() + 1;
|
||||
packed_coords_el_ty = vec->type();
|
||||
} else {
|
||||
packed_coords_size = 2;
|
||||
packed_coords_el_ty = param_coords->result_type();
|
||||
}
|
||||
|
||||
// Cast param_array_index to the vector element type
|
||||
ast::TypeConstructorExpression array_index_cast(packed_coords_el_ty,
|
||||
{param_array_index});
|
||||
array_index_cast.set_result_type(packed_coords_el_ty);
|
||||
|
||||
ast::type::VectorType packed_coords_ty(packed_coords_el_ty,
|
||||
packed_coords_size);
|
||||
|
||||
ast::ExpressionList coords;
|
||||
// If the coordinates are already passed in a vector constructor, extract
|
||||
// the elements into the new vector instead of nesting a vector-in-vector.
|
||||
if (auto* vc = AsVectorConstructor(param_coords)) {
|
||||
coords = vc->values();
|
||||
} else {
|
||||
coords.emplace_back(param_coords);
|
||||
}
|
||||
coords.emplace_back(&array_index_cast);
|
||||
|
||||
ast::TypeConstructorExpression constructor{&packed_coords_ty,
|
||||
std::move(coords)};
|
||||
|
||||
if (!EmitExpression(pre, out, &constructor))
|
||||
if (!PackCoordAndArrayIndex(param_coords, param_array_index,
|
||||
[&](ast::TypeConstructorExpression* packed) {
|
||||
return EmitExpression(pre, out, packed);
|
||||
})) {
|
||||
return false;
|
||||
}
|
||||
|
||||
} else {
|
||||
if (!EmitExpression(pre, out, params[pidx.coords]))
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
// Copyright 2020 The Tint Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#include "src/writer/pack_coord_arrayidx.h"
|
||||
|
||||
#include <utility>
|
||||
|
||||
#include "src/ast/expression.h"
|
||||
#include "src/ast/type/vector_type.h"
|
||||
#include "src/ast/type_constructor_expression.h"
|
||||
|
||||
namespace tint {
|
||||
namespace writer {
|
||||
|
||||
namespace {
|
||||
|
||||
ast::TypeConstructorExpression* AsVectorConstructor(ast::Expression* expr) {
|
||||
if (!expr->IsConstructor())
|
||||
return nullptr;
|
||||
auto* constructor = expr->AsConstructor();
|
||||
if (!constructor->IsTypeConstructor()) {
|
||||
return nullptr;
|
||||
}
|
||||
auto* type_constructor = constructor->AsTypeConstructor();
|
||||
if (!type_constructor->type()->IsVector()) {
|
||||
return nullptr;
|
||||
}
|
||||
return type_constructor;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
bool PackCoordAndArrayIndex(
|
||||
ast::Expression* coords,
|
||||
ast::Expression* array_idx,
|
||||
std::function<bool(ast::TypeConstructorExpression*)> callback) {
|
||||
uint32_t packed_size;
|
||||
ast::type::Type* packed_el_ty; // Currenly must be f32.
|
||||
if (coords->result_type()->IsVector()) {
|
||||
auto* vec = coords->result_type()->AsVector();
|
||||
packed_size = vec->size() + 1;
|
||||
packed_el_ty = vec->type();
|
||||
} else {
|
||||
packed_size = 2;
|
||||
packed_el_ty = coords->result_type();
|
||||
}
|
||||
|
||||
if (!packed_el_ty) {
|
||||
return false; // missing type info
|
||||
}
|
||||
|
||||
// Cast array_idx to the vector element type
|
||||
ast::TypeConstructorExpression array_index_cast(packed_el_ty, {array_idx});
|
||||
array_index_cast.set_result_type(packed_el_ty);
|
||||
|
||||
ast::type::VectorType packed_ty(packed_el_ty, packed_size);
|
||||
|
||||
// If the coordinates are already passed in a vector constructor, extract
|
||||
// the elements into the new vector instead of nesting a vector-in-vector.
|
||||
ast::ExpressionList packed;
|
||||
if (auto* vc = AsVectorConstructor(coords)) {
|
||||
packed = vc->values();
|
||||
} else {
|
||||
packed.emplace_back(coords);
|
||||
}
|
||||
packed.emplace_back(&array_index_cast);
|
||||
|
||||
ast::TypeConstructorExpression constructor{&packed_ty, std::move(packed)};
|
||||
|
||||
return callback(&constructor);
|
||||
}
|
||||
|
||||
} // namespace writer
|
||||
} // namespace tint
|
|
@ -0,0 +1,52 @@
|
|||
// Copyright 2020 The Tint Authors.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
#ifndef SRC_WRITER_PACK_COORD_ARRAYIDX_H_
|
||||
#define SRC_WRITER_PACK_COORD_ARRAYIDX_H_
|
||||
|
||||
#include <functional>
|
||||
|
||||
#include "src/source.h"
|
||||
|
||||
namespace tint {
|
||||
|
||||
namespace ast {
|
||||
class Expression;
|
||||
class TypeConstructorExpression;
|
||||
} // namespace ast
|
||||
|
||||
namespace writer {
|
||||
|
||||
/// A helper function use to generate texture intrinsic function calls for
|
||||
/// backends that expect the texture coordinate and array index to be packed
|
||||
/// together into a single 'coordinate' parameter.
|
||||
/// PackCoordAndArrayIndex() calls the @p callback function with a vector
|
||||
/// expression containing the elements of @p coords followed by the single
|
||||
/// element of @p array_idx cast to the @p coords element type.
|
||||
/// All types must have been assigned to the expressions and their child nodes
|
||||
/// before calling.
|
||||
/// @param coords the texture coordinates. May be a scalar, `vec2` or `vec3`.
|
||||
/// @param array_idx the texture array index. Must be a scalar.
|
||||
/// @param callback the function called with the packed result. Note that the
|
||||
/// pointer argument is only valid for the duration of the call.
|
||||
/// @returns the value returned by `callback` to indicate success
|
||||
bool PackCoordAndArrayIndex(
|
||||
ast::Expression* coords,
|
||||
ast::Expression* array_idx,
|
||||
std::function<bool(ast::TypeConstructorExpression*)> callback);
|
||||
|
||||
} // namespace writer
|
||||
} // namespace tint
|
||||
|
||||
#endif // SRC_WRITER_PACK_COORD_ARRAYIDX_H_
|
Loading…
Reference in New Issue