define [see_through] import: group

name = $string.replace($project, 'liboneapi-', '')

source redist.build

json{$name-manifest}: $src_root/manifest manifest.json

manifest_json = [json_object] $json.load($src_base/manifest.json)

package_ver = "$(version.major).$(version.minor).$(version.patch)"

for plat: [json_object] ($manifest_json["$project"])
{
  plat_key   = $member_name($plat)
  plat_val   = $member_value($plat)
  enabled    = [bool] ($cc.target.cpu-$cc.target.class == $plat_key)
  devel_id   = [string] ($plat_val["devel_id"])
  runtime_id = [string] ($plat_val["runtime_id"])

  if (!$empty($devel_id))
  {
    json{$devel_id...}:   json{$name-manifest}
    archive{$name-intel.oneapi.$(name).devel-$package_ver...}: json{$devel_id...}: include = $enabled
  }
  if (!$empty($runtime_id))
  {
    json{$runtime_id...}: json{$name-manifest}
    archive{$name-intel.oneapi.$(name).runtime-$package_ver...}: json{$runtime_id...}: include = $enabled
  }
}

extract{$name-devel}:   archive{$name-intel.oneapi.$(name).devel-$package_ver...}
extract{$name-runtime}: archive{$name-intel.oneapi.$(name).runtime-$package_ver...}

import{$name-headers}: extract{$name-devel}: update = match
import{$name-legals}: extract{$name-runtime}: update = match

import{$name-headers}:
{{
  o = $directory($>[0])
  d = $o/$name($>[0]).files

  hdrs = [paths]
  for g : $filter($<, group)
    if test -d $o/$name($g)/include
      find "$o/$name($g)/include" -type f -name "*.h*" \
        | set -n f [paths]
      hdrs += $f
    end
  end

  depdb dyndep \
    --dyn-target \
    --target-cwd "$o" \
    --target-what 'imported headers' \
    --target-extension-type 'h=h' \
    --target-extension-type 'hpp=hxx' \
    --format lines \
    --file $d \
    -- \
      echo $regex.merge($hdrs, '(.+)', '\1\n') >$d

  diag import $>

  for t : $filter_out($>, group)
    touch $path($t)
  end
}}

import{$name-legals}:
{{
  o = $directory($>[0])
  d = $o/$name($>[0]).files

  files = [paths]
  for g : $filter($<, group)
    if test -d $o/$name($g)/share/doc/$name
      find "$o/$name($g)/share/doc/$name" -type f -name "*" \
        | set -n f [paths]
      files += $f
    end
  end

  depdb dyndep \
    --dyn-target \
    --target-cwd "$o" \
    --target-what 'imported legals' \
    --target-default-type 'legal' \
    --target-extension-type '=legal' \
    --format lines \
    --file $d \
    -- \
      echo $regex.merge($files, '(.+)', '\1\n') >$d

  diag import $>

  for t : $filter_out($>, group)
    touch $path($t)
  end
}}

pub_hdrs = [strings] "-I$out_base/$name-devel/include"

./: json{package}
json = [json_object] $json.load($src_base/package.json)
for plat: [json_object] $json
{
  plat_key = $member_name($plat)
  if ($plat_key != 'exes')
  {
    enabled  = [bool] ($cc.target.cpu-$cc.target.class == $plat_key)

    for m: [json_object] ($member_value($plat))
    {
      n = $member_name($m)
      v = $member_value($m)
      loptions =
      libs = [paths]
      libi = [paths]
      liba = [paths]
      depends = [names]
      for x: [json_array] ($v["loptions"])
      {
        loptions += [paths] $x
      }
      for x: [json_array] ($v["libs"])
      {
        libs += [paths] $out_base/$x
      }
      for x: [json_array] ($v["libi"])
      {
        libi += [paths] $out_base/$x
      }
      for x: [json_array] ($v["liba"])
      {
        liba += [paths] $out_base/$x
      }
      for x: [json_array] ($v["depends"])
      {
        depends += [names] $x
      }

      ./: libs{$n}:
      {
        include = $enabled
        clean = false
      }

      # The "bundles" are either both shared & import libs (Windows),
      # or shared-only (implicitly loaded, just needs to respect RPATH).
      # Also explicitly append the extract-targets as inner-most prerequisites
      # to make sure they are always unpacked first.
      #
      [rule_hint=cxx.link] \
      libs{$n}: import{$name-legals} import{$name-headers}: \
                  extract{$name-devel} extract{$name-runtime}:
      {
        include = $enabled
        update  = match
      }

      if (!$empty($depends))
      {
        # Inter-dependencies
        #
        libs{$n}: libs{$depends}: include = $enabled
        if $enabled
        {
          libs{$n}: cc.export.libs += libs{$depends}
        }
      }
      if (!$empty($libs) && !$empty($libi))
      {
        <libs{$libs} libi{$libi}>: extract{$name-devel} extract{$name-runtime}: include = $enabled
        libs{$n}: libs{$libs}: include = $enabled
        if $enabled
        {
          # Export options.
          #
          libs{$n}:
          {
            cc.export.libs =+ libs{$libs}
          }
        }
      }
      elif (!$empty($libs))
      {
        <libs{$libs}>: extract{$name-devel} extract{$name-runtime}: include = $enabled
        libs{$n}: libs{$libs}: include = $enabled
        if $enabled
        {
          # Export options.
          #
          if ($cc.target.class != 'windows')
          {
            libs{$n}:
            {
              cc.export.libs =+ libs{$libs} $loptions
            }
          }
        }
      }
      elif (!$empty($libi))
      {
        fail "$n: 'libi' without 'libs' is not supported; use 'liba' for static-link archives."
      }
      elif ($empty($liba))
      {
        fail "$n: No shared, import, or static libraries specified. See '$src_base/package.json'."
      }

      if (!$empty($liba))
      {
        <liba{$liba}>: extract{$name-devel}: include = $enabled
        libs{$n}: liba{$liba}: include = $enabled
        if $enabled
        {
          libs{$n}: cc.export.libs += liba{$liba}
        }
      }

      # Export options.
      #
      libs{$n}:
      {
        cc.type = cc
        cc.export.poptions = $pub_hdrs
      }

      # For pre-releases use the complete version to make sure they cannot
      # be used in place of another pre-release or the final version. See
      # the version module for details on the version.* variable values.
      #
      if $version.pre_release
        lib{$name}: bin.lib.version = "-$version.project_id"
      else
        lib{$name}: bin.lib.version = "-$version.major.$version.minor"
    }
  }
}

# Recreate the upstream include/ hierarchy under, e.g., /usr/include/.
#
$name-devel/include/{h hxx}{*}:
{
  install         = include/
  install.subdirs = true
}

# Executables declared in package.json.
#
for plat: [json_object] ($json["exes"])
{
  plat_key = $member_name($plat)
  enabled  = [bool] ($cc.target.cpu-$cc.target.class == $plat_key)

  for m: [json_object] ($member_value($plat))
  {
    p = $member_value($m)
    if ($cc.target.class == 'windows')
      p = "$(p).exe"

    ./: exe{$p}: include = $enabled
    <exe{$p}>: extract{$name-runtime}: include = $enabled
  }
}

# No registered rule matches a pre-built exe that has no source prerequisites
# and does not yet exist on disk. This ad-hoc regex pattern rule provides an
# explicit perform(update)/perform(clean) entry point for all path-qualified
# exe targets so build2 can attach the operation to them.
#
exe{~'/(.+)/'}: $name-runtime/fsdir{bin} extract{$name-runtime}
{{
  diag import $> $<
  touch $path($>)
}}
