Add --compilation_mode support in transitions
Add support for converting //command_line_option:compilation_mode from
Java value to Starlark value so that it can be read in a transition.
Fixes --compilation_mode in #10690, but not the general case.
This patch does not contain any tests. What kind of test is expected and where should it be implemented?
Closes #11347.
PiperOrigin-RevId: 333249729
diff --git a/src/main/java/com/google/devtools/build/lib/analysis/BUILD b/src/main/java/com/google/devtools/build/lib/analysis/BUILD
index 53cc44d..d4461b2 100644
--- a/src/main/java/com/google/devtools/build/lib/analysis/BUILD
+++ b/src/main/java/com/google/devtools/build/lib/analysis/BUILD
@@ -1554,7 +1554,10 @@
java_library(
name = "config/compilation_mode",
srcs = ["config/CompilationMode.java"],
- deps = ["//src/main/java/com/google/devtools/common/options"],
+ deps = [
+ "//src/main/java/com/google/devtools/common/options",
+ "//src/main/java/net/starlark/java/eval",
+ ],
)
java_library(
diff --git a/src/main/java/com/google/devtools/build/lib/analysis/config/CompilationMode.java b/src/main/java/com/google/devtools/build/lib/analysis/config/CompilationMode.java
index 1b83708..3058d76 100644
--- a/src/main/java/com/google/devtools/build/lib/analysis/config/CompilationMode.java
+++ b/src/main/java/com/google/devtools/build/lib/analysis/config/CompilationMode.java
@@ -14,12 +14,14 @@
package com.google.devtools.build.lib.analysis.config;
import com.google.devtools.common.options.EnumConverter;
+import net.starlark.java.eval.Printer;
+import net.starlark.java.eval.StarlarkValue;
-/**
- * This class represents the debug/optimization mode the binaries will be
- * built for.
- */
-public enum CompilationMode {
+/** This class represents the debug/optimization mode the binaries will be built for. */
+// TODO(bazel-team): Implementing StarlarkValue is a workaround until a well-defined Java-Starlark
+// conversion interface has been created. Avoid replicating this workaround.
+// See also https://github.com/bazelbuild/bazel/pull/11347#issuecomment-630260102
+public enum CompilationMode implements StarlarkValue {
// Fast build mode (-g0).
FASTBUILD("fastbuild"),
@@ -47,4 +49,9 @@
super(CompilationMode.class, "compilation mode");
}
}
+
+ @Override
+ public void repr(Printer printer) {
+ printer.append(toString());
+ }
}
diff --git a/src/test/java/com/google/devtools/build/lib/analysis/StarlarkAttrTransitionProviderTest.java b/src/test/java/com/google/devtools/build/lib/analysis/StarlarkAttrTransitionProviderTest.java
index d59e41b..fce6873 100644
--- a/src/test/java/com/google/devtools/build/lib/analysis/StarlarkAttrTransitionProviderTest.java
+++ b/src/test/java/com/google/devtools/build/lib/analysis/StarlarkAttrTransitionProviderTest.java
@@ -507,7 +507,7 @@
@Test
public void testOptionConversionCpu() throws Exception {
writeOptionConversionTestFiles();
- BazelMockAndroidSupport.setupNdk(mockToolsConfig);
+ BazelMockAndroidSupport.setupNdk(mockToolsConfig); // cc_binary needs this
ConfiguredTarget target = getConfiguredTarget("//test/starlark:test");
@@ -518,6 +518,90 @@
assertThat(getConfiguration(Iterables.getOnlyElement(dep)).getCpu()).isEqualTo("armeabi-v7a");
}
+ private void writeReadAndPassthroughOptionsTestFiles() throws Exception {
+ setBuildLanguageOptions("--experimental_starlark_config_transitions=true");
+ writeAllowlistFile();
+
+ scratch.file(
+ "test/skylark/my_rule.bzl",
+ "load('//myinfo:myinfo.bzl', 'MyInfo')",
+ "settings_under_test = {",
+ " '//command_line_option:cpu': 'armeabi-v7a',",
+ " '//command_line_option:compilation_mode': 'dbg',",
+ " '//command_line_option:crosstool_top': '//android/crosstool:everything',",
+ " '//command_line_option:platform_suffix': 'my-platform-suffix',",
+ "}",
+ "def set_options_transition_func(settings, attr):",
+ " return settings_under_test",
+ "def passthrough_transition_func(settings, attr):",
+ // All values in this test should be possible to copy within Starlark.
+ " ret = dict(settings)",
+ // All values in this test should be possible to read within Starlark.
+ // This does not mean that it is possible to set a string value for all settings,
+ // e.g. //command_line_option:test_arg should be set to a list of strings.
+ " for key, expected_value in settings_under_test.items():",
+ " if str(ret[key]) != expected_value:",
+ " fail('%s did not pass through, got %r expected %r' %",
+ " (key, str(ret[key]), expected_value))",
+ " ret['//command_line_option:test_arg'] = ['ok']",
+ " return ret",
+ "my_set_options_transition = transition(",
+ " implementation = set_options_transition_func,",
+ " inputs = [],",
+ " outputs = settings_under_test.keys())",
+ "my_passthrough_transition = transition(",
+ " implementation = passthrough_transition_func,",
+ " inputs = settings_under_test.keys(),",
+ " outputs = ['//command_line_option:test_arg'] + settings_under_test.keys())",
+ "def impl(ctx): ",
+ " return MyInfo(attr_dep = ctx.attr.dep)",
+ "my_set_options_rule = rule(",
+ " implementation = impl,",
+ " attrs = {",
+ " 'dep': attr.label(cfg = my_set_options_transition),",
+ " '_allowlist_function_transition': attr.label(",
+ " default = '//tools/allowlists/function_transition_allowlist',",
+ " ),",
+ " })",
+ "my_passthrough_rule = rule(",
+ " implementation = impl,",
+ " attrs = {",
+ " 'dep': attr.label(cfg = my_passthrough_transition),",
+ " '_allowlist_function_transition': attr.label(",
+ " default = '//tools/allowlists/function_transition_allowlist',",
+ " ),",
+ " })");
+
+ scratch.file(
+ "test/skylark/BUILD",
+ "load('//test/skylark:my_rule.bzl', 'my_passthrough_rule', 'my_set_options_rule')",
+ "my_set_options_rule(name = 'top', dep = ':test')",
+ "my_passthrough_rule(name = 'test', dep = ':main')",
+ "cc_binary(name = 'main', srcs = ['main.c'])");
+ }
+
+ @Test
+ public void testCompilationModeReadableInStarlarkTransitions() throws Exception {
+ writeReadAndPassthroughOptionsTestFiles();
+ BazelMockAndroidSupport.setupNdk(mockToolsConfig); // cc_binary needs this
+
+ ConfiguredTarget topTarget = getConfiguredTarget("//test/skylark:top");
+
+ @SuppressWarnings("unchecked")
+ List<ConfiguredTarget> topDep =
+ (List<ConfiguredTarget>) getMyInfoFromTarget(topTarget).getValue("attr_dep");
+ assertThat(topDep).hasSize(1);
+ ConfiguredTarget testTarget = Iterables.getOnlyElement(topDep);
+ @SuppressWarnings("unchecked")
+ List<ConfiguredTarget> testDep =
+ (List<ConfiguredTarget>) getMyInfoFromTarget(testTarget).getValue("attr_dep");
+ assertThat(testDep).hasSize(1);
+ ConfiguredTarget mainTarget = Iterables.getOnlyElement(testDep);
+ List<String> testArguments =
+ getConfiguration(mainTarget).getOptions().get(TestOptions.class).testArguments;
+ assertThat(testArguments).containsExactly("ok");
+ }
+
@Test
public void testUndeclaredOptionKey() throws Exception {
setBuildLanguageOptions("--experimental_starlark_config_transitions=true");