Skip to content

Commit

Permalink
Build stdlib from inside the aspect
Browse files Browse the repository at this point in the history
This removes the hard coded list of standard libraries, and builds it per aspect
being propagated.
This is both cleaner and a pre-requisite for the additional link modes to work.

Related to bazel-contrib#1264 and bazel-contrib#54 and bazel-contrib#539
  • Loading branch information
ianthehat committed Jan 31, 2018
1 parent 53f410c commit a9c73d4
Show file tree
Hide file tree
Showing 7 changed files with 45 additions and 125 deletions.
11 changes: 3 additions & 8 deletions BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,10 @@ load("@io_bazel_rules_go//go/private:tools/lines_sorted_test.bzl", "lines_sorted
load("@io_bazel_rules_go//go/private:rules/info.bzl", "go_info")
load("@io_bazel_rules_go//proto:go_proto_library.bzl", "go_google_protobuf")
load("@io_bazel_rules_go//go/private:context.bzl", "go_context_data")
load("@io_bazel_rules_go//go/private:rules/stdlib.bzl", "stdlib")

go_context_data(
name = "go_bootstrap_context_data",
strip = select({
"@io_bazel_rules_go//go/private:strip-always": "always",
"@io_bazel_rules_go//go/private:strip-sometimes": "sometimes",
"@io_bazel_rules_go//go/private:strip-never": "never",
}),
stdlib_all = [],
stdlib(
name = "stdlib",
visibility = ["//visibility:public"],
)

Expand Down
2 changes: 0 additions & 2 deletions go/private/BUILD.sdk.bazel
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
load("@io_bazel_rules_go//go/private:rules/stdlib.bzl", "stdlib")

package(default_visibility = [ "//visibility:public" ])

filegroup(
Expand Down
48 changes: 16 additions & 32 deletions go/private/context.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -45,14 +45,20 @@ INFERRED_PATH = "inferred"

EXPORT_PATH = "export"

def _declare_file(go, path="", ext="", name = ""):
filename = mode_string(go.mode) + "/"
filename += name if name else go._ctx.label.name
def _declare_child(go, path, ext, name):
childname = mode_string(go.mode) + "/"
childname += name if name else go._ctx.label.name
if path:
filename += "~/" + path
childname += "~/" + path
if ext:
filename += ext
return go.actions.declare_file(filename)
childname += ext
return childname

def _declare_file(go, path="", ext="", name = ""):
return go.actions.declare_file(_declare_child(go, path, ext, name))

def _declare_directory(go, path="", ext="", name = ""):
return go.actions.declare_directory(_declare_child(go, path, ext, name))

def _new_args(go):
args = go.actions.args()
Expand Down Expand Up @@ -195,20 +201,9 @@ def go_context(ctx, attr=None):
mode = get_mode(ctx, toolchain, context_data)
root, binary = _get_go_binary(context_data)

stdlib = None
for check in [s[GoStdLib] for s in context_data.stdlib_all]:
if (check.mode.goos == mode.goos and
check.mode.goarch == mode.goarch and
check.mode.race == mode.race and
check.mode.pure == mode.pure):
if stdlib:
fail("Multiple matching standard library for {}: {} and {}".format(
mode_string(mode),
check.root_file.dirname,
stdlib.root_file.dirname))
stdlib = check
if not stdlib and context_data.stdlib_all:
fail("No matching standard library for "+mode_string(mode))
stdlib = getattr(attr, "_stdlib", None)
if stdlib:
stdlib = get_source(stdlib).stdlib

importpath, pathtype = _infer_importpath(ctx)
return GoContext(
Expand Down Expand Up @@ -241,21 +236,12 @@ def go_context(ctx, attr=None):
new_library = _new_library,
library_to_source = _library_to_source,
declare_file = _declare_file,
declare_directory = _declare_directory,

# Private
_ctx = ctx, # TODO: All uses of this should be removed
)

def _stdlib_all():
stdlibs = []
for goos, goarch in GOOS_GOARCH:
stdlibs.extend([
Label("@go_stdlib_{}_{}_cgo".format(goos, goarch)),
Label("@go_stdlib_{}_{}_pure".format(goos, goarch)),
Label("@go_stdlib_{}_{}_cgo_race".format(goos, goarch)),
])
return stdlibs

def _go_context_data(ctx):
cpp = ctx.fragments.cpp
features = ctx.features
Expand All @@ -275,7 +261,6 @@ def _go_context_data(ctx):
compiler_path, _ = cpp.ld_executable.rsplit("/", 1)
return struct(
strip = ctx.attr.strip,
stdlib_all = ctx.attr.stdlib_all,
crosstool = ctx.files._crosstool,
package_list = ctx.file._package_list,
sdk_files = ctx.files._sdk_files,
Expand All @@ -295,7 +280,6 @@ go_context_data = rule(
_go_context_data,
attrs = {
"strip": attr.string(mandatory = True),
"stdlib_all": attr.label_list(default = _stdlib_all()),
# Hidden internal attributes
"_crosstool": attr.label(default = Label("//tools/defaults:crosstool")),
"_package_list": attr.label(
Expand Down
24 changes: 0 additions & 24 deletions go/private/repositories.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@
load("@io_bazel_rules_go//go/private:common.bzl", "MINIMUM_BAZEL_VERSION")
load("@io_bazel_rules_go//go/private:repository_tools.bzl", "go_repository_tools")
load("@io_bazel_rules_go//go/private:go_repository.bzl", "go_repository")
load("@io_bazel_rules_go//go/private:rules/stdlib.bzl", "go_stdlib")
load("@io_bazel_rules_go//go/private:skylib/lib/versions.bzl", "versions")
load("@io_bazel_rules_go//go/toolchain:toolchains.bzl", "go_register_toolchains")
load("@io_bazel_rules_go//go/platform:list.bzl", "GOOS_GOARCH")
Expand Down Expand Up @@ -55,29 +54,6 @@ def go_rules_dependencies():
type = "zip",
)

for goos, goarch in GOOS_GOARCH:
_maybe(go_stdlib,
name = "go_stdlib_{}_{}_cgo".format(goos, goarch),
goos = goos,
goarch = goarch,
race = False,
pure = False,
)
_maybe(go_stdlib,
name = "go_stdlib_{}_{}_pure".format(goos, goarch),
goos = goos,
goarch = goarch,
race = False,
pure = True,
)
_maybe(go_stdlib,
name = "go_stdlib_{}_{}_cgo_race".format(goos, goarch),
goos = goos,
goarch = goarch,
race = True,
pure = False,
)

_maybe(go_repository_tools,
name = "io_bazel_rules_go_repository_tools",
)
Expand Down
1 change: 1 addition & 0 deletions go/private/rules/aspect.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,7 @@ go_archive_aspect = aspect(
"embed",
"compiler",
"compilers",
"_stdlib",
],
attrs = {
"pure": attr.string(values = [
Expand Down
7 changes: 5 additions & 2 deletions go/private/rules/rule.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,14 @@ load(
)

def go_rule(implementation, attrs={}, toolchains=[], bootstrap=False, **kwargs):
attrs["_go_context_data"] = attr.label(default = Label("@io_bazel_rules_go//:go_context_data"))
aspects = []
if all([k in attrs for k in ["pure", "static", "msan", "race"]]):
aspects.append(go_archive_aspect)
if not bootstrap:
attrs["_go_context_data"] = attr.label(default = Label("@io_bazel_rules_go//:go_context_data"))
attrs["_stdlib"] = attr.label(default = Label("@io_bazel_rules_go//:stdlib"), aspects = aspects)
toolchains = toolchains + ["@io_bazel_rules_go//go:toolchain"]
else:
attrs["_go_context_data"] = attr.label(default = Label("@io_bazel_rules_go//:go_bootstrap_context_data"))
toolchains = toolchains + ["@io_bazel_rules_go//go:bootstrap_toolchain"]

return rule(
Expand Down
77 changes: 20 additions & 57 deletions go/private/rules/stdlib.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -16,90 +16,53 @@ load(
"@io_bazel_rules_go//go/private:providers.bzl",
"GoStdLib",
)
load("@io_bazel_rules_go//go/private:context.bzl",
load(
"@io_bazel_rules_go//go/private:context.bzl",
"go_context",
)
load(
"@io_bazel_rules_go//go/private:rules/rule.bzl",
"go_rule",
)

_STDLIB_BUILD = """
load("@io_bazel_rules_go//go/private:rules/stdlib.bzl", "stdlib")
stdlib(
name = "{name}",
goos = "{goos}",
goarch = "{goarch}",
race = {race},
pure = {pure},
visibility = ["//visibility:public"],
)
"""

def _stdlib_impl(ctx):
go = go_context(ctx)
pkg = ctx.actions.declare_directory("pkg")
root_file = ctx.actions.declare_file("ROOT")
def _stdlib_library_to_source(go, attr, source, merge):
pkg = go.declare_directory(go, "pkg")
root_file = go.declare_file(go, "ROOT")
files = [root_file, go.go, pkg]
args = go.args(go)
args.add(["-out", root_file.dirname])
if ctx.attr.race:
if go.mode.race:
args.add("-race")
ctx.actions.write(root_file, "")
go.actions.write(root_file, "")
go.actions.run(
inputs = go.sdk_files + go.sdk_tools + [go.package_list, root_file],
outputs = [pkg],
mnemonic = "GoStdlib",
executable = ctx.executable._stdlib_builder,
executable = attr._stdlib_builder.files.to_list()[0],
arguments = [args],
)
source["stdlib"] = GoStdLib(
root_file = root_file,
mode = go.mode,
libs = [pkg],
headers = [pkg],
files = files,
)

return [
DefaultInfo(
files = depset(files),
),
GoStdLib(
root_file = root_file,
mode = go.mode,
libs = [pkg],
headers = [pkg],
files = files,
),
]
def _stdlib_impl(ctx):
go = go_context(ctx)
library = go.new_library(go, resolver = _stdlib_library_to_source)
source = go.library_to_source(go, ctx.attr, library, False)
return [source, library]

stdlib = go_rule(
_stdlib_impl,
bootstrap = True,
attrs = {
"goos": attr.string(mandatory = True),
"goarch": attr.string(mandatory = True),
"race": attr.bool(mandatory = True),
"pure": attr.bool(mandatory = True),
"_stdlib_builder": attr.label(
executable = True,
cfg = "host",
default = Label("@io_bazel_rules_go//go/tools/builders:stdlib"),
),
},
)

def _go_stdlib_impl(ctx):
ctx.file("BUILD.bazel", _STDLIB_BUILD.format(
name = ctx.name,
goos = ctx.attr.goos,
goarch = ctx.attr.goarch,
race = ctx.attr.race,
pure = ctx.attr.pure,
))

go_stdlib = repository_rule(
implementation = _go_stdlib_impl,
attrs = {
"goos": attr.string(mandatory = True),
"goarch": attr.string(mandatory = True),
"race": attr.bool(mandatory = True),
"pure": attr.bool(mandatory = True),
},
)
"""See /go/toolchains.rst#go-sdk for full documentation."""

0 comments on commit a9c73d4

Please sign in to comment.