# Copyright 2020 The Pigweed 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
#
#     https://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.

import("//build_overrides/pigweed.gni")

import("$dir_pw_toolchain/host_clang/toolchains.gni")
import("$dir_pw_unit_test/test.gni")

# Creates a libFuzzer-based fuzzer executable target.
#
# This will link `sources` and `deps` with the libFuzzer compiler runtime. The
# `sources` and `deps` should include a definition of the standard LLVM fuzz
# target function, `LLVMFuzzerTestOneInput`. For more details, see:
#   //pw_fuzzer/docs.rst
#   https://llvm.org/docs/LibFuzzer.html
#
template("pw_fuzzer") {
  # This currently is ONLY supported on Linux and Mac using clang (debug).
  # TODO(pwbug/179): Add Windows here after testing.
  fuzzing_platforms = [
    "linux",
    "mac",
  ]

  fuzzing_toolchains =
      [ get_path_info("$dir_pigweed/targets/host:host_clang_fuzz", "abspath") ]

  # This is how GN says 'elem in list':
  can_fuzz = fuzzing_platforms + [ host_os ] - [ host_os ] != fuzzing_platforms

  can_fuzz = fuzzing_toolchains + [ current_toolchain ] -
             [ current_toolchain ] != fuzzing_toolchains && can_fuzz

  if (can_fuzz && pw_toolchain_SANITIZERS != []) {
    # Build the actual fuzzer using the fuzzing config.
    pw_executable(target_name) {
      forward_variables_from(invoker, "*", [ "visibility" ])
      forward_variables_from(invoker, [ "visibility" ])

      if (!defined(deps)) {
        deps = []
      }
      deps += [ dir_pw_fuzzer ]

      if (!defined(configs)) {
        configs = []
      }
      if (pw_toolchain_OSS_FUZZ_ENABLED) {
        configs += [ "$dir_pw_fuzzer:oss_fuzz" ]
      } else {
        configs += [ "$dir_pw_fuzzer:fuzzing" ]
      }

      _fuzzer_output_dir = "${target_out_dir}/bin"
      if (defined(invoker.output_dir)) {
        _fuzzer_output_dir = invoker.output_dir
      }
      output_dir = _fuzzer_output_dir

      # Metadata for this fuzzer when used as part of a pw_test_group target.
      metadata = {
        tests = [
          {
            type = "fuzzer"
            test_name = target_name
            test_directory = rebase_path(output_dir, root_build_dir)
          },
        ]
      }
    }

    # No-op target to satisfy `pw_test_group`. It is empty as we don't want to
    # automatically run fuzzers.
    group(target_name + ".run") {
    }

    # No-op target to satisfy `pw_test`. It is empty as we don't need a separate
    # lib target.
    group(target_name + ".lib") {
    }
  } else {
    # Build a unit test that exercise the fuzz target function.
    pw_test(target_name) {
      # TODO(b/234891784): Re-enable when there's better configurability for
      # on-device fuzz testing.
      enable_if = false
      sources = []
      deps = []
      forward_variables_from(invoker, "*", [ "visibility" ])
      forward_variables_from(invoker, [ "visibility" ])
      sources += [ "$dir_pw_fuzzer/pw_fuzzer_disabled.cc" ]
      deps += [ "$dir_pw_fuzzer:run_as_unit_test" ]
    }
  }
}
