// Copyright 2021 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/transform/calculate_array_length.h"

#include "src/transform/simplify_pointers.h"
#include "src/transform/test_helper.h"
#include "src/transform/unshadow.h"

namespace tint {
namespace transform {
namespace {

using CalculateArrayLengthTest = TransformTest;

TEST_F(CalculateArrayLengthTest, Error_MissingCalculateArrayLength) {
  auto* src = "";

  auto* expect =
      "error: tint::transform::CalculateArrayLength depends on "
      "tint::transform::SimplifyPointers but the dependency was not run";

  auto got = Run<CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, Basic) {
  auto* src = R"(
@group(0) @binding(0) var<storage, read> sb : array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var len : u32 = arrayLength(&sb);
}
)";

  auto* expect = R"(
@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : array<i32>, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = (tint_symbol_1 / 4u);
  var len : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, BasicInStruct) {
  auto* src = R"(
struct SB {
  x : i32;
  arr : array<i32>;
};

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var len : u32 = arrayLength(&sb.arr);
}
)";

  auto* expect = R"(
struct SB {
  x : i32;
  arr : array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = ((tint_symbol_1 - 4u) / 4u);
  var len : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, InSameBlock) {
  auto* src = R"(
@group(0) @binding(0) var<storage, read> sb : array<i32>;;

@stage(compute) @workgroup_size(1)
fn main() {
  var a : u32 = arrayLength(&sb);
  var b : u32 = arrayLength(&sb);
  var c : u32 = arrayLength(&sb);
}
)";

  auto* expect = R"(
@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : array<i32>, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = (tint_symbol_1 / 4u);
  var a : u32 = tint_symbol_2;
  var b : u32 = tint_symbol_2;
  var c : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, InSameBlock_Struct) {
  auto* src = R"(
struct SB {
  x : i32;
  arr : array<i32>;
};

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var a : u32 = arrayLength(&sb.arr);
  var b : u32 = arrayLength(&sb.arr);
  var c : u32 = arrayLength(&sb.arr);
}
)";

  auto* expect = R"(
struct SB {
  x : i32;
  arr : array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = ((tint_symbol_1 - 4u) / 4u);
  var a : u32 = tint_symbol_2;
  var b : u32 = tint_symbol_2;
  var c : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, WithStride) {
  auto* src = R"(
@group(0) @binding(0) var<storage, read> sb : @stride(64) array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var len : u32 = arrayLength(&sb);
}
)";

  auto* expect = R"(
@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : @stride(64) array<i32>, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : @stride(64) array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = (tint_symbol_1 / 64u);
  var len : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, WithStride_InStruct) {
  auto* src = R"(
struct SB {
  x : i32;
  y : f32;
  arr : @stride(64) array<i32>;
};

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var len : u32 = arrayLength(&sb.arr);
}
)";

  auto* expect = R"(
struct SB {
  x : i32;
  y : f32;
  arr : @stride(64) array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb, &(tint_symbol_1));
  let tint_symbol_2 : u32 = ((tint_symbol_1 - 8u) / 64u);
  var len : u32 = tint_symbol_2;
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, Nested) {
  auto* src = R"(
struct SB {
  x : i32;
  arr : array<i32>;
};

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  if (true) {
    var len : u32 = arrayLength(&sb.arr);
  } else {
    if (true) {
      var len : u32 = arrayLength(&sb.arr);
    }
  }
}
)";

  auto* expect = R"(
struct SB {
  x : i32;
  arr : array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  if (true) {
    var tint_symbol_1 : u32 = 0u;
    tint_symbol(sb, &(tint_symbol_1));
    let tint_symbol_2 : u32 = ((tint_symbol_1 - 4u) / 4u);
    var len : u32 = tint_symbol_2;
  } else {
    if (true) {
      var tint_symbol_3 : u32 = 0u;
      tint_symbol(sb, &(tint_symbol_3));
      let tint_symbol_4 : u32 = ((tint_symbol_3 - 4u) / 4u);
      var len : u32 = tint_symbol_4;
    }
  }
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, MultipleStorageBuffers) {
  auto* src = R"(
struct SB1 {
  x : i32;
  arr1 : array<i32>;
};

struct SB2 {
  x : i32;
  arr2 : array<vec4<f32>>;
};

@group(0) @binding(0) var<storage, read> sb1 : SB1;

@group(0) @binding(1) var<storage, read> sb2 : SB2;

@group(0) @binding(2) var<storage, read> sb3 : array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var len1 : u32 = arrayLength(&(sb1.arr1));
  var len2 : u32 = arrayLength(&(sb2.arr2));
  var len3 : u32 = arrayLength(&sb3);
  var x : u32 = (len1 + len2 + len3);
}
)";

  auto* expect = R"(
@internal(intrinsic_buffer_size)
fn tint_symbol_6(@internal(disable_validation__ignore_constructible_function_parameter) buffer : array<i32>, result : ptr<function, u32>)

struct SB1 {
  x : i32;
  arr1 : array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB1, result : ptr<function, u32>)

struct SB2 {
  x : i32;
  arr2 : array<vec4<f32>>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol_3(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB2, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> sb1 : SB1;

@group(0) @binding(1) var<storage, read> sb2 : SB2;

@group(0) @binding(2) var<storage, read> sb3 : array<i32>;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(sb1, &(tint_symbol_1));
  let tint_symbol_2 : u32 = ((tint_symbol_1 - 4u) / 4u);
  var tint_symbol_4 : u32 = 0u;
  tint_symbol_3(sb2, &(tint_symbol_4));
  let tint_symbol_5 : u32 = ((tint_symbol_4 - 16u) / 16u);
  var tint_symbol_7 : u32 = 0u;
  tint_symbol_6(sb3, &(tint_symbol_7));
  let tint_symbol_8 : u32 = (tint_symbol_7 / 4u);
  var len1 : u32 = tint_symbol_2;
  var len2 : u32 = tint_symbol_5;
  var len3 : u32 = tint_symbol_8;
  var x : u32 = ((len1 + len2) + len3);
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

TEST_F(CalculateArrayLengthTest, Shadowing) {
  auto* src = R"(
struct SB {
  x : i32;
  arr : array<i32>;
};

@group(0) @binding(0) var<storage, read> a : SB;
@group(0) @binding(1) var<storage, read> b : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  let x = &a;
  var a : u32 = arrayLength(&a.arr);
  {
    var b : u32 = arrayLength(&((*x).arr));
  }
}
)";

  auto* expect =
      R"(
struct SB {
  x : i32;
  arr : array<i32>;
}

@internal(intrinsic_buffer_size)
fn tint_symbol(@internal(disable_validation__ignore_constructible_function_parameter) buffer : SB, result : ptr<function, u32>)

@group(0) @binding(0) var<storage, read> a : SB;

@group(0) @binding(1) var<storage, read> b : SB;

@stage(compute) @workgroup_size(1)
fn main() {
  var tint_symbol_1 : u32 = 0u;
  tint_symbol(a, &(tint_symbol_1));
  let tint_symbol_2 : u32 = ((tint_symbol_1 - 4u) / 4u);
  var a_1 : u32 = tint_symbol_2;
  {
    var tint_symbol_3 : u32 = 0u;
    tint_symbol(a, &(tint_symbol_3));
    let tint_symbol_4 : u32 = ((tint_symbol_3 - 4u) / 4u);
    var b_1 : u32 = tint_symbol_4;
  }
}
)";

  auto got = Run<Unshadow, SimplifyPointers, CalculateArrayLength>(src);

  EXPECT_EQ(expect, str(got));
}

}  // namespace
}  // namespace transform
}  // namespace tint
