diff --git a/src/main/java/com/google/devtools/build/lib/bazel/rules/cpp/BazelCcModule.java b/src/main/java/com/google/devtools/build/lib/bazel/rules/cpp/BazelCcModule.java index c666a7cae1a8e5..e944d1a71490e9 100644 --- a/src/main/java/com/google/devtools/build/lib/bazel/rules/cpp/BazelCcModule.java +++ b/src/main/java/com/google/devtools/build/lib/bazel/rules/cpp/BazelCcModule.java @@ -184,6 +184,9 @@ public CcLinkingOutputs link( Object onlyForDynamicLibs, Object mainOutput, Object linkerOutputs, + Object useTestOnlyFlags, + Object pdbFile, + Object winDefFile, StarlarkThread thread) throws InterruptedException, EvalException { return super.link( @@ -211,13 +214,21 @@ public CcLinkingOutputs link( onlyForDynamicLibs, mainOutput, linkerOutputs, + useTestOnlyFlags, + pdbFile, + winDefFile, thread); } @Override public CcCompilationOutputs createCompilationOutputsFromStarlark( - Object objectsObject, Object picObjectsObject) throws EvalException { - return super.createCompilationOutputsFromStarlark(objectsObject, picObjectsObject); + Object objectsObject, + Object picObjectsObject, + Object ltoCopmilationContextObject, + StarlarkThread thread) + throws EvalException { + return super.createCompilationOutputsFromStarlark( + objectsObject, picObjectsObject, ltoCopmilationContextObject, thread); } @Override diff --git a/src/main/java/com/google/devtools/build/lib/rules/cpp/CcModule.java b/src/main/java/com/google/devtools/build/lib/rules/cpp/CcModule.java index e9ca40fb725adc..65fdd41c870bdb 100644 --- a/src/main/java/com/google/devtools/build/lib/rules/cpp/CcModule.java +++ b/src/main/java/com/google/devtools/build/lib/rules/cpp/CcModule.java @@ -217,6 +217,17 @@ public String getToolForAction( return featureConfiguration.getFeatureConfiguration().getToolPathForAction(actionName); } + @Override + public Sequence getToolRequirementForAction( + FeatureConfigurationForStarlark featureConfiguration, + String actionName, + StarlarkThread thread) + throws EvalException { + CcModule.checkPrivateStarlarkificationAllowlist(thread); + return StarlarkList.immutableCopyOf( + featureConfiguration.getFeatureConfiguration().getToolRequirementsForAction(actionName)); + } + @Override public Sequence getExecutionRequirements( FeatureConfigurationForStarlark featureConfiguration, String actionName) { @@ -275,43 +286,61 @@ public CcToolchainVariables getCompileBuildVariables( Object thinLtoOutputObjectFile, boolean usePic, boolean addLegacyCxxOptions, - Object variablesExtension) + Object variablesExtension, + Object stripOpts, + Object inputFile, + StarlarkThread thread) throws EvalException { + if (checkObjectsBound(stripOpts, inputFile)) { + CcModule.checkPrivateStarlarkificationAllowlist(thread); + } ImmutableList variablesExtensions = asDict(variablesExtension).isEmpty() ? ImmutableList.of() : ImmutableList.of(new UserVariablesExtension(asDict(variablesExtension))); - return CompileBuildVariables.setupVariablesOrThrowEvalException( - featureConfiguration.getFeatureConfiguration(), - ccToolchainProvider, - featureConfiguration - .getBuildOptionsFromFeatureConfigurationCreatedForStarlark_andIKnowWhatImDoing(), - featureConfiguration - .getCppConfigurationFromFeatureConfigurationCreatedForStarlark_andIKnowWhatImDoing(), - convertFromNoneable(sourceFile, /* defaultValue= */ null), - convertFromNoneable(outputFile, /* defaultValue= */ null), - /* gcnoFile= */ null, - /* isUsingFission= */ false, - /* dwoFile= */ null, - /* ltoIndexingFile= */ null, - convertFromNoneable(thinLtoIndex, /* defaultValue= */ null), - convertFromNoneable(thinLtoInputBitcodeFile, /* defaultValue=*/ null), - convertFromNoneable(thinLtoOutputObjectFile, /* defaultValue=*/ null), - /* includes= */ ImmutableList.of(), - userFlagsToIterable(userCompileFlags), - /* cppModuleMap= */ null, - usePic, - /* fdoStamp= */ null, - /* dotdFileExecPath= */ null, - variablesExtensions, - /* additionalBuildVariables= */ ImmutableMap.of(), - /* directModuleMaps= */ ImmutableList.of(), - Depset.noneableCast(includeDirs, String.class, "framework_include_directories"), - Depset.noneableCast(quoteIncludeDirs, String.class, "quote_include_directories"), - Depset.noneableCast(systemIncludeDirs, String.class, "system_include_directories"), - Depset.noneableCast(frameworkIncludeDirs, String.class, "framework_include_directories"), - Depset.noneableCast(defines, String.class, "preprocessor_defines").toList(), - ImmutableList.of()); + CcToolchainVariables.Builder variables = + CcToolchainVariables.builder( + CompileBuildVariables.setupVariablesOrThrowEvalException( + featureConfiguration.getFeatureConfiguration(), + ccToolchainProvider, + featureConfiguration + .getBuildOptionsFromFeatureConfigurationCreatedForStarlark_andIKnowWhatImDoing(), + featureConfiguration + .getCppConfigurationFromFeatureConfigurationCreatedForStarlark_andIKnowWhatImDoing(), + convertFromNoneable(sourceFile, /* defaultValue= */ null), + convertFromNoneable(outputFile, /* defaultValue= */ null), + /* gcnoFile= */ null, + /* isUsingFission= */ false, + /* dwoFile= */ null, + /* ltoIndexingFile= */ null, + convertFromNoneable(thinLtoIndex, /* defaultValue= */ null), + convertFromNoneable(thinLtoInputBitcodeFile, /* defaultValue=*/ null), + convertFromNoneable(thinLtoOutputObjectFile, /* defaultValue=*/ null), + /* includes= */ ImmutableList.of(), + userFlagsToIterable(userCompileFlags), + /* cppModuleMap= */ null, + usePic, + /* fdoStamp= */ null, + /* dotdFileExecPath= */ null, + variablesExtensions, + /* additionalBuildVariables= */ ImmutableMap.of(), + /* directModuleMaps= */ ImmutableList.of(), + Depset.noneableCast(includeDirs, String.class, "framework_include_directories"), + Depset.noneableCast( + quoteIncludeDirs, String.class, "quote_include_directories"), + Depset.noneableCast( + systemIncludeDirs, String.class, "system_include_directories"), + Depset.noneableCast( + frameworkIncludeDirs, String.class, "framework_include_directories"), + Depset.noneableCast(defines, String.class, "preprocessor_defines").toList(), + ImmutableList.of())) + .addStringSequenceVariable("stripopts", asClassImmutableList(stripOpts)); + + String inputFileString = convertFromNoneable(inputFile, null); + if (inputFileString != null) { + variables.addStringVariable("input_file", inputFileString); + } + return variables.build(); } @Override @@ -1804,16 +1833,26 @@ public Tuple createLinkingContextFromCompilationOutputs( Sequence linkingContexts, // expected String name, String languageString, - boolean alwayslink, // expected - Sequence additionalInputs, + boolean alwayslink, + Sequence additionalInputs, // expected boolean disallowStaticLibraries, boolean disallowDynamicLibraries, Object grepIncludes, Object variablesExtension, + Object stamp, StarlarkThread thread) throws InterruptedException, EvalException { + if (checkObjectsBound(stamp)) { + CcModule.checkPrivateStarlarkificationAllowlist(thread); + } Language language = parseLanguage(languageString); StarlarkActionFactory actions = starlarkActionFactoryApi; + int stampInt = 0; + if (stamp != Starlark.UNBOUND) { + stampInt = (int) stamp; + } + boolean isStampingEnabled = + isStampingEnabled(stampInt, actions.getRuleContext().getConfiguration()); CcToolchainProvider ccToolchainProvider = convertFromNoneable(starlarkCcToolchainProvider, null); FeatureConfigurationForStarlark featureConfiguration = @@ -1863,6 +1902,7 @@ public Tuple createLinkingContextFromCompilationOutputs( .setStaticLinkType(staticLinkTargetType) .setDynamicLinkType(LinkTargetType.NODEPS_DYNAMIC_LIBRARY) .emitInterfaceSharedLibraries(true) + .setIsStampingEnabled(isStampingEnabled) .addLinkopts(Sequence.cast(userLinkFlags, String.class, "user_link_flags")); if (!asDict(variablesExtension).isEmpty()) { helper.addVariableExtension(new UserVariablesExtension(asDict(variablesExtension))); @@ -2268,6 +2308,9 @@ protected CcLinkingOutputs link( Object onlyForDynamicLibsObject, Object mainOutputObject, Object linkerOutputsObject, + Object useTestOnlyFlags, + Object pdbFile, + Object winDefFile, StarlarkThread thread) throws InterruptedException, EvalException { // TODO(bazel-team): Rename always_link to alwayslink before delisting. Also it looks like the @@ -2284,7 +2327,10 @@ protected CcLinkingOutputs link( wholeArchiveObject, additionalLinkstampDefines, mainOutputObject, - onlyForDynamicLibsObject)) { + onlyForDynamicLibsObject, + useTestOnlyFlags, + pdbFile, + winDefFile)) { checkPrivateStarlarkificationAllowlist(thread); } Language language = parseLanguage(languageString); @@ -2379,6 +2425,9 @@ protected CcLinkingOutputs link( && CppHelper.useInterfaceSharedLibraries( cppConfiguration, ccToolchainProvider, actualFeatureConfiguration)) .setLinkerOutputArtifact(convertFromNoneable(mainOutput, null)) + .setUseTestOnlyFlags(convertFromNoneable(useTestOnlyFlags, false)) + .setPdbFile(convertFromNoneable(pdbFile, null)) + .setDefFile(convertFromNoneable(winDefFile, null)) .addLinkerOutputs(linkerOutputs); if (staticLinkTargetType != null) { helper.setShouldCreateDynamicLibrary(false).setStaticLinkType(staticLinkTargetType); @@ -2397,7 +2446,14 @@ protected CcLinkingOutputs link( } protected CcCompilationOutputs createCompilationOutputsFromStarlark( - Object objectsObject, Object picObjectsObject) throws EvalException { + Object objectsObject, + Object picObjectsObject, + Object ltoCompilationContextObject, + StarlarkThread thread) + throws EvalException { + if (checkObjectsBound(ltoCompilationContextObject)) { + CcModule.checkPrivateStarlarkificationAllowlist(thread); + } CcCompilationOutputs.Builder ccCompilationOutputsBuilder = CcCompilationOutputs.builder(); NestedSet objects = convertToNestedSet(objectsObject, Artifact.class, "objects"); validateExtensions( @@ -2406,6 +2462,8 @@ protected CcCompilationOutputs createCompilationOutputsFromStarlark( Link.OBJECT_FILETYPES, Link.OBJECT_FILETYPES, /* allowAnyTreeArtifacts= */ false); + LtoCompilationContext ltoCompilationContext = + convertFromNoneable(ltoCompilationContextObject, null); NestedSet picObjects = convertToNestedSet(picObjectsObject, Artifact.class, "pic_objects"); validateExtensions( @@ -2416,6 +2474,9 @@ protected CcCompilationOutputs createCompilationOutputsFromStarlark( /* allowAnyTreeArtifacts= */ false); ccCompilationOutputsBuilder.addObjectFiles(objects.toList()); ccCompilationOutputsBuilder.addPicObjectFiles(picObjects.toList()); + if (ltoCompilationContext != null) { + ccCompilationOutputsBuilder.addLtoCompilationContext(ltoCompilationContext); + } return ccCompilationOutputsBuilder.build(); } diff --git a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/BazelCcModuleApi.java b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/BazelCcModuleApi.java index fb34ddc2e920e5..661f3117d3833b 100644 --- a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/BazelCcModuleApi.java +++ b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/BazelCcModuleApi.java @@ -566,7 +566,26 @@ Tuple compile( positional = false, named = true, allowedTypes = {@ParamType(type = Sequence.class)}, - defaultValue = "unbound") + defaultValue = "unbound"), + @Param( + name = "use_test_only_flags", + documented = false, + positional = false, + named = true, + allowedTypes = {@ParamType(type = Boolean.class)}, + defaultValue = "unbound"), + @Param( + name = "pdb_file", + documented = false, + positional = false, + named = true, + defaultValue = "unbound"), + @Param( + name = "win_def_file", + documented = false, + positional = false, + named = true, + defaultValue = "unbound"), }) LinkingOutputsT link( StarlarkActionFactoryT starlarkActionFactoryApi, @@ -593,12 +612,16 @@ LinkingOutputsT link( Object onlyForDynamicLibs, Object mainOutput, Object linkerOutputs, + Object useTestOnlyFlags, + Object pdbFile, + Object winDefFile, StarlarkThread thread) throws InterruptedException, EvalException; @StarlarkMethod( name = "create_compilation_outputs", doc = "Create compilation outputs object.", + useStarlarkThread = true, parameters = { @Param( name = "objects", @@ -620,9 +643,19 @@ LinkingOutputsT link( @ParamType(type = Depset.class), @ParamType(type = NoneType.class), }), + @Param( + name = "lto_compilation_context", + documented = false, + positional = false, + named = true, + defaultValue = "unbound"), }) CompilationOutputsT createCompilationOutputsFromStarlark( - Object objectsObject, Object picObjectsObject) throws EvalException; + Object objectsObject, + Object picObjectsObject, + Object ltoCopmilationContextObject, + StarlarkThread thread) + throws EvalException; @StarlarkMethod( name = "merge_compilation_outputs", diff --git a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/CcModuleApi.java b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/CcModuleApi.java index 172a303a7618e3..d1eebd4c09a205 100644 --- a/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/CcModuleApi.java +++ b/src/main/java/com/google/devtools/build/lib/starlarkbuildapi/cpp/CcModuleApi.java @@ -259,6 +259,7 @@ Dict getEnvironmentVariable( @StarlarkMethod( name = "create_compile_variables", doc = "Returns variables used for compilation actions.", + useStarlarkThread = true, parameters = { @Param( name = "cc_toolchain", @@ -400,6 +401,26 @@ Dict getEnvironmentVariable( positional = false, allowedTypes = {@ParamType(type = Dict.class)}, defaultValue = "unbound"), + @Param( + name = "strip_opts", + documented = false, + positional = false, + named = true, + defaultValue = "unbound", + allowedTypes = { + @ParamType(type = Sequence.class, generic1 = String.class), + @ParamType(type = NoneType.class), + }), + @Param( + name = "input_file", + documented = false, + named = true, + positional = false, + defaultValue = "unbound", + allowedTypes = { + @ParamType(type = String.class), + @ParamType(type = NoneType.class), + }), }) CcToolchainVariablesT getCompileBuildVariables( CcToolchainProviderT ccToolchainProvider, @@ -417,7 +438,10 @@ CcToolchainVariablesT getCompileBuildVariables( Object thinLtoOutputObjectFile, boolean usePic, boolean addLegacyCxxOptions, - Object variablesExtension) + Object variablesExtension, + Object stripOpts, + Object inputFile, + StarlarkThread thread) throws EvalException; @StarlarkMethod( @@ -1206,6 +1230,12 @@ CcToolchainConfigInfoT ccToolchainConfigInfoFromStarlark( documented = false, allowedTypes = {@ParamType(type = Dict.class)}, defaultValue = "unbound"), + @Param( + name = "stamp", + positional = false, + named = true, + documented = false, + defaultValue = "unbound"), }) Tuple createLinkingContextFromCompilationOutputs( StarlarkActionFactoryT starlarkActionFactoryApi, @@ -1222,6 +1252,7 @@ Tuple createLinkingContextFromCompilationOutputs( boolean disallowDynamicLibraries, Object grepIncludes, Object variablesExtension, + Object stamp, StarlarkThread thread) throws InterruptedException, EvalException; @@ -1305,4 +1336,16 @@ LtoBackendArtifactsT createLtoBackendArtifacts( CompilationContextT mergeCompilationContexts( Sequence compilationContexts) // expected throws EvalException; + + @StarlarkMethod( + name = "get_tool_requirement_for_action", + documented = false, + useStarlarkThread = true, + parameters = { + @Param(name = "feature_configuration", positional = false, named = true), + @Param(name = "action_name", named = true, positional = false), + }) + Sequence getToolRequirementForAction( + FeatureConfigurationT featureConfiguration, String actionName, StarlarkThread thread) + throws EvalException; } diff --git a/src/test/java/com/google/devtools/build/lib/rules/cpp/StarlarkCcCommonTest.java b/src/test/java/com/google/devtools/build/lib/rules/cpp/StarlarkCcCommonTest.java index a1dd46db776abf..5d60af0a8e1922 100644 --- a/src/test/java/com/google/devtools/build/lib/rules/cpp/StarlarkCcCommonTest.java +++ b/src/test/java/com/google/devtools/build/lib/rules/cpp/StarlarkCcCommonTest.java @@ -7769,4 +7769,234 @@ public void testExtendedCcLinkingOutputsApiBlocked() throws Exception { assertThat(e).hasMessageThat().contains("cannot use private API"); } + + @Test + public void testToolRequirementForActionIsNotAccessibleFromOutsideBuiltins() throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.get_tool_requirement_for_action(feature_configuration = feature_configuration," + + " action_name = 'test')", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testCreateCompilationOutputsPrivateParameterIsNotAccessibleFromOutsideBuiltins() + throws Exception { + scratch.file( + "foo/BUILD", "load(':custom_rule.bzl', 'custom_rule')", "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_common.create_compilation_outputs(objects = None, pic_objects = None," + + " lto_compilation_context = None)", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testGetCompileBuildVariablesStripOptsNotAcessibleFromOutsideBuiltins() + throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.create_compile_variables(cc_toolchain = cc_toolchain, feature_configuration =" + + " feature_configuration, strip_opts = [])", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testGetCompileBuildVariablesInputFileNotAcessibleFromOutsideBuiltins() + throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.create_compile_variables(cc_toolchain = cc_toolchain, feature_configuration =" + + " feature_configuration, input_file = '')", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testCreateLinkingContextFromCompilationOutputsStampNotAcessibleFromOutsideBuiltins() + throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.create_linking_context_from_compilation_outputs(actions = ctx.actions," + + " cc_toolchain = cc_toolchain, feature_configuration =" + + " feature_configuration,compilation_outputs = cc_common.create_compilation_outputs()," + + " name = 'test', stamp = 0)", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testLinkUseTestOnlyFlagNotAcessibleFromOutsideBuiltins() throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.link(actions = ctx.actions, cc_toolchain = cc_toolchain, feature_configuration" + + " = feature_configuration,use_test_only_flags = True, name = 'test')", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testLinkUsePdbFileNotAcessibleFromOutsideBuiltins() throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.link(actions = ctx.actions, cc_toolchain = cc_toolchain, feature_configuration" + + " = feature_configuration,pdb_file = None, name = 'test')", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } + + @Test + public void testLinkUseWinDefFileNotAcessibleFromOutsideBuiltins() throws Exception { + scratch.file( + "foo/BUILD", + "load(':custom_rule.bzl', 'custom_rule')", + "cc_toolchain_alias(name='alias')", + "custom_rule(name = 'custom')"); + scratch.file( + "foo/custom_rule.bzl", + "def _impl(ctx):", + " cc_toolchain = ctx.attr._cc_toolchain[cc_common.CcToolchainInfo]", + " feature_configuration = cc_common.configure_features(ctx = ctx, cc_toolchain =" + + " cc_toolchain)", + " cc_common.link(actions = ctx.actions, cc_toolchain = cc_toolchain, feature_configuration" + + " = feature_configuration,win_def_file = None, name = 'test')", + " return []", + "custom_rule = rule(", + " implementation = _impl,", + " attrs = {'_cc_toolchain':" + " attr.label(default=Label('//foo:alias'))},", + " fragments = ['cpp'],", + ")"); + invalidatePackages(); + + AssertionError e = + assertThrows(AssertionError.class, () -> getConfiguredTarget("//foo:custom")); + + assertThat(e).hasMessageThat().contains("cannot use private API"); + } }