# Copyright 2023 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/zircon/c_utils.gni")

# Defines an hermetic code blob, which is defined by the following properties
# (enforced at link-time):
#
# * the named function (`entrypoint`) is first in the link order and all of the
#   sources/deps together form a closed set that is collectively hermetic;
# * no dynamic relocations.
#
# It produces the raw binary content of a position-indepdendent executable,
# output to "$target_out_dir/$output_name.bin".  This is the output file of the
# primary target. If $public, $public_configs, or $public_deps is provided
# (even if empty), then a "$target_name.public" source_set() target will also
# be defined; that can be used in $deps of compiling targets that use the
# $public headers.
#
# Parameters
#
#   * allow_rodata
#     - Optional: If true, .rodata* sections in the hermetic code are allowed.
#     By default, only .text* (executable code) sections are permitted.
#     - Type: bool
#     - Default: false
#
#   * add_configs
#     - Optional: Additional configs added to the default list for compilation.
#     - Type: list(label)
#     - Default: []
#
#   * entrypoint
#     - Optional: The name of the symbol (or C function) that is the entrypoint
#     to this code blob.
#     - Type: string
#     - Default: $target_name.
#
#   * output_name
#     - Optional: The output file will be "$target_out_dir/$output_name.bin".
#     - Type: string
#     - Default: target_name
#
#   * public, public_deps, public_configs
#     - Optional: As for source_set(). These are passed on to the
#     "$target_name.public" target rather than the main target.
#     The underlying executable() target implicitly depends on that
#     target, so it gets these configs and deps indirectly and can
#     use the $public headers itself.
#
# Other parameters are as for executable(), except for the `output_*`
# parameters.
#
template("hermetic_code_blob") {
  image_target = target_name
  executable_target = "_hermetic_code_blob.$target_name.executable"

  if (defined(invoker.entrypoint)) {
    entrypoint = invoker.entrypoint
  } else {
    entrypoint = target_name
  }

  allow_rodata = defined(invoker.allow_rodata) && invoker.allow_rodata

  if (defined(invoker.public) || defined(invoker.public_configs) ||
      defined(invoker.public_deps)) {
    public_target = "$target_name.public"
    public_target_deps = [ ":$public_target" ]
  } else {
    public_target_deps = []
  }

  executable(executable_target) {
    forward_variables_from(invoker, [ "testonly" ])
    visibility = [ ":*" ]

    deps = []
    ldflags = []
    exclude_toolchain_tags = []
    forward_variables_from(invoker,
                           "*",
                           [
                             "add_configs",
                             "allow_rodata",
                             "configs",
                             "entrypoint",
                             "metadata",
                             "output_dir",
                             "output_extension",
                             "public",
                             "public_configs",
                             "public_deps",
                             "testonly",
                             "visibility",
                           ])

    deps += public_target_deps

    output_dir = target_out_dir

    configs += [ "//build/config/zircon:hermetic-code-blob" ]
    configs += [ "//build/config/zircon:static-pie-link" ]
    configs -= [ "//build/config/zircon:static-pie-link" ]
    if (defined(invoker.add_configs)) {
      configs += invoker.add_configs
    }

    ldflags += [ "-Wl,-defsym,HERMETIC_ENTRY=$entrypoint" ]
    if (allow_rodata) {
      ldflags += [ "-Wl,-defsym,HERMETIC_RODATA_OK=1" ]
    }

    # This code should use the normal toolchain for its containing environment,
    # kernel vs kernel.phys, etc.  But it cannot use any fancy variants.
    exclude_toolchain_tags += [ "instrumented" ]
  }

  image_binary(image_target) {
    forward_variables_from(invoker,
                           [
                             "output_name",
                             "metadata",
                             "visibility",
                             "testonly",
                           ])
    deps = [ ":$executable_target" ]
    output_dir = target_out_dir

    # We expect no dynamic relocations.
    pure = true
  }

  if (public_target_deps != []) {
    source_set(public_target) {
      forward_variables_from(invoker,
                             [
                               "public",
                               "public_configs",
                               "public_deps",
                               "testonly",
                               "visibility",
                             ])
      if (defined(visibility)) {
        visibility += [ ":*" ]
      }
    }
  }
}
