From 0f37afb74ef88c05222e660701a3214dd8998994 Mon Sep 17 00:00:00 2001 From: Ben Clayton Date: Thu, 3 Dec 2020 20:25:29 +0000 Subject: [PATCH] Refactor transformer tests Transformers will be moving to a transform-on-copy model, instead of transform-in-place. Rework the tests to handle this. Bug: tint:390 Change-Id: Id53a0ba0bd365472940d116bd686e450a29e5028 Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/34571 Reviewed-by: dan sinclair Commit-Queue: Ben Clayton --- .../bound_array_accessors_transform_test.cc | 980 ++++++++---------- .../emit_vertex_point_size_transform_test.cc | 162 +-- 2 files changed, 545 insertions(+), 597 deletions(-) diff --git a/src/transform/bound_array_accessors_transform_test.cc b/src/transform/bound_array_accessors_transform_test.cc index e48308235b..2053277e9a 100644 --- a/src/transform/bound_array_accessors_transform_test.cc +++ b/src/transform/bound_array_accessors_transform_test.cc @@ -21,6 +21,7 @@ #include "src/ast/array_accessor_expression.h" #include "src/ast/binary_expression.h" #include "src/ast/block_statement.h" +#include "src/ast/builder.h" #include "src/ast/call_expression.h" #include "src/ast/function.h" #include "src/ast/identifier_expression.h" @@ -40,6 +41,7 @@ #include "src/ast/uint_literal.h" #include "src/ast/variable.h" #include "src/ast/variable_decl_statement.h" +#include "src/diagnostic/formatter.h" #include "src/transform/manager.h" #include "src/type_determiner.h" @@ -47,47 +49,61 @@ namespace tint { namespace transform { namespace { +template +T* FindVariable(ast::Module* mod, std::string name) { + if (auto* func = mod->FindFunctionByName("func")) { + for (auto* stmt : *func->body()) { + if (auto* decl = stmt->As()) { + if (auto* var = decl->variable()) { + if (var->name() == name) { + return As(var->constructor()); + } + } + } + } + } + return nullptr; +} + class BoundArrayAccessorsTest : public testing::Test { public: - BoundArrayAccessorsTest() : td_(&mod_) { - auto transform = std::make_unique(&mod_); - transform_ = transform.get(); - manager_.append(std::move(transform)); + ast::Module Transform(ast::Module mod) { + TypeDeterminer td(&mod); + if (!td.Determine()) { + error = "Type determination failed: " + td.error(); + return {}; + } + + Manager manager; + manager.append(std::make_unique(&mod)); + if (!manager.Run(&mod)) { + error = "manager().Run() errored:\n" + manager.error(); + return {}; + } + + return mod; } - ast::BlockStatement* SetupFunctionAndBody() { - auto* block = create(); - body_ = block; - auto* func = - create("func", ast::VariableList{}, &void_type_, block); - mod_.AddFunction(func); - return body_; + std::string error; +}; + +struct ModuleBuilder : public ast::BuilderWithModule { + ModuleBuilder() : body_(create()) { + mod->AddFunction( + create("func", ast::VariableList{}, ty.void_, body_)); } - void DeclareVariable(ast::Variable* var) { + ast::Module Module() { + Build(); + return std::move(*mod); + } + + protected: + virtual void Build() = 0; + void OnVariableBuilt(ast::Variable* var) override { ASSERT_NE(body_, nullptr); body_->append(create(var)); } - - TypeDeterminer* td() { return &td_; } - - bool Run() { return manager_.Run(&mod_); } - - /// Creates a new `ast::Node` owned by the Module. When the Module is - /// destructed, the `ast::Node` will also be destructed. - /// @param args the arguments to pass to the type constructor - /// @returns the node pointer - template - T* create(ARGS&&... args) { - return mod_.create(std::forward(args)...); - } - - private: - ast::Module mod_; - TypeDeterminer td_; - ast::type::Void void_type_; - Manager manager_; - BoundArrayAccessorsTransform* transform_; ast::BlockStatement* body_ = nullptr; }; @@ -97,38 +113,25 @@ TEST_F(BoundArrayAccessorsTest, Ptrs_Clamp) { // const b : ptr = a[c] // // -> const b : ptr = a[min(u32(c), 2)] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array()); + Const("c", ast::StorageClass::kFunction, ty.u32); + Const("b", ast::StorageClass::kFunction, + ty.pointer(ast::StorageClass::kFunction)) + ->set_constructor(Index("a", "c")); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Array ary(&f32, 3); - ast::type::Pointer ptr_type(&f32, ast::StorageClass::kFunction); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* c_var = create("c", ast::StorageClass::kFunction, &u32); - c_var->set_is_const(true); - DeclareVariable(c_var); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* access_idx = create("c"); - - auto* accessor = create( - create("a"), access_idx); - auto* ptr = accessor; - - auto* b = create("b", ast::StorageClass::kFunction, &ptr_type); - b->set_constructor(accessor); - b->set_is_const(true); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* idx = ptr->idx_expr()->As(); + auto* idx = b->idx_expr()->As(); ASSERT_TRUE(idx->func()->Is()); EXPECT_EQ(idx->func()->As()->name(), "min"); @@ -139,7 +142,8 @@ TEST_F(BoundArrayAccessorsTest, Ptrs_Clamp) { auto* tc = idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], access_idx); + ASSERT_TRUE(tc->values()[0]->Is()); + ASSERT_EQ(tc->values()[0]->As()->name(), "c"); ASSERT_TRUE(idx->params()[1]->Is()); ASSERT_TRUE(idx->params()[1]->Is()); @@ -147,8 +151,8 @@ TEST_F(BoundArrayAccessorsTest, Ptrs_Clamp) { ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Array_Idx_Nested_Scalar) { @@ -158,40 +162,26 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Nested_Scalar) { // var c : f32 = a[b[i]]; // // -> var c : f32 = a[min(u32(b[min(u32(i), 4)]), 2)]; + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array()); + Var("b", ast::StorageClass::kFunction, ty.array()); + Var("i", ast::StorageClass::kFunction, ty.u32); + Const("c", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", Index("b", "i"))); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Array ary3(&f32, 3); - ast::type::Array ary5(&f32, 5); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary3)); - DeclareVariable( - create("b", ast::StorageClass::kFunction, &ary5)); - DeclareVariable( - create("i", ast::StorageClass::kFunction, &u32)); + auto* c = FindVariable(&module, "c"); + ASSERT_NE(c, nullptr); - auto* b_access_idx = create("i"); + ASSERT_TRUE(c->Is()); + ASSERT_TRUE(c->idx_expr()->Is()); - auto* a_access_idx = create( - create("b"), b_access_idx); - - auto* accessor = create( - create("a"), a_access_idx); - auto* ptr = accessor; - - auto* b = create("c", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* idx = ptr->idx_expr()->As(); + auto* idx = c->idx_expr()->As(); ASSERT_TRUE(idx->func()->Is()); EXPECT_EQ(idx->func()->As()->name(), "min"); @@ -220,7 +210,8 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Nested_Scalar) { tc = sub_idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], b_access_idx); + ASSERT_TRUE(tc->values()[0]->Is()); + ASSERT_EQ(tc->values()[0]->As()->name(), "i"); ASSERT_TRUE(sub_idx->params()[1]->Is()); ASSERT_TRUE(sub_idx->params()[1]->Is()); @@ -234,8 +225,8 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Nested_Scalar) { ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(c->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(c->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Array_Idx_Scalar) { @@ -243,38 +234,30 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Scalar) { // var b : f32 = a[1]; // // -> var b : f32 = a[1]; + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array(ty.f32, 3)); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", 1u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Array ary(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&u32, 1u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Array_Idx_Expr) { @@ -283,40 +266,25 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Expr) { // var b : f32 = a[c + 2 - 3] // // -> var b : f32 = a[min(u32(c + 2 - 3), 2)] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array()); + Var("c", ast::StorageClass::kFunction, ty.u32); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", Add("c", Sub(2u, 3u)))); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Array ary(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary)); - DeclareVariable( - create("c", ast::StorageClass::kFunction, &u32)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* access_idx = create( - ast::BinaryOp::kAdd, create("c"), - create(ast::BinaryOp::kSubtract, - create( - create(&u32, 2)), - create( - create(&u32, 3)))); + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* accessor = create( - create("a"), access_idx); - auto* ptr = accessor; - - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* idx = ptr->idx_expr()->As(); + auto* idx = b->idx_expr()->As(); ASSERT_TRUE(idx->func()->Is()); EXPECT_EQ(idx->func()->As()->name(), "min"); @@ -327,7 +295,28 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Expr) { auto* tc = idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], access_idx); + auto* add = tc->values()[0]->As(); + ASSERT_NE(add, nullptr); + ASSERT_EQ(add->op(), ast::BinaryOp::kAdd); + auto* add_lhs = add->lhs()->As(); + ASSERT_NE(add_lhs, nullptr); + ASSERT_EQ(add_lhs->name(), "c"); + auto* add_rhs = add->rhs()->As(); + ASSERT_NE(add_rhs, nullptr); + ASSERT_TRUE(add_rhs->lhs()->Is()); + ASSERT_EQ(add_rhs->lhs() + ->As() + ->literal() + ->As() + ->value(), + 2u); + ASSERT_TRUE(add_rhs->rhs()->Is()); + ASSERT_EQ(add_rhs->rhs() + ->As() + ->literal() + ->As() + ->value(), + 3u); ASSERT_TRUE(idx->params()[1]->Is()); ASSERT_TRUE(idx->params()[1]->Is()); @@ -335,8 +324,8 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Expr) { ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Array_Idx_Negative) { @@ -344,38 +333,30 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_Negative) { // var b : f32 = a[-1] // // -> var b : f32 = a[0] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", -1)); + } + }; - ast::type::F32 f32; - ast::type::I32 i32; - ast::type::Array ary(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&i32, -1))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 0); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Array_Idx_OutOfBounds) { @@ -383,38 +364,30 @@ TEST_F(BoundArrayAccessorsTest, Array_Idx_OutOfBounds) { // var b : f32 = a[3] // // -> var b : f32 = a[2] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.array()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", 3u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Array ary(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &ary)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&u32, 3u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Vector_Idx_Scalar) { @@ -422,38 +395,30 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_Scalar) { // var b : f32 = a[1]; // // -> var b : f32 = a[1] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.vec3()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", 1u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Vector vec(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &vec)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&u32, 1u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Vector_Idx_Expr) { @@ -462,40 +427,25 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_Expr) { // var b : f32 = a[c + 2 - 3] // // -> var b : f32 = a[min(u32(c + 2 - 3), 2)] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.vec3()); + Var("c", ast::StorageClass::kFunction, ty.u32); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", Add("c", Sub(2u, 3u)))); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Vector vec(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &vec)); - DeclareVariable( - create("c", ast::StorageClass::kFunction, &u32)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* access_idx = create( - ast::BinaryOp::kAdd, create("c"), - create(ast::BinaryOp::kSubtract, - create( - create(&u32, 2)), - create( - create(&u32, 3)))); + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* accessor = create( - create("a"), access_idx); - auto* ptr = accessor; - - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* idx = ptr->idx_expr()->As(); + auto* idx = b->idx_expr()->As(); ASSERT_TRUE(idx->func()->Is()); EXPECT_EQ(idx->func()->As()->name(), "min"); @@ -505,7 +455,27 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_Expr) { auto* tc = idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], access_idx); + auto* add = tc->values()[0]->As(); + ASSERT_NE(add, nullptr); + auto* add_lhs = add->lhs()->As(); + ASSERT_NE(add_lhs, nullptr); + ASSERT_EQ(add_lhs->name(), "c"); + auto* add_rhs = add->rhs()->As(); + ASSERT_NE(add_rhs, nullptr); + ASSERT_TRUE(add_rhs->lhs()->Is()); + ASSERT_EQ(add_rhs->lhs() + ->As() + ->literal() + ->As() + ->value(), + 2u); + ASSERT_TRUE(add_rhs->rhs()->Is()); + ASSERT_EQ(add_rhs->rhs() + ->As() + ->literal() + ->As() + ->value(), + 3u); ASSERT_TRUE(idx->params()[1]->Is()); ASSERT_TRUE(idx->params()[1]->Is()); @@ -513,8 +483,8 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_Expr) { ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Vector_Idx_Negative) { @@ -522,38 +492,30 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_Negative) { // var b : f32 = a[-1] // // -> var b : f32 = a[0] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.vec3()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", -1)); + } + }; - ast::type::F32 f32; - ast::type::I32 i32; - ast::type::Vector vec(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &vec)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&i32, -1))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 0); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Vector_Idx_OutOfBounds) { @@ -561,38 +523,30 @@ TEST_F(BoundArrayAccessorsTest, Vector_Idx_OutOfBounds) { // var b : f32 = a[3] // // -> var b : f32 = a[2] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.vec3()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index("a", 3u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Vector vec(&f32, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &vec)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create("a"), - create( - create(&u32, 3u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - - auto* scalar = ptr->idx_expr()->As(); + auto* scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 2u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Scalar) { @@ -600,35 +554,24 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Scalar) { // var b : f32 = a[2][1]; // // -> var b : f32 = a[2][1] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", 2u), 1u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Matrix mat(&f32, 2, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create( - create("a"), - create( - create(&u32, 2u))), - create( - create(&u32, 1u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -639,15 +582,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Scalar) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Column) { @@ -656,43 +599,25 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Column) { // var b : f32 = a[c + 2 - 3][1] // // -> var b : f32 = a[min(u32(c + 2 - 3), 2)][1] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("c", ast::StorageClass::kFunction, ty.u32); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", Add("c", Sub(2u, 3u))), 1u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Matrix mat(&f32, 2, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); - DeclareVariable( - create("c", ast::StorageClass::kFunction, &u32)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* access_idx = create( - ast::BinaryOp::kAdd, create("c"), - create(ast::BinaryOp::kSubtract, - create( - create(&u32, 2)), - create( - create(&u32, 3)))); + ASSERT_TRUE(b->Is()); - auto* accessor = create( - create( - create("a"), access_idx), - create( - create(&u32, 1u))); - auto* ptr = accessor; - - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); auto* idx = ary->idx_expr()->As(); @@ -706,7 +631,27 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Column) { auto* tc = idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], access_idx); + auto* add = tc->values()[0]->As(); + ASSERT_NE(add, nullptr); + auto* add_lhs = add->lhs()->As(); + ASSERT_NE(add_lhs, nullptr); + ASSERT_EQ(add_lhs->name(), "c"); + auto* add_rhs = add->rhs()->As(); + ASSERT_NE(add_rhs, nullptr); + ASSERT_TRUE(add_rhs->lhs()->Is()); + ASSERT_EQ(add_rhs->lhs() + ->As() + ->literal() + ->As() + ->value(), + 2u); + ASSERT_TRUE(add_rhs->rhs()->Is()); + ASSERT_EQ(add_rhs->rhs() + ->As() + ->literal() + ->As() + ->value(), + 3u); ASSERT_TRUE(idx->params()[1]->Is()); ASSERT_TRUE(idx->params()[1]->Is()); @@ -717,15 +662,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Column) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Row) { @@ -734,44 +679,25 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Row) { // var b : f32 = a[1][c + 2 - 3] // // -> var b : f32 = a[1][min(u32(c + 2 - 3), 1)] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("c", ast::StorageClass::kFunction, ty.u32); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", 1u), Add("c", Sub(2u, 3u)))); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Matrix mat(&f32, 2, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); - DeclareVariable( - create("c", ast::StorageClass::kFunction, &u32)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* access_idx = create( - ast::BinaryOp::kAdd, create("c"), - create(ast::BinaryOp::kSubtract, - create( - create(&u32, 2)), - create( - create(&u32, 3)))); + ASSERT_TRUE(b->Is()); - auto* accessor = create( - create( - create("a"), - create( - create(&u32, 1u))), - access_idx); - auto* ptr = accessor; - - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -780,8 +706,8 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Row) { ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_TRUE(ptr->idx_expr()->Is()); - auto* idx = ptr->idx_expr()->As(); + ASSERT_TRUE(b->idx_expr()->Is()); + auto* idx = b->idx_expr()->As(); ASSERT_TRUE(idx->func()->Is()); EXPECT_EQ(idx->func()->As()->name(), "min"); @@ -792,7 +718,27 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Row) { auto* tc = idx->params()[0]->As(); EXPECT_TRUE(tc->type()->Is()); ASSERT_EQ(tc->values().size(), 1u); - ASSERT_EQ(tc->values()[0], access_idx); + auto* add = tc->values()[0]->As(); + ASSERT_NE(add, nullptr); + auto* add_lhs = add->lhs()->As(); + ASSERT_NE(add_lhs, nullptr); + ASSERT_EQ(add_lhs->name(), "c"); + auto* add_rhs = add->rhs()->As(); + ASSERT_NE(add_rhs, nullptr); + ASSERT_TRUE(add_rhs->lhs()->Is()); + ASSERT_EQ(add_rhs->lhs() + ->As() + ->literal() + ->As() + ->value(), + 2u); + ASSERT_TRUE(add_rhs->rhs()->Is()); + ASSERT_EQ(add_rhs->rhs() + ->As() + ->literal() + ->As() + ->value(), + 3u); ASSERT_TRUE(idx->params()[1]->Is()); ASSERT_TRUE(idx->params()[1]->Is()); @@ -803,8 +749,8 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Expr_Row) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Column) { @@ -812,34 +758,24 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Column) { // var b : f32 = a[-1][1] // // -> var b : f32 = a[0][1] - ast::type::F32 f32; - ast::type::I32 i32; - ast::type::Matrix mat(&f32, 2, 3); + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", -1), 1)); + } + }; - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - auto* accessor = create( - create( - create("a"), - create( - create(&i32, -1))), - create( - create(&i32, 1))); - auto* ptr = accessor; + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); + ASSERT_TRUE(b->Is()); - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -850,15 +786,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Column) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Row) { @@ -866,34 +802,24 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Row) { // var b : f32 = a[2][-1] // // -> var b : f32 = a[2][0] - ast::type::F32 f32; - ast::type::I32 i32; - ast::type::Matrix mat(&f32, 2, 3); + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", 2), -1)); + } + }; - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - auto* accessor = create( - create( - create("a"), - create( - create(&i32, 2))), - create( - create(&i32, -1))); - auto* ptr = accessor; + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); + ASSERT_TRUE(b->Is()); - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -904,15 +830,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_Negative_Row) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 0); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Column) { @@ -920,35 +846,24 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Column) { // var b : f32 = a[5][1] // // -> var b : f32 = a[2][1] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", 5u), 1u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Matrix mat(&f32, 2, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create( - create("a"), - create( - create(&u32, 5u))), - create( - create(&u32, 1u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -959,15 +874,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Column) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Row) { @@ -975,35 +890,24 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Row) { // var b : f32 = a[2][5] // // -> var b : f32 = a[2][1] + struct Builder : ModuleBuilder { + void Build() override { + Var("a", ast::StorageClass::kFunction, ty.mat3x2()); + Var("b", ast::StorageClass::kFunction, ty.f32) + ->set_constructor(Index(Index("a", 2u), 5u)); + } + }; - ast::type::F32 f32; - ast::type::U32 u32; - ast::type::Matrix mat(&f32, 2, 3); + ast::Module module = Transform(Builder{}.Module()); + ASSERT_EQ(error, ""); - SetupFunctionAndBody(); - DeclareVariable( - create("a", ast::StorageClass::kFunction, &mat)); + auto* b = FindVariable(&module, "b"); + ASSERT_NE(b, nullptr); - auto* accessor = create( - create( - create("a"), - create( - create(&u32, 2u))), - create( - create(&u32, 5u))); - auto* ptr = accessor; + ASSERT_TRUE(b->Is()); - auto* b = create("b", ast::StorageClass::kFunction, &f32); - b->set_constructor(accessor); - DeclareVariable(b); - - ASSERT_TRUE(td()->Determine()) << td()->error(); - - ASSERT_TRUE(Run()); - ASSERT_TRUE(ptr->Is()); - - ASSERT_TRUE(ptr->array()->Is()); - auto* ary = ptr->array()->As(); + ASSERT_TRUE(b->array()->Is()); + auto* ary = b->array()->As(); ASSERT_TRUE(ary->idx_expr()->Is()); ASSERT_TRUE(ary->idx_expr()->Is()); @@ -1014,15 +918,15 @@ TEST_F(BoundArrayAccessorsTest, Matrix_Idx_OutOfBounds_Row) { ASSERT_NE(ary->idx_expr()->result_type(), nullptr); ASSERT_TRUE(ary->idx_expr()->result_type()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); - ASSERT_TRUE(ptr->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); + ASSERT_TRUE(b->idx_expr()->Is()); - scalar = ptr->idx_expr()->As(); + scalar = b->idx_expr()->As(); ASSERT_TRUE(scalar->literal()->Is()); EXPECT_EQ(scalar->literal()->As()->value(), 1u); - ASSERT_NE(ptr->idx_expr()->result_type(), nullptr); - ASSERT_TRUE(ptr->idx_expr()->result_type()->Is()); + ASSERT_NE(b->idx_expr()->result_type(), nullptr); + ASSERT_TRUE(b->idx_expr()->result_type()->Is()); } // TODO(dsinclair): Implement when constant_id exists diff --git a/src/transform/emit_vertex_point_size_transform_test.cc b/src/transform/emit_vertex_point_size_transform_test.cc index 0167bf61bf..58337e5e63 100644 --- a/src/transform/emit_vertex_point_size_transform_test.cc +++ b/src/transform/emit_vertex_point_size_transform_test.cc @@ -19,49 +19,79 @@ #include "gtest/gtest.h" #include "src/ast/builder.h" -#include "src/ast/call_statement.h" #include "src/ast/stage_decoration.h" +#include "src/ast/variable_decl_statement.h" +#include "src/diagnostic/diagnostic.h" +#include "src/diagnostic/formatter.h" #include "src/transform/manager.h" namespace tint { namespace transform { namespace { -class EmitVertexPointSizeTransformTest : public testing::Test, - public ast::BuilderWithModule { +class EmitVertexPointSizeTransformTest : public testing::Test { public: - EmitVertexPointSizeTransformTest() { - auto transform = std::make_unique(mod); - manager = std::make_unique(); - manager->append(std::move(transform)); + struct Output { + ast::Module module; + diag::List diagnostics; + }; + Output Transform(ast::Module mod) { + Manager manager; + manager.append(std::make_unique(&mod)); + manager.Run(&mod); + Output out; + out.module = std::move(mod); + auto err = manager.error(); + if (!err.empty()) { + diag::Diagnostic diag; + diag.message = err; + diag.severity = diag::Severity::Error; + out.diagnostics.add(std::move(diag)); + } + return out; + } +}; + +struct ModuleBuilder : public ast::BuilderWithModule { + ModuleBuilder() {} + + ast::Module Module() { + Build(); + return std::move(*mod); } - std::unique_ptr manager; + protected: + virtual void Build() = 0; }; TEST_F(EmitVertexPointSizeTransformTest, VertexStageBasic) { - auto* block = create(Source{}); - block->append(create(create( - Source{}, - create( - Source{}, "builtin_assignments_should_happen_before_this"), - ast::ExpressionList{}))); + struct Builder : ModuleBuilder { + void Build() override { + auto* block = create(Source{}); - mod->AddFunction(create( - "non_entry_a", ast::VariableList{}, create(), - create(Source{}))); + block->append(create( + Var("builtin_assignments_should_happen_before_this", + tint::ast::StorageClass::kFunction, ty.f32))); - auto* entry = create("entry", ast::VariableList{}, - create(), block); - entry->set_decorations( - {create(ast::PipelineStage::kVertex, Source{})}); - mod->AddFunction(entry); + mod->AddFunction( + create("non_entry_a", ast::VariableList{}, ty.void_, + create(Source{}))); - mod->AddFunction(create( - "non_entry_b", ast::VariableList{}, create(), - create(Source{}))); + auto* entry = + create("entry", ast::VariableList{}, ty.void_, block); + entry->set_decorations({create( + ast::PipelineStage::kVertex, Source{})}); + mod->AddFunction(entry); - manager->Run(mod); + mod->AddFunction( + create("non_entry_b", ast::VariableList{}, ty.void_, + create(Source{}))); + } + }; + + auto result = Transform(Builder{}.Module()); + ASSERT_FALSE(result.diagnostics.contains_errors()) + << diag::Formatter().format(result.diagnostics); auto* expected = R"(Module{ DecoratedVariable{ @@ -84,10 +114,12 @@ TEST_F(EmitVertexPointSizeTransformTest, VertexStageBasic) { Identifier[__ptr_out__f32]{tint_pointsize} ScalarConstructor[__f32]{1.000000} } - Call[not set]{ - Identifier[not set]{builtin_assignments_should_happen_before_this} - ( - ) + VariableDeclStatement{ + Variable{ + builtin_assignments_should_happen_before_this + function + __f32 + } } } Function non_entry_b -> __void @@ -96,26 +128,32 @@ TEST_F(EmitVertexPointSizeTransformTest, VertexStageBasic) { } } )"; - EXPECT_EQ(expected, mod->to_str()); + EXPECT_EQ(expected, result.module.to_str()); } TEST_F(EmitVertexPointSizeTransformTest, VertexStageEmpty) { - mod->AddFunction(create( - "non_entry_a", ast::VariableList{}, create(), - create(Source{}))); + struct Builder : ModuleBuilder { + void Build() override { + mod->AddFunction( + create("non_entry_a", ast::VariableList{}, ty.void_, + create(Source{}))); - auto* entry = create("entry", ast::VariableList{}, - create(), - create(Source{})); - entry->set_decorations( - {create(ast::PipelineStage::kVertex, Source{})}); - mod->AddFunction(entry); + auto* entry = + create("entry", ast::VariableList{}, ty.void_, + create(Source{})); + entry->set_decorations({create( + ast::PipelineStage::kVertex, Source{})}); + mod->AddFunction(entry); - mod->AddFunction(create( - "non_entry_b", ast::VariableList{}, create(), - create(Source{}))); + mod->AddFunction( + create("non_entry_b", ast::VariableList{}, ty.void_, + create(Source{}))); + } + }; - manager->Run(mod); + auto result = Transform(Builder{}.Module()); + ASSERT_FALSE(result.diagnostics.contains_errors()) + << diag::Formatter().format(result.diagnostics); auto* expected = R"(Module{ DecoratedVariable{ @@ -145,25 +183,31 @@ TEST_F(EmitVertexPointSizeTransformTest, VertexStageEmpty) { } } )"; - EXPECT_EQ(expected, mod->to_str()); + EXPECT_EQ(expected, result.module.to_str()); } TEST_F(EmitVertexPointSizeTransformTest, NonVertexStage) { - auto* fragment_entry = create( - "fragment_entry", ast::VariableList{}, create(), - create(Source{})); - fragment_entry->set_decorations( - {create(ast::PipelineStage::kFragment, Source{})}); - mod->AddFunction(fragment_entry); + struct Builder : ModuleBuilder { + void Build() override { + auto* fragment_entry = + create("fragment_entry", ast::VariableList{}, ty.void_, + create(Source{})); + fragment_entry->set_decorations({create( + ast::PipelineStage::kFragment, Source{})}); + mod->AddFunction(fragment_entry); - auto* compute_entry = create( - "compute_entry", ast::VariableList{}, create(), - create(Source{})); - compute_entry->set_decorations( - {create(ast::PipelineStage::kCompute, Source{})}); - mod->AddFunction(compute_entry); + auto* compute_entry = + create("compute_entry", ast::VariableList{}, ty.void_, + create(Source{})); + compute_entry->set_decorations({create( + ast::PipelineStage::kCompute, Source{})}); + mod->AddFunction(compute_entry); + } + }; - manager->Run(mod); + auto result = Transform(Builder{}.Module()); + ASSERT_FALSE(result.diagnostics.contains_errors()) + << diag::Formatter().format(result.diagnostics); auto* expected = R"(Module{ Function fragment_entry -> __void @@ -178,7 +222,7 @@ TEST_F(EmitVertexPointSizeTransformTest, NonVertexStage) { } } )"; - EXPECT_EQ(expected, mod->to_str()); + EXPECT_EQ(expected, result.module.to_str()); } } // namespace