# Copyright 2018 The Fuchsia Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

import("//build/cpp/fidl_cpp.gni")
import("//build/dart/toolchain.gni")
import("//build/fidl/toolchain.gni")
import("//build/fidl/wireformat.gni")
import("//build/go/toolchain.gni")
import("//build/rust/toolchain.gni")

# Declares a FIDL library.
#
# Depending on the toolchain in which this targets is expanded, it will yield
# different results:
#   - in the FIDL toolchain, it will compile its source files into an
#     intermediate representation consumable by language bindings generators;
#   - in the target or shared toolchain, this will produce a source_set
#     containing C++ bindings.
#
# Parameters
#
#   sources (required)
#     List of paths to library source files.
#
#   name (optional)
#     Name of the library.
#     Defaults to the target's name.
#
#   sdk_category (optional)
#     Publication level of the library in SDKs.
#     See //build/sdk/sdk_atom.gni.
#
#   api (optional)
#     Path to the file representing the API of this library.
#     This file is used to ensure modifications to the library's API are
#     explicitly acknowledged. It is mandatory for publication categories of
#     "partner" or "public".
#     Defaults to "<target name>.api".
#
#   excluded_checks (optional)
#     A list of fidl-lint check IDs to ignore (by passing the command line flag
#     "-e some-check-id" for each value).
#
#   fuzzers (optional)
#     Protocol/methods for which to generate LibFuzzer fuzz targets. Example:
#       [
#         {
#           # Required:
#           protocol = "fully.qualified.FIDLProtocolName"
#           # Optional. Default: All methods in protocol.
#           methods = [ "MethodName1", "MethodName2", ... ]
#         },
#         ...
#       ]
#
#   experimental_flags (optional)
#     A list of experimental fidlc features to enable.
#
#   non_fidl_deps (optional)
#     A list of non-FIDL dependency targets, i.e. targets that don't contribute
#     FIDL artifacts, but should be built before this target regardless.
#
#   should_lint (optional, boolean)
#     If set to false, the linting step is skipped.

