#include <metal_stdlib>
using namespace metal;

template<typename T, size_t N>
struct tint_array {
  const constant T& operator[](size_t i) const constant { return elements[i]; }
  device T& operator[](size_t i) device { return elements[i]; }
  const device T& operator[](size_t i) const device { return elements[i]; }
  thread T& operator[](size_t i) thread { return elements[i]; }
  const thread T& operator[](size_t i) const thread { return elements[i]; }
  threadgroup T& operator[](size_t i) threadgroup { return elements[i]; }
  const threadgroup T& operator[](size_t i) const threadgroup { return elements[i]; }
  T elements[N];
};

struct tint_module_vars_struct {
  threadgroup tint_array<int, 4>* v;
};

struct tint_symbol_1 {
  tint_array<int, 4> tint_symbol;
};

tint_array<int, 4> foo(tint_module_vars_struct tint_module_vars) {
  threadgroup_barrier(mem_flags::mem_threadgroup);
  tint_array<int, 4> const v_1 = (*tint_module_vars.v);
  threadgroup_barrier(mem_flags::mem_threadgroup);
  return v_1;
}

void main_inner(uint tint_local_index, tint_module_vars_struct tint_module_vars) {
  {
    uint v_2 = 0u;
    v_2 = tint_local_index;
    while(true) {
      uint const v_3 = v_2;
      if ((v_3 >= 4u)) {
        break;
      }
      (*tint_module_vars.v)[v_3] = 0;
      {
        v_2 = (v_3 + 1u);
      }
    }
  }
  threadgroup_barrier(mem_flags::mem_threadgroup);
  foo(tint_module_vars);
}

[[max_total_threads_per_threadgroup(1)]]
kernel void v_4(uint tint_local_index [[thread_index_in_threadgroup]], threadgroup tint_symbol_1* v_5 [[threadgroup(0)]]) {
  tint_module_vars_struct const tint_module_vars = tint_module_vars_struct{.v=(&(*v_5).tint_symbol)};
  main_inner(tint_local_index, tint_module_vars);
}
