// 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.

#ifndef FUZZERS_TINT_AST_FUZZER_UTIL_H_
#define FUZZERS_TINT_AST_FUZZER_UTIL_H_

#include <vector>

#include "src/ast/module.h"
#include "src/ast/variable_decl_statement.h"
#include "src/program.h"
#include "src/sem/block_statement.h"
#include "src/sem/statement.h"
#include "src/sem/variable.h"

namespace tint {
namespace fuzzers {
namespace ast_fuzzer {
namespace util {
/// @file

/// @brief Returns all in-scope variables (including formal function parameters)
/// related to statement `curr_stmt`.
///
/// These variables are additionally filtered by applying a predicate `pred`.
///
/// @tparam Pred - a predicate that accepts a `const sem::Variable*` and returns
///     `bool`.
/// @param program - the program to look for variables in.
/// @param curr_stmt - the current statement. Everything below it is not in
///     scope.
/// @param pred - a predicate (e.g. a function pointer, functor, lambda etc) of
///     type `Pred`.
/// @return a vector of all variables that can be accessed from `curr_stmt`.
template <typename Pred>
std::vector<const sem::Variable*> GetAllVarsInScope(
    const tint::Program& program,
    const sem::Statement* curr_stmt,
    Pred&& pred) {
  std::vector<const sem::Variable*> result;

  // Walk up the hierarchy of blocks in which `curr_stmt` is contained.
  for (const auto* block = curr_stmt->Block(); block; block = block->Block()) {
    for (const auto* stmt : *block->Declaration()) {
      if (stmt == curr_stmt->Declaration()) {
        // `curr_stmt` was found. This is only possible if `block is the
        // enclosing block of `curr_stmt` since the AST nodes are not shared.
        // Because of all this, skip the iteration of the inner loop since
        // the rest of the instructions in the `block` are not visible from the
        // `curr_stmt`.
        break;
      }

      if (const auto* var_node = tint::As<ast::VariableDeclStatement>(stmt)) {
        const auto* sem_var = program.Sem().Get(var_node->variable());
        if (pred(sem_var)) {
          result.push_back(sem_var);
        }
      }
    }
  }

  // Process function parameters.
  for (const auto* param : curr_stmt->Function()->params()) {
    const auto* sem_var = program.Sem().Get(param);
    if (pred(sem_var)) {
      result.push_back(sem_var);
    }
  }

  // Global variables do not belong to any ast::BlockStatement.
  for (const auto* global_decl : program.AST().GlobalDeclarations()) {
    if (global_decl == curr_stmt->Function()) {
      // The same situation as in the previous loop. The current function has
      // been reached. If there are any variables declared below, they won't be
      // visible in this function. Thus, exit the loop.
      break;
    }

    if (const auto* global_var = tint::As<ast::Variable>(global_decl)) {
      const auto* sem_node = program.Sem().Get(global_var);
      if (pred(sem_node)) {
        result.push_back(sem_node);
      }
    }
  }

  return result;
}

}  // namespace util
}  // namespace ast_fuzzer
}  // namespace fuzzers
}  // namespace tint

#endif  // FUZZERS_TINT_AST_FUZZER_UTIL_H_