template("fidl") {
  if (defined(invoker.sdk_category)) {
    not_needed(invoker, [ "sdk_category" ])
  }
  if (defined(invoker.api)) {
    not_needed(invoker, [ "api" ])
  }
  if (defined(invoker.excluded_checks)) {
    not_needed(invoker, [ "excluded_checks" ])
  }
  if (defined(invoker.fuzzers)) {
    not_needed(invoker, [ "fuzzers" ])
  }
  if (defined(invoker.experimental_flags)) {
    not_needed(invoker, [ "experimental_flags" ])
  }

  # Allow generated targets visibility to their dependant generated targets
  if (defined(invoker.visibility)) {
    invoker.visibility += [ ":*" ]
  }

  assert(!defined(invoker.deps),
         "All FIDL dependencies are inherently " +
             "public, use 'public_deps' instead of 'deps'.")

  deps = []

  if (defined(invoker.non_fidl_deps)) {
    deps += invoker.non_fidl_deps
  }

  if (current_toolchain == dart_toolchain) {
    import("//build/dart/fidl_dart.gni")

    fidl_dart(target_name) {
      forward_variables_from(invoker, "*")
    }
  } else if (current_toolchain == rust_toolchain) {
    import("//build/rust/fidl_rust.gni")

    fidl_rust(target_name) {
      forward_variables_from(invoker, "*")
    }
  } else if (current_toolchain == go_toolchain) {
    import("//build/go/fidl_go.gni")

    fidl_go(target_name) {
      forward_variables_from(invoker, "*")
    }
  } else {
    import("//build/c/fidl_c.gni")
    import("//build/rust/fidl_rust_library.gni")

    if (current_toolchain == fidl_toolchain) {
      import("//build/fidl/fidl_library.gni")

      if (string_replace(invoker.target_out_dir, "zircon/public", "") !=
          invoker.target_out_dir) {
        # For now, with //zircon dependencies, we will exclude all known checks on their FIDL
        # libraries. I need to figure out how to set excluded_checks in a BUILD.gn file somewhere.
        # I'm trying to find out where the zircon fidl() templates are being invoked. It doesn't
        # seem to be from the zircon/system/fidl/<xyz>/BUILD.gn file's zircon version of
        # fidl_library() template. Setting "excluded_checks" there has no effect on the non-zircon,
        # "//build/fidl"-based deps.
        excluded_checks = [
          "too-many-nested-libraries",
          "disallowed-library-name-component",
          "name-repeats-library-name",
          "wrong-prefix-for-platform-source-library",
          "invalid-copyright-for-platform-source-library",
          "todo-should-not-be-doc-comment",
          "copyright-should-not-be-doc-comment",
          "no-trailing-comment",
          "invalid-case-for-primitive-alias",
          "invalid-case-for-constant",
          "invalid-case-for-decl-name",
          "name-repeats-enclosing-type-name",
          "protocol-name-includes-service",
          "event-names-must-start-with-on",
          "invalid-case-for-decl-member",
          "string-bounds-not-specified",
          "vector-bounds-not-specified",
        ]
      } else {
        excluded_checks = []
      }

      if (defined(invoker.excluded_checks)) {
        excluded_checks = invoker.excluded_checks
      }
      fidl_library(target_name) {
        forward_variables_from(invoker, "*")
      }
    }

    if (is_fuchsia) {
      hlcpp_public_deps = [ "//sdk/lib/fidl/cpp" ]
      _llcpp_generators = [
        {
          target_suffix = "llcpp"
          fidlgen_generator = "llcpp"
          output_stem = "llcpp/fidl"
          additional_public_deps = [
            "//zircon/public/lib/fidl",
            "//zircon/public/lib/fidl-llcpp",
            "//zircon/public/lib/fit",
          ]
        },
      ]
    } else {
      hlcpp_public_deps = [ "//sdk/lib/fidl/cpp:cpp_base" ]
      _llcpp_generators = []
    }

    fidl_cpp(target_name) {
      forward_variables_from(invoker, "*")
      generators = [
        {
          fidlgen_tool = "//tools/fidl/fidlgen_hlcpp"
          fidlgen_generator = "cpp"
          output_stem = "cpp/fidl"
          additional_public_deps = hlcpp_public_deps
        },
        {
          fidlgen_tool = "//tools/fidl/fidlgen_libfuzzer"
          fidlgen_generator = "libfuzzer"
          output_stem = "cpp/libfuzzer"
          target_suffix = "libfuzzer"
          additional_public_deps = [
            "//zircon/system/ulib/async-default",
            "//zircon/system/ulib/async-loop:async-loop-cpp",
            "//zircon/system/ulib/async-loop:async-loop-default",
          ]
          header_only = true

          # The generated headers `#include` the hlcpp bindings headers
          # generated by the clause above, so the generated target needs
          # that bindings library target in its public_deps.
          generated_deps_target_suffix = [ "" ]
        },
      ]
      llcpp_generators = _llcpp_generators
    }

    fidl_tables(target_name) {
      forward_variables_from(invoker,
                             [
                               "testonly",
                               "visibility",
                             ])
    }

    # TODO(cramertj): remove pending TC-81.
    fidl_rust_library(target_name) {
      forward_variables_from(invoker, "*")
    }

    if (is_fuchsia) {
      fidl_c_client(target_name) {
        forward_variables_from(invoker, "*")
      }

      fidl_c_server(target_name) {
        forward_variables_from(invoker, "*")
      }

      group("${target_name}_c") {
        forward_variables_from(invoker,
                               [
                                 "testonly",
                                 "visibility",
                               ])

        public_deps = [
          ":${target_name}_client",
          ":${target_name}_server",
        ]
      }
    }
  }
}
