blob: d07df65316f71d64ff3ac813593285e877c26915 [file] [log] [blame]
# 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.
"""Recipe for building Dart toolchain."""
from recipe_engine.config import Enum
from recipe_engine.recipe_api import Property
DEPS = [
"fuchsia/git",
"fuchsia/goma",
"fuchsia/macos_sdk",
"fuchsia/status_check",
"fuchsia/upload",
"recipe_engine/buildbucket",
"recipe_engine/cipd",
"recipe_engine/context",
"recipe_engine/file",
"recipe_engine/json",
"recipe_engine/path",
"recipe_engine/platform",
"recipe_engine/properties",
"recipe_engine/raw_io",
"recipe_engine/step",
]
DEPOT_TOOLS_GIT = "https://chromium.googlesource.com/chromium/tools/depot_tools"
DART_SDK_GIT = "https://dart.googlesource.com/sdk.git"
PROPERTIES = {
"repository": Property(kind=str, help="Git repository URL", default=DART_SDK_GIT),
"revision": Property(kind=str, help="Revision", default=None),
"host_cpu": Property(
kind=Enum("arm64", "x64"),
help="GN $host_cpu toolchain will run on",
default=None,
),
"host_os": Property(
kind=Enum("linux", "mac"),
help="GN $host_os toolchain will run on",
default=None,
),
}
# Fuchsia targets the toolchain must support.
FUCHSIA_TARGETS = [
"arm64",
"x64",
]
GN_CIPD_CPU_MAP = {
"x64": "amd64",
}
def RunSteps(api, repository, revision, host_cpu, host_os):
api.goma.ensure()
gitiles_commit = api.buildbucket.build_input.gitiles_commit
if gitiles_commit.host and gitiles_commit.project and gitiles_commit.id:
repository = "https://%s/%s" % (gitiles_commit.host, gitiles_commit.project)
revision = gitiles_commit.id
if not host_cpu:
# TODO(mcgrathr): Native bots are all x64 and api.platform.arch is useless.
host_cpu = "x64"
if not host_os:
host_os = api.platform.name
cipd_platform = "%s-%s" % (host_os, GN_CIPD_CPU_MAP.get(host_cpu, host_cpu))
with api.step.nest("ensure_packages"):
with api.context(infra_steps=True):
pkgs = api.cipd.EnsureFile()
pkgs.add_package("infra/ninja/${platform}", "version:1.8.2")
if host_os == "linux":
pkgs.add_package("fuchsia/sysroot/%s" % cipd_platform, "latest")
cipd_dir = api.path["start_dir"].join("cipd")
api.cipd.ensure(cipd_dir, pkgs)
ninja = [cipd_dir.join("ninja"), "-j%d" % api.goma.jobs]
with api.context(infra_steps=True):
with api.step.nest("depot_tools"):
# TODO(phosek): Move this to a named cache so it's shared across builds.
depot_tools_dir = api.path["start_dir"].join("depot_tools")
api.git.checkout(DEPOT_TOOLS_GIT, depot_tools_dir, submodules=False)
with api.step.nest("dart-sdk"):
sdk_dir = api.path["start_dir"].join("dart", "sdk")
revision = api.git.checkout(
repository, sdk_dir, ref=revision, submodules=False
)
# Use gclient to fetch the DEPS, but don't let it change dart/sdk itself.
dart_dir = api.path["start_dir"].join("dart")
with api.context(
infra_steps=True, cwd=dart_dir, env_prefixes={"PATH": [depot_tools_dir]}
):
api.step(
"gclient config",
[
"gclient",
"config",
"--unmanaged",
# TODO(mcgrathr): Set --cache-dir?
"-v",
DART_SDK_GIT,
],
)
api.step(
"gclient sync",
[
"gclient",
"sync",
"--no-history",
"-v",
"--output-json",
api.json.output(),
],
)
dart_targets = sorted(
set(
[host_cpu]
+ ["sim" + cpu if cpu != host_cpu else cpu for cpu in FUCHSIA_TARGETS]
)
)
def out_dir(cpu):
return sdk_dir.join(
"xcodebuild" if api.platform.is_mac else "out", "Release" + cpu.upper()
)
with api.macos_sdk(), api.goma.build_with_goma(), api.context(cwd=sdk_dir):
# TODO(mcgrathr): Move this logic into a host_build recipe module shared
# with gcc_toolchain.py and others.
if host_os == "linux":
host_sysroot = cipd_dir
elif host_os == "mac":
with api.context(infra_steps=True):
step_result = api.step(
"xcrun",
["xcrun", "--sdk", "macosx", "--show-sdk-path"],
stdout=api.raw_io.output(name="sdk-path", add_output_log=True),
step_test_data=lambda: api.raw_io.test_api.stream_output(
"/some/xcode/path"
),
)
host_sysroot = step_result.stdout.strip()
else: # pragma: no cover
assert False, "what platform?"
gn_common = [
"tools/gn.py",
"-v",
"--mode=release",
"--goma",
# It actually wants a sysroot for the build host regardless of what
# Dart target CPU the build is configured for, but wants it in the
# form `%(target_cpu)s=%(host_sysroot)s`.
"--target-sysroot="
+ ",".join("%s=%s" % (cpu, host_sysroot) for cpu in dart_targets),
]
api.step(
"gn host (%s)" % host_cpu,
gn_common + ["--arch=%s" % host_cpu, "--platform-sdk"],
)
for cpu in dart_targets:
if cpu != host_cpu:
api.step("gn %s" % cpu, gn_common + ["--arch=%s" % cpu])
api.step(
"build host (%s) SDK" % host_cpu,
ninja
+ [
"-C",
out_dir(host_cpu),
"create_sdk",
"gen_snapshot",
"gen_snapshot_product",
],
)
for cpu in dart_targets:
api.step(
"build %s" % cpu,
ninja
+ [
"-C",
out_dir(cpu),
"gen_snapshot_fuchsia",
"gen_snapshot_product_fuchsia",
"runtime",
],
)
for cpu in dart_targets:
remote_config = "dartk-linux-release-%s" % cpu
local_config = "dartk-%s-release-%s" % (host_os, cpu)
api.step(
"run tests",
[
"tools/sdks/dart-sdk/bin/dart",
"tools/test.dart",
"-n",
remote_config,
"-N",
local_config,
"--",
"--progress=line",
"--report",
"--time",
"vm",
"language",
],
)
with api.step.nest("install"):
pkg_dir = api.path["cleanup"].join("dart-sdk")
api.file.copytree(
"install dart-sdk",
out_dir(host_cpu).join("dart-sdk"),
pkg_dir,
symlinks=True,
)
for cpu, is_host in [(host_cpu, True)] + [(cpu, False) for cpu in dart_targets]:
exe_dir = out_dir(cpu).join("exe.stripped")
if not is_host and cpu.startswith("sim"):
cpu = cpu[3:]
for tool in ["gen_snapshot", "gen_snapshot_product"]:
src = exe_dir.join(tool + ("" if is_host else "_fuchsia"))
dst_name = "%s.%s-%s" % (tool, host_os if is_host else "fuchsia", cpu)
dst = pkg_dir.join("bin", dst_name)
api.file.copy("install %s" % dst_name, src, dst)
dart_sdk_version = api.file.read_text(
"read dart-sdk version",
pkg_dir.join("version"),
test_data="2.0.0-edge." + revision + "\n",
).strip()
api.upload.cipd_package(
"fuchsia/dart-sdk/" + cipd_platform,
pkg_dir,
[api.upload.DirectoryPath(pkg_dir)],
{"git_revision": revision},
repository,
extra_tags={"dart_sdk_version": dart_sdk_version},
)
def GenTests(api):
revision = "301b5a1f16414bc031091eb214ddd6c589e6ed9a"
for platform in ("linux", "mac"):
yield (
api.status_check.test(platform)
+ api.platform.name(platform)
+ api.step_data(
"dart-sdk.git rev-parse", api.raw_io.stream_output(revision)
)
+ api.buildbucket.ci_build(git_repo=DART_SDK_GIT, revision=revision)
)
yield (
api.status_check.test(platform + "_new")
+ api.platform.name(platform)
+ api.buildbucket.ci_build(git_repo=DART_SDK_GIT, revision=revision)
+ api.step_data(
"dart-sdk.git rev-parse", api.raw_io.stream_output(revision)
)
+ api.step_data(
"cipd.cipd search fuchsia/dart-sdk/"
+ platform
+ "-amd64 "
+ "git_revision:"
+ revision,
api.json.output({"result": []}),
)
+ api.step_data("gclient sync", api.json.output({"solutions": {}}))
)
for host_os, host_cpu, cipd_host_cpu in [("linux", "arm64", "arm64")]:
cipd_platform = host_os + "-" + cipd_host_cpu
yield (
api.status_check.test(host_os + "_cross")
+ api.platform.name(host_os)
+ api.properties(host_cpu=host_cpu, host_os=host_os)
+ api.buildbucket.ci_build(git_repo=DART_SDK_GIT, revision=revision)
+ api.step_data(
"dart-sdk.git rev-parse", api.raw_io.stream_output(revision)
)
+ api.step_data(
"cipd.cipd search fuchsia/dart-sdk/"
+ cipd_platform
+ " git_revision:"
+ revision,
api.json.output({"result": []}),
)
+ api.step_data("gclient sync", api.json.output({"solutions": {}}))
)