Create a cc_directory_tool rule.
BEGIN_PUBLIC
Create a cc_directory_tool rule.
This should allow for easy definition of tools from the sysroot. For example:
cc_directory_tool(
name = "clang",
directory = "@sysroot//:sysroot",
executable = "usr/bin/clang",
)
END_PUBLIC
PiperOrigin-RevId: 639947945
Change-Id: I4c211eb9c0b5fdc6457d9d32ef9250b5384a4ef3
diff --git a/cc/toolchains/directory_tool.bzl b/cc/toolchains/directory_tool.bzl
new file mode 100644
index 0000000..b4572e7
--- /dev/null
+++ b/cc/toolchains/directory_tool.bzl
@@ -0,0 +1,49 @@
+# Copyright 2024 The Bazel Authors. All rights reserved.
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+"""Macro to extract tools from a directory."""
+
+load("@bazel_skylib//rules/directory:glob.bzl", "directory_glob")
+load(":tool.bzl", "cc_tool")
+
+def cc_directory_tool(name, directory, executable, data = [], exclude = [], allow_empty = False, **kwargs):
+ """A tool extracted from a directory.
+
+ Args:
+ name: (str) The name of the generated target
+ directory: (Label) The directory to extract from
+ executable: (str) The relative path from the directory to the
+ executable.
+ data: (List[str]) A list of globs to runfiles for the executable,
+ relative to the directory.
+ exclude: (List[str]) A list of globs to exclude from data.
+ allow_empty: (bool) If false, any glob that fails to match anything will
+ result in a failure.
+ **kwargs: Kwargs to be passed through to cc_tool.
+ """
+ files_name = "_%s_files" % name
+ directory_glob(
+ name = files_name,
+ directory = directory,
+ srcs = [executable],
+ data = data,
+ exclude = exclude,
+ allow_empty = allow_empty,
+ visibility = ["//visibility:private"],
+ )
+
+ cc_tool(
+ name = name,
+ src = files_name,
+ **kwargs
+ )
diff --git a/tests/rule_based_toolchain/testdata/BUILD b/tests/rule_based_toolchain/testdata/BUILD
index fa2cdd8..950751c 100644
--- a/tests/rule_based_toolchain/testdata/BUILD
+++ b/tests/rule_based_toolchain/testdata/BUILD
@@ -39,3 +39,10 @@
name = "bin_filegroup",
srcs = ["bin"],
)
+
+# Analysis_test is unable to depend on source files directly, but it can depend
+# on a filegroup containing a single file.
+filegroup(
+ name = "bin_wrapper_filegroup",
+ srcs = ["bin_wrapper.sh"],
+)
diff --git a/tests/rule_based_toolchain/tool/BUILD b/tests/rule_based_toolchain/tool/BUILD
index d16ded6..8c48bd8 100644
--- a/tests/rule_based_toolchain/tool/BUILD
+++ b/tests/rule_based_toolchain/tool/BUILD
@@ -1,4 +1,5 @@
load("@rules_testing//lib:util.bzl", "util")
+load("//cc/toolchains:directory_tool.bzl", "cc_directory_tool")
load("//cc/toolchains:tool.bzl", "cc_tool")
load("//tests/rule_based_toolchain:analysis_test_suite.bzl", "analysis_test_suite")
load(":tool_test.bzl", "TARGETS", "TESTS")
@@ -19,6 +20,15 @@
visibility = ["//tests/rule_based_toolchain:__subpackages__"],
)
+cc_directory_tool(
+ name = "directory_tool",
+ data = ["bin"],
+ directory = "//tests/rule_based_toolchain/testdata:directory",
+ executable = "bin_wrapper.sh",
+ execution_requirements = ["requires-network"],
+ requires_any_of = ["//tests/rule_based_toolchain/features:direct_constraint"],
+)
+
analysis_test_suite(
name = "test_suite",
targets = TARGETS,
diff --git a/tests/rule_based_toolchain/tool/tool_test.bzl b/tests/rule_based_toolchain/tool/tool_test.bzl
index 8e9b68a..0f31a37 100644
--- a/tests/rule_based_toolchain/tool/tool_test.bzl
+++ b/tests/rule_based_toolchain/tool/tool_test.bzl
@@ -37,8 +37,8 @@
_BIN_WRAPPER = "tests/rule_based_toolchain/testdata/bin_wrapper.sh"
_BIN = "tests/rule_based_toolchain/testdata/bin"
-def _tool_test(env, targets):
- tool = env.expect.that_target(targets.tool).provider(ToolInfo)
+def _tool_test(env, targets, target):
+ tool = env.expect.that_target(target).provider(ToolInfo)
tool.exe().short_path_equals(_BIN_WRAPPER)
tool.execution_requirements().contains_exactly(["requires-network"])
tool.runfiles().contains_exactly([
@@ -106,14 +106,17 @@
"//tests/rule_based_toolchain/features:direct_constraint",
"//tests/rule_based_toolchain/tool:tool",
"//tests/rule_based_toolchain/tool:wrapped_tool",
+ "//tests/rule_based_toolchain/tool:directory_tool",
"//tests/rule_based_toolchain/testdata:bin_wrapper",
"//tests/rule_based_toolchain/testdata:multiple",
"//tests/rule_based_toolchain/testdata:bin_filegroup",
+ "//tests/rule_based_toolchain/testdata:bin_wrapper_filegroup",
]
# @unsorted-dict-items
TESTS = {
- "tool_test": _tool_test,
+ "tool_test": lambda env, targets: _tool_test(env, targets, targets.tool),
+ "directory_tool_test": lambda env, targets: _tool_test(env, targets, targets.directory_tool),
"wrapped_tool_includes_runfiles_test": _wrapped_tool_includes_runfiles_test,
"collect_tools_collects_tools_test": _collect_tools_collects_tools_test,
"collect_tools_collects_binaries_test": _collect_tools_collects_binaries_test,