Move ObjC compilation actions for J2ObjC-translated code from binary level to the edges (J2ObjcAspect and J2ObjcProtoAspect).
RELNOTES[INC]:
ObjC compile actions for J2ObjC-translated code now only has access to headers from the java deps of the associated original java rule.
These compile actions no longer takes the compiler options specified in "copts" attribute on objc_binary/ios_test rules.
J2ObjC dead code removal (enabled through flag "--j2objc_dead_code_removal") now happens *after* ObjC compilation.
--
MOS_MIGRATED_REVID=113910545
diff --git a/src/main/java/com/google/devtools/build/lib/bazel/rules/BazelRuleClassProvider.java b/src/main/java/com/google/devtools/build/lib/bazel/rules/BazelRuleClassProvider.java
index 650c556..ca1071d 100644
--- a/src/main/java/com/google/devtools/build/lib/bazel/rules/BazelRuleClassProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/bazel/rules/BazelRuleClassProvider.java
@@ -87,8 +87,6 @@
import com.google.devtools.build.lib.rules.cpp.CppConfigurationLoader;
import com.google.devtools.build.lib.rules.cpp.CppOptions;
import com.google.devtools.build.lib.rules.genquery.GenQueryRule;
-import com.google.devtools.build.lib.rules.java.J2ObjcCommandLineOptions;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.java.JavaConfigurationLoader;
import com.google.devtools.build.lib.rules.java.JavaCpuSupplier;
import com.google.devtools.build.lib.rules.java.JavaImportBaseRule;
@@ -103,6 +101,8 @@
import com.google.devtools.build.lib.rules.objc.IosFrameworkBinaryRule;
import com.google.devtools.build.lib.rules.objc.IosFrameworkRule;
import com.google.devtools.build.lib.rules.objc.IosTestRule;
+import com.google.devtools.build.lib.rules.objc.J2ObjcCommandLineOptions;
+import com.google.devtools.build.lib.rules.objc.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.objc.J2ObjcLibraryBaseRule;
import com.google.devtools.build.lib.rules.objc.ObjcBinaryRule;
import com.google.devtools.build.lib.rules.objc.ObjcBuildInfoFactory;
diff --git a/src/main/java/com/google/devtools/build/lib/bazel/rules/java/BazelJavaLibraryRule.java b/src/main/java/com/google/devtools/build/lib/bazel/rules/java/BazelJavaLibraryRule.java
index 454201f..317c9b8 100644
--- a/src/main/java/com/google/devtools/build/lib/bazel/rules/java/BazelJavaLibraryRule.java
+++ b/src/main/java/com/google/devtools/build/lib/bazel/rules/java/BazelJavaLibraryRule.java
@@ -26,7 +26,6 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder;
import com.google.devtools.build.lib.rules.cpp.CppConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.java.JavaCompilationArgsProvider;
import com.google.devtools.build.lib.rules.java.JavaConfiguration;
import com.google.devtools.build.lib.rules.java.JavaSourceInfoProvider;
@@ -41,8 +40,7 @@
public RuleClass build(Builder builder, final RuleDefinitionEnvironment env) {
return builder
- .requiresConfigurationFragments(
- JavaConfiguration.class, CppConfiguration.class, J2ObjcConfiguration.class)
+ .requiresConfigurationFragments(JavaConfiguration.class, CppConfiguration.class)
.requiresHostConfigurationFragments(Jvm.class) // For BaseJavaCompilationHelper
/* <!-- #BLAZE_RULE(java_library).IMPLICIT_OUTPUTS -->
<ul>
diff --git a/src/main/java/com/google/devtools/build/lib/bazel/rules/objc/BazelJ2ObjcLibraryRule.java b/src/main/java/com/google/devtools/build/lib/bazel/rules/objc/BazelJ2ObjcLibraryRule.java
index 4815526..4c71e4b 100644
--- a/src/main/java/com/google/devtools/build/lib/bazel/rules/objc/BazelJ2ObjcLibraryRule.java
+++ b/src/main/java/com/google/devtools/build/lib/bazel/rules/objc/BazelJ2ObjcLibraryRule.java
@@ -22,8 +22,8 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.objc.J2ObjcAspect;
+import com.google.devtools.build.lib.rules.objc.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.objc.J2ObjcLibrary;
import com.google.devtools.build.lib.rules.objc.J2ObjcLibraryBaseRule;
import com.google.devtools.build.lib.rules.objc.ObjcConfiguration;
diff --git a/src/main/java/com/google/devtools/build/lib/rules/apple/AppleToolchain.java b/src/main/java/com/google/devtools/build/lib/rules/apple/AppleToolchain.java
index bf55f10..1c4b6bf 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/apple/AppleToolchain.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/apple/AppleToolchain.java
@@ -170,6 +170,15 @@
* Base rule definition to be ancestor for rules which may require an xcode toolchain.
*/
public static class RequiresXcodeConfigRule implements RuleDefinition {
+ public static final LateBoundLabel<BuildConfiguration> XCODE_CONFIG_LABEL =
+ new LateBoundLabel<BuildConfiguration>(
+ AppleCommandLineOptions.DEFAULT_XCODE_VERSION_CONFIG_LABEL, AppleConfiguration.class) {
+ @Override
+ public Label getDefault(Rule rule, BuildConfiguration configuration) {
+ return configuration.getFragment(AppleConfiguration.class).getXcodeConfigLabel();
+ }
+ };
+
@Override
public RuleClass build(Builder builder, RuleDefinitionEnvironment env) {
return builder
@@ -178,14 +187,7 @@
.checkConstraints()
.direct_compile_time_input()
.cfg(HOST)
- .value(new LateBoundLabel<BuildConfiguration>(
- AppleCommandLineOptions.DEFAULT_XCODE_VERSION_CONFIG_LABEL,
- AppleConfiguration.class) {
- @Override
- public Label getDefault(Rule rule, BuildConfiguration configuration) {
- return configuration.getFragment(AppleConfiguration.class).getXcodeConfigLabel();
- }
- }))
+ .value(XCODE_CONFIG_LABEL))
.build();
}
@Override
diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/JavaImportBaseRule.java b/src/main/java/com/google/devtools/build/lib/rules/java/JavaImportBaseRule.java
index 200a39e..1c991c9 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/java/JavaImportBaseRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/java/JavaImportBaseRule.java
@@ -37,8 +37,7 @@
@Override
public RuleClass build(Builder builder, RuleDefinitionEnvironment environment) {
return builder
- .requiresConfigurationFragments(JavaConfiguration.class, CppConfiguration.class,
- J2ObjcConfiguration.class)
+ .requiresConfigurationFragments(JavaConfiguration.class, CppConfiguration.class)
.add(attr(":host_jdk", LABEL)
.cfg(HOST)
.value(JavaSemantics.HOST_JDK))
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/AbstractJ2ObjcProtoAspect.java b/src/main/java/com/google/devtools/build/lib/rules/objc/AbstractJ2ObjcProtoAspect.java
index 743c544..f9cb428 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/AbstractJ2ObjcProtoAspect.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/AbstractJ2ObjcProtoAspect.java
@@ -14,9 +14,13 @@
package com.google.devtools.build.lib.rules.objc;
+import static com.google.devtools.build.lib.packages.Attribute.ConfigurationTransition.HOST;
+import static com.google.devtools.build.lib.packages.Attribute.attr;
+import static com.google.devtools.build.lib.packages.BuildType.LABEL;
import static com.google.devtools.build.lib.rules.objc.J2ObjcSource.SourceType;
import com.google.common.collect.ImmutableList;
+import com.google.devtools.build.lib.Constants;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.analysis.ConfiguredAspect;
import com.google.devtools.build.lib.analysis.ConfiguredNativeAspectFactory;
@@ -24,12 +28,14 @@
import com.google.devtools.build.lib.analysis.RuleConfiguredTarget.Mode;
import com.google.devtools.build.lib.analysis.RuleContext;
import com.google.devtools.build.lib.cmdline.Label;
-import com.google.devtools.build.lib.cmdline.LabelSyntaxException;
import com.google.devtools.build.lib.collect.nestedset.NestedSet;
import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
import com.google.devtools.build.lib.packages.AspectDefinition;
import com.google.devtools.build.lib.packages.AspectParameters;
+import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
+import com.google.devtools.build.lib.rules.apple.AppleToolchain;
import com.google.devtools.build.lib.rules.proto.ProtoCommon;
+import com.google.devtools.build.lib.rules.proto.ProtoConfiguration;
import com.google.devtools.build.lib.rules.proto.ProtoSourcesProvider;
import com.google.devtools.build.lib.vfs.PathFragment;
@@ -51,32 +57,45 @@
*/
public abstract class AbstractJ2ObjcProtoAspect implements ConfiguredNativeAspectFactory {
public static final String NAME = "J2ObjcProtoAspect";
+ private static final Iterable<Attribute> DEPENDENT_ATTRIBUTES = ImmutableList.of(
+ new Attribute("$protobuf_lib", Mode.TARGET),
+ new Attribute("deps", Mode.TARGET));
+ @Override
public AspectDefinition getDefinition(AspectParameters aspectParameters) {
AspectDefinition.Builder builder = new AspectDefinition.Builder("J2ObjcProtoAspect")
.requireProvider(ProtoSourcesProvider.class)
+ .requiresConfigurationFragments(
+ AppleConfiguration.class,
+ J2ObjcConfiguration.class,
+ ObjcConfiguration.class,
+ ProtoConfiguration.class)
.attributeAspect("deps", getClass())
.attributeAspect("exports", getClass())
- .attributeAspect("runtime_deps", getClass());
+ .attributeAspect("runtime_deps", getClass())
+ .add(attr("$protobuf_lib", LABEL)
+ .value(Label.parseAbsoluteUnchecked("//third_party/java/j2objc:proto_runtime")))
+ .add(attr("$xcrunwrapper", LABEL).cfg(HOST).exec()
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/objc:xcrunwrapper")))
+ .add(attr(":xcode_config", LABEL)
+ .allowedRuleClasses("xcode_config")
+ .checkConstraints()
+ .direct_compile_time_input()
+ .cfg(HOST)
+ .value(AppleToolchain.RequiresXcodeConfigRule.XCODE_CONFIG_LABEL));
return addAdditionalAttributes(builder).build();
}
protected abstract AspectDefinition.Builder addAdditionalAttributes(
AspectDefinition.Builder builder);
- protected static Label parseLabel(String from) {
- try {
- return Label.parseAbsolute(from);
- } catch (LabelSyntaxException e) {
- throw new IllegalArgumentException(from);
- }
- }
-
protected abstract boolean checkShouldCreateAspect(RuleContext ruleContext);
@Override
public ConfiguredAspect create(
- ConfiguredTarget base, RuleContext ruleContext, AspectParameters parameters) {
+ ConfiguredTarget base, RuleContext ruleContext, AspectParameters parameters)
+ throws InterruptedException {
if (!checkShouldCreateAspect(ruleContext)) {
return new ConfiguredAspect.Builder(NAME, ruleContext).build();
}
@@ -85,39 +104,64 @@
ImmutableList<Artifact> protoSources = protoSourcesProvider.getDirectProtoSources();
NestedSet<Artifact> transitiveImports = protoSourcesProvider.getTransitiveImports();
- J2ObjcSrcsProvider.Builder srcsBuilder = new J2ObjcSrcsProvider.Builder();
+ XcodeProvider xcodeProvider;
Iterable<Artifact> headerMappingFiles;
Iterable<Artifact> classMappingFiles;
+ ObjcCommon common;
if (protoSources.isEmpty()) {
headerMappingFiles = ImmutableList.of();
classMappingFiles = ImmutableList.of();
+ common = J2ObjcAspect.common(
+ ruleContext,
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<PathFragment>of(),
+ DEPENDENT_ATTRIBUTES);
+ xcodeProvider = J2ObjcAspect.xcodeProvider(
+ ruleContext,
+ common,
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<PathFragment>of(),
+ DEPENDENT_ATTRIBUTES);
} else {
J2ObjcSource j2ObjcSource = j2ObjcSource(ruleContext, protoSources);
headerMappingFiles = headerMappingFiles(ruleContext, protoSources);
classMappingFiles = classMappingFiles(ruleContext, protoSources);
- srcsBuilder.addSource(j2ObjcSource);
createActions(base, ruleContext, protoSources, transitiveImports,
headerMappingFiles, classMappingFiles, j2ObjcSource);
+ common = J2ObjcAspect.common(
+ ruleContext,
+ j2ObjcSource.getObjcSrcs(),
+ j2ObjcSource.getObjcHdrs(),
+ j2ObjcSource.getHeaderSearchPaths(),
+ DEPENDENT_ATTRIBUTES);
+ xcodeProvider = J2ObjcAspect.xcodeProvider(
+ ruleContext,
+ common,
+ j2ObjcSource.getObjcHdrs(),
+ j2ObjcSource.getHeaderSearchPaths(),
+ DEPENDENT_ATTRIBUTES);
+
+ new CompilationSupport(ruleContext).registerCompileAndArchiveActions(common);
}
- J2ObjcSrcsProvider j2objcSrcsProvider = srcsBuilder
- .addTransitiveJ2ObjcSrcs(ruleContext, "deps")
- .build();
NestedSet<Artifact> j2ObjcTransitiveHeaderMappingFiles = j2ObjcTransitiveHeaderMappingFiles(
ruleContext, headerMappingFiles);
NestedSet<Artifact> j2ObjcTransitiveClassMappingFiles = j2ObjcTransitiveClassMappingFiles(
ruleContext, classMappingFiles);
return new ConfiguredAspect.Builder(NAME, ruleContext)
- .addProvider(J2ObjcSrcsProvider.class, j2objcSrcsProvider)
.addProvider(
J2ObjcMappingFileProvider.class,
new J2ObjcMappingFileProvider(
j2ObjcTransitiveHeaderMappingFiles,
j2ObjcTransitiveClassMappingFiles,
+ NestedSetBuilder.<Artifact>stableOrder().build(),
NestedSetBuilder.<Artifact>stableOrder().build()))
+ .addProvider(ObjcProvider.class, common.getObjcProvider())
+ .addProvider(XcodeProvider.class, xcodeProvider)
.build();
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/BUILD b/src/main/java/com/google/devtools/build/lib/rules/objc/BUILD
index c746977..5879101 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/BUILD
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/BUILD
@@ -14,6 +14,7 @@
"//src/main/java/com/google/devtools/build/lib:collect",
"//src/main/java/com/google/devtools/build/lib:common",
"//src/main/java/com/google/devtools/build/lib:concurrent",
+ "//src/main/java/com/google/devtools/build/lib:events",
"//src/main/java/com/google/devtools/build/lib:java-rules",
"//src/main/java/com/google/devtools/build/lib:packages-internal",
"//src/main/java/com/google/devtools/build/lib:proto-rules",
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/BazelJ2ObjcProtoAspect.java b/src/main/java/com/google/devtools/build/lib/rules/objc/BazelJ2ObjcProtoAspect.java
index b2ce8f9..b49bb8f 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/BazelJ2ObjcProtoAspect.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/BazelJ2ObjcProtoAspect.java
@@ -26,6 +26,7 @@
import com.google.devtools.build.lib.analysis.RuleContext;
import com.google.devtools.build.lib.analysis.actions.CustomCommandLine;
import com.google.devtools.build.lib.analysis.actions.SpawnAction;
+import com.google.devtools.build.lib.cmdline.Label;
import com.google.devtools.build.lib.collect.nestedset.NestedSet;
import com.google.devtools.build.lib.packages.AspectDefinition;
import com.google.devtools.build.lib.vfs.PathFragment;
@@ -43,62 +44,70 @@
.add(attr("$protoc_darwin", LABEL)
.cfg(HOST)
.exec()
- .value(parseLabel(Constants.TOOLS_REPOSITORY + "//tools/objc:compile_protos")))
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/objc:compile_protos")))
.add(attr("$protoc_support_darwin", LABEL)
.cfg(HOST)
.exec()
- .value(parseLabel(Constants.TOOLS_REPOSITORY + "//tools/objc:proto_support")))
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/objc:proto_support")))
.add(attr("$j2objc_plugin", LABEL)
.cfg(HOST)
.exec()
- .value(parseLabel(
+ .value(Label.parseAbsoluteUnchecked(
Constants.TOOLS_REPOSITORY + "//third_party/java/j2objc:proto_plugin")));
}
- @Override
- protected boolean checkShouldCreateAspect(RuleContext ruleContext) {
- return true;
- }
-
- protected void createActions(ConfiguredTarget base, RuleContext ruleContext,
- Iterable<Artifact> protoSources, NestedSet<Artifact> transitiveProtoSources,
- Iterable<Artifact> headerMappingFiles, Iterable<Artifact> classMappingFiles,
- J2ObjcSource j2ObjcSource) {
- String genDir = ruleContext.getConfiguration().getGenfilesDirectory().getExecPathString();
- Artifact compiler = ruleContext.getPrerequisiteArtifact(
- "$protoc_darwin", Mode.HOST);
- Artifact j2objcPlugin = ruleContext.getPrerequisiteArtifact("$j2objc_plugin", Mode.HOST);
-
- ruleContext.registerAction(new SpawnAction.Builder()
- .setMnemonic("TranslatingJ2ObjcProtos")
- .addInput(compiler)
- .addInput(j2objcPlugin)
- .addInputs(ruleContext.getPrerequisiteArtifacts(
- "$protoc_support_darwin", Mode.HOST).list())
- .addInputs(protoSources)
- .addTransitiveInputs(transitiveProtoSources)
- .addOutputs(j2ObjcSource.getObjcSrcs())
- .addOutputs(j2ObjcSource.getObjcHdrs())
- .addOutputs(headerMappingFiles)
- .addOutputs(classMappingFiles)
- .setExecutable(new PathFragment("/usr/bin/python"))
- .setCommandLine(new CustomCommandLine.Builder()
- .add(compiler.getPath().toString())
- .add("-w")
- .add(".") // Actions are always run with the exec root as cwd
- .add("--generate-j2objc")
- .add("--generator-param=file_dir_mapping")
- .add("--generator-param=generate_class_mappings")
- .add("--j2objc-plugin=" + j2objcPlugin.getExecPathString())
- .add("--output-dir=" + genDir)
- .addExecPaths(protoSources)
- .build())
- .setExecutionInfo(ImmutableMap.of(ExecutionRequirements.REQUIRES_DARWIN, ""))
- .build(ruleContext));
+ @Override
+ protected boolean checkShouldCreateAspect(RuleContext ruleContext) {
+ return true;
}
- @Override
+ @Override
+ protected void createActions(
+ ConfiguredTarget base,
+ RuleContext ruleContext,
+ Iterable<Artifact> protoSources,
+ NestedSet<Artifact> transitiveProtoSources,
+ Iterable<Artifact> headerMappingFiles,
+ Iterable<Artifact> classMappingFiles,
+ J2ObjcSource j2ObjcSource) {
+ String genDir = ruleContext.getConfiguration().getGenfilesDirectory().getExecPathString();
+ Artifact compiler = ruleContext.getPrerequisiteArtifact("$protoc_darwin", Mode.HOST);
+ Artifact j2objcPlugin = ruleContext.getPrerequisiteArtifact("$j2objc_plugin", Mode.HOST);
+
+ ruleContext.registerAction(
+ new SpawnAction.Builder()
+ .setMnemonic("TranslatingJ2ObjcProtos")
+ .addInput(compiler)
+ .addInput(j2objcPlugin)
+ .addInputs(
+ ruleContext.getPrerequisiteArtifacts("$protoc_support_darwin", Mode.HOST).list())
+ .addInputs(protoSources)
+ .addTransitiveInputs(transitiveProtoSources)
+ .addOutputs(j2ObjcSource.getObjcSrcs())
+ .addOutputs(j2ObjcSource.getObjcHdrs())
+ .addOutputs(headerMappingFiles)
+ .addOutputs(classMappingFiles)
+ .setExecutable(new PathFragment("/usr/bin/python"))
+ .setCommandLine(
+ new CustomCommandLine.Builder()
+ .add(compiler.getPath().toString())
+ .add("-w")
+ .add(".") // Actions are always run with the exec root as cwd
+ .add("--generate-j2objc")
+ .add("--generator-param=file_dir_mapping")
+ .add("--generator-param=generate_class_mappings")
+ .add("--j2objc-plugin=" + j2objcPlugin.getExecPathString())
+ .add("--output-dir=" + genDir)
+ .addExecPaths(protoSources)
+ .build())
+ .setExecutionInfo(ImmutableMap.of(ExecutionRequirements.REQUIRES_DARWIN, ""))
+ .build(ruleContext));
+ }
+
+ @Override
protected boolean checkShouldCreateSources(RuleContext ruleContext) {
- return true;
+ return true;
}
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/BinaryLinkingTargetFactory.java b/src/main/java/com/google/devtools/build/lib/rules/objc/BinaryLinkingTargetFactory.java
index 44b949c..4330751 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/BinaryLinkingTargetFactory.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/BinaryLinkingTargetFactory.java
@@ -99,7 +99,6 @@
CompilationSupport compilationSupport =
new CompilationSupport(ruleContext)
- .registerJ2ObjcCompileAndArchiveActions(objcProvider)
.registerCompileAndArchiveActions(common)
.addXcodeSettings(xcodeProviderBuilder, common)
.registerLinkActions(
@@ -208,7 +207,6 @@
.setIntermediateArtifacts(intermediateArtifacts)
.setAlwayslink(false)
.setHasModuleMap()
- .addExtraImportLibraries(ObjcRuleClasses.j2ObjcLibraries(ruleContext))
.setLinkedBinary(intermediateArtifacts.strippedSingleArchitectureBinary());
if (ObjcRuleClasses.objcConfiguration(ruleContext).generateDebugSymbols()) {
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/CompilationSupport.java b/src/main/java/com/google/devtools/build/lib/rules/objc/CompilationSupport.java
index 9fb00d4..c0eca43 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/CompilationSupport.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/CompilationSupport.java
@@ -69,6 +69,7 @@
import com.google.devtools.build.lib.analysis.actions.SpawnAction;
import com.google.devtools.build.lib.collect.nestedset.NestedSet;
import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
+import com.google.devtools.build.lib.collect.nestedset.Order;
import com.google.devtools.build.lib.packages.BuildType;
import com.google.devtools.build.lib.packages.ImplicitOutputsFunction.SafeImplicitOutputsFunction;
import com.google.devtools.build.lib.packages.TargetUtils;
@@ -78,8 +79,6 @@
import com.google.devtools.build.lib.rules.cpp.CppModuleMap;
import com.google.devtools.build.lib.rules.cpp.CppModuleMapAction;
import com.google.devtools.build.lib.rules.cpp.LinkerInputs;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
-import com.google.devtools.build.lib.rules.objc.J2ObjcSource.SourceType;
import com.google.devtools.build.lib.rules.objc.ObjcCommon.CompilationAttributes;
import com.google.devtools.build.lib.rules.objc.XcodeProvider.Builder;
import com.google.devtools.build.lib.rules.test.InstrumentedFilesCollector;
@@ -713,10 +712,30 @@
dsymBundle = Optional.absent();
}
- registerLinkAction(objcProvider, extraLinkArgs, extraLinkInputs, dsymBundle);
+ Iterable<Artifact> prunedJ2ObjcArchives = ImmutableList.<Artifact>of();
+ if (stripJ2ObjcDeadCode()) {
+ J2ObjcEntryClassProvider provider = J2ObjcEntryClassProvider.buildFrom(ruleContext);
+ registerJ2ObjcDeadCodeRemovalActions(objcProvider, provider.getEntryClasses());
+ prunedJ2ObjcArchives = j2objcPrunedLibraries(objcProvider);
+ }
+
+ registerLinkAction(
+ objcProvider,
+ extraLinkArgs,
+ extraLinkInputs,
+ dsymBundle,
+ prunedJ2ObjcArchives);
return this;
}
+ private boolean stripJ2ObjcDeadCode() {
+ J2ObjcEntryClassProvider provider = J2ObjcEntryClassProvider.buildFrom(ruleContext);
+ J2ObjcConfiguration j2objcConfiguration = ruleContext.getFragment(J2ObjcConfiguration.class);
+ // Only perform J2ObjC dead code stripping if flag --j2objc_dead_code_removal is specified and
+ // users have specified entry classes.
+ return j2objcConfiguration.removeDeadCode() && !provider.getEntryClasses().isEmpty();
+ }
+
/**
* Registers an action that will generate a clang module map for this target, using the hdrs
* attribute of this rule.
@@ -768,7 +787,8 @@
}
private void registerLinkAction(ObjcProvider objcProvider, ExtraLinkArgs extraLinkArgs,
- Iterable<Artifact> extraLinkInputs, Optional<Artifact> dsymBundle) {
+ Iterable<Artifact> extraLinkInputs, Optional<Artifact> dsymBundle,
+ Iterable<Artifact> prunedJ2ObjcArchives) {
ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
IntermediateArtifacts intermediateArtifacts =
ObjcRuleClasses.intermediateArtifacts(ruleContext);
@@ -784,19 +804,23 @@
: intermediateArtifacts.strippedSingleArchitectureBinary();
ImmutableList<Artifact> ccLibraries = ccLibraries(objcProvider);
+ NestedSet<Artifact> bazelBuiltLibraries = Iterables.isEmpty(prunedJ2ObjcArchives)
+ ? objcProvider.get(LIBRARY) : substituteJ2ObjcPrunedLibraries(objcProvider);
ruleContext.registerAction(
ObjcRuleClasses.spawnXcrunActionBuilder(ruleContext)
.setMnemonic("ObjcLink")
.setShellCommand(ImmutableList.of("/bin/bash", "-c"))
.setCommandLine(
- linkCommandLine(extraLinkArgs, objcProvider, binaryToLink, dsymBundle, ccLibraries))
+ linkCommandLine(extraLinkArgs, objcProvider, binaryToLink, dsymBundle, ccLibraries,
+ bazelBuiltLibraries))
.addOutput(binaryToLink)
.addOutputs(dsymBundle.asSet())
- .addTransitiveInputs(objcProvider.get(LIBRARY))
+ .addTransitiveInputs(bazelBuiltLibraries)
.addTransitiveInputs(objcProvider.get(IMPORTED_LIBRARY))
.addTransitiveInputs(objcProvider.get(FRAMEWORK_FILE))
.addInputs(ccLibraries)
.addInputs(extraLinkInputs)
+ .addInputs(prunedJ2ObjcArchives)
.addInput(xcrunwrapper(ruleContext).getExecutable())
.build(ruleContext));
@@ -827,6 +851,16 @@
return ccLibraryBuilder.build();
}
+ private ImmutableList<Artifact> j2objcPrunedLibraries(ObjcProvider objcProvider) {
+ IntermediateArtifacts intermediateArtifacts =
+ ObjcRuleClasses.intermediateArtifacts(ruleContext);
+ ImmutableList.Builder<Artifact> j2objcPrunedLibraryBuilder = ImmutableList.builder();
+ for (Artifact j2objcLibrary : objcProvider.get(ObjcProvider.J2OBJC_LIBRARY)) {
+ j2objcPrunedLibraryBuilder.add(intermediateArtifacts.j2objcPrunedArchive(j2objcLibrary));
+ }
+ return j2objcPrunedLibraryBuilder.build();
+ }
+
private static CommandLine symbolStripCommandLine(
Iterable<String> extraFlags, Artifact unstrippedArtifact, Artifact strippedArtifact) {
return CustomCommandLine.builder()
@@ -837,16 +871,37 @@
.build();
}
+ /**
+ * Returns a nested set of Bazel-built ObjC libraries with all unpruned J2ObjC libraries
+ * substituted with pruned ones.
+ */
+ private NestedSet<Artifact> substituteJ2ObjcPrunedLibraries(ObjcProvider objcProvider) {
+ ImmutableList.Builder<Artifact> libraries = new ImmutableList.Builder<>();
+ IntermediateArtifacts intermediateArtifacts =
+ ObjcRuleClasses.intermediateArtifacts(ruleContext);
+
+ Set<Artifact> unprunedJ2ObjcLibs = objcProvider.get(ObjcProvider.J2OBJC_LIBRARY).toSet();
+ for (Artifact library : objcProvider.get(LIBRARY)) {
+ // If we match an unpruned J2ObjC library, add the pruned version of the J2ObjC static library
+ // instead.
+ if (unprunedJ2ObjcLibs.contains(library)) {
+ libraries.add(intermediateArtifacts.j2objcPrunedArchive(library));
+ } else {
+ libraries.add(library);
+ }
+ }
+ return NestedSetBuilder.wrap(Order.NAIVE_LINK_ORDER, libraries.build());
+ }
+
private CommandLine linkCommandLine(ExtraLinkArgs extraLinkArgs,
ObjcProvider objcProvider, Artifact linkedBinary, Optional<Artifact> dsymBundle,
- ImmutableList<Artifact> ccLibraries) {
+ Iterable<Artifact> ccLibraries, Iterable<Artifact> bazelBuiltLibraries) {
ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
AppleConfiguration appleConfiguration = ruleContext.getFragment(AppleConfiguration.class);
Iterable<String> libraryNames = libraryNames(objcProvider);
CustomCommandLine.Builder commandLine = CustomCommandLine.builder()
.addPath(xcrunwrapper(ruleContext).getExecutable().getExecPath());
-
if (objcProvider.is(USES_CPP)) {
commandLine
.add(CLANG_PLUSPLUS)
@@ -883,7 +938,7 @@
commandLine
.addExecPath("-o", linkedBinary)
- .addExecPaths(objcProvider.get(LIBRARY))
+ .addExecPaths(bazelBuiltLibraries)
.addExecPaths(objcProvider.get(IMPORTED_LIBRARY))
.addExecPaths(ccLibraries)
.addBeforeEach("-force_load", Artifact.toExecPaths(objcProvider.get(FORCE_LOAD_LIBRARY)))
@@ -982,131 +1037,59 @@
return names;
}
- /**
- * Registers actions that compile and archive j2Objc dependencies of this rule.
- *
- * @param objcProvider common information about this rule's attributes and its dependencies
- *
- * @return this compilation support
- */
- CompilationSupport registerJ2ObjcCompileAndArchiveActions(ObjcProvider objcProvider)
- throws InterruptedException {
- J2ObjcSrcsProvider provider = J2ObjcSrcsProvider.buildFrom(ruleContext);
- Iterable<J2ObjcSource> j2ObjcSources = provider.getSrcs();
- J2ObjcConfiguration j2objcConfiguration = ruleContext.getFragment(J2ObjcConfiguration.class);
-
- // Only perform J2ObjC dead code stripping if flag --j2objc_dead_code_removal is specified and
- // users have specified entry classes.
- boolean stripJ2ObjcDeadCode = j2objcConfiguration.removeDeadCode()
- && !provider.getEntryClasses().isEmpty();
-
- if (stripJ2ObjcDeadCode) {
- registerJ2ObjcDeadCodeRemovalActions(j2ObjcSources, provider.getEntryClasses());
- }
-
- for (J2ObjcSource j2ObjcSource : j2ObjcSources) {
- if (j2ObjcSource.hasSourceFiles()) {
- J2ObjcSource sourceToCompile =
- j2ObjcSource.getSourceType() == SourceType.JAVA && stripJ2ObjcDeadCode
- ? j2ObjcSource.toPrunedSource(ruleContext)
- : j2ObjcSource;
- IntermediateArtifacts intermediateArtifacts =
- ObjcRuleClasses.j2objcIntermediateArtifacts(ruleContext, sourceToCompile);
- CompilationArtifacts compilationArtifact = new CompilationArtifacts.Builder()
- .addNonArcSrcs(sourceToCompile.getObjcSrcs())
- .setIntermediateArtifacts(intermediateArtifacts)
- .setPchFile(Optional.<Artifact>absent())
- .build();
- // The module map that the above intermediateArtifacts would point to is a combination of
- // the current target and the java target. Instead, we want the one generated for that
- // source, but there is no easy way to get that. So for now, compile the source with the
- // module map (and therefore module name) for this rule.
- // TODO(bazel-team): Generate module maps along with the J2Objc sources, and use that here.
- Optional<CppModuleMap> moduleMap;
- if (ObjcRuleClasses.objcConfiguration(ruleContext).moduleMapsEnabled()) {
- moduleMap = Optional.of(ObjcRuleClasses.intermediateArtifacts(ruleContext).moduleMap());
- } else {
- moduleMap = Optional.absent();
- }
- registerCompileAndArchiveActions(
- compilationArtifact,
- intermediateArtifacts,
- objcProvider.toJ2ObjcOnlyProvider(),
- moduleMap,
- ruleContext.getConfiguration().isCodeCoverageEnabled(),
- false);
- }
- }
-
- return this;
- }
-
- /**
- * Registers actions that generates a module map for all {@link J2ObjcSource}s in
- * {@link J2ObjcSrcsProvider}.
- *
- * @return this compilation support
- */
- public CompilationSupport registerJ2ObjcGenerateModuleMapAction(J2ObjcSrcsProvider provider) {
- if (ObjcRuleClasses.objcConfiguration(ruleContext).moduleMapsEnabled()) {
- CppModuleMap moduleMap = ObjcRuleClasses.intermediateArtifacts(ruleContext).moduleMap();
- ImmutableSet.Builder<Artifact> headers = ImmutableSet.builder();
- for (J2ObjcSource j2ObjcSource : provider.getSrcs()) {
- headers.addAll(j2ObjcSource.getObjcHdrs());
- }
- registerGenerateModuleMapAction(moduleMap, headers.build(), ImmutableList.<Artifact>of());
- }
- return this;
- }
-
- private void registerJ2ObjcDeadCodeRemovalActions(Iterable<J2ObjcSource> j2ObjcSources,
+ private void registerJ2ObjcDeadCodeRemovalActions(ObjcProvider objcProvider,
Iterable<String> entryClasses) {
Artifact pruner = ruleContext.getPrerequisiteArtifact("$j2objc_dead_code_pruner", Mode.HOST);
J2ObjcMappingFileProvider provider = ObjcRuleClasses.j2ObjcMappingFileProvider(ruleContext);
NestedSet<Artifact> j2ObjcDependencyMappingFiles = provider.getDependencyMappingFiles();
NestedSet<Artifact> j2ObjcHeaderMappingFiles = provider.getHeaderMappingFiles();
+ NestedSet<Artifact> j2ObjcArchiveSourceMappingFiles = provider.getArchiveSourceMappingFiles();
+ IntermediateArtifacts intermediateArtifacts =
+ ObjcRuleClasses.intermediateArtifacts(ruleContext);
- for (J2ObjcSource j2ObjcSource : j2ObjcSources) {
- if (j2ObjcSource.getSourceType() == SourceType.JAVA
- && j2ObjcSource.hasSourceFiles()) {
- Iterable<Artifact> sourceArtifacts = j2ObjcSource.getObjcSrcs();
- Iterable<Artifact> prunedSourceArtifacts =
- j2ObjcSource.toPrunedSource(ruleContext).getObjcSrcs();
- PathFragment paramFilePath = FileSystemUtils.replaceExtension(
- j2ObjcSource.getTargetLabel().toPathFragment(), ".param.j2objc");
- Artifact paramFile = ruleContext.getUniqueDirectoryArtifact(
- "_j2objc_pruned",
- paramFilePath,
- ruleContext.getBinOrGenfilesDirectory());
- PathFragment objcFilePath = j2ObjcSource.getObjcFilePath();
- CustomCommandLine commandLine = CustomCommandLine.builder()
- .addJoinExecPaths("--input_files", ",", sourceArtifacts)
- .addJoinExecPaths("--output_files", ",", prunedSourceArtifacts)
- .addJoinExecPaths("--dependency_mapping_files", ",", j2ObjcDependencyMappingFiles)
- .addJoinExecPaths("--header_mapping_files", ",", j2ObjcHeaderMappingFiles)
- .add("--entry_classes").add(Joiner.on(",").join(entryClasses))
- .add("--objc_file_path").add(objcFilePath.getPathString())
- .build();
+ for (Artifact j2objcArchive : objcProvider.get(ObjcProvider.J2OBJC_LIBRARY)) {
+ PathFragment paramFilePath = FileSystemUtils.replaceExtension(
+ j2objcArchive.getOwner().toPathFragment(), ".param.j2objc");
+ Artifact paramFile = ruleContext.getUniqueDirectoryArtifact(
+ "_j2objc_pruned",
+ paramFilePath,
+ ruleContext.getBinOrGenfilesDirectory());
+ Artifact prunedJ2ObjcArchive = intermediateArtifacts.j2objcPrunedArchive(j2objcArchive);
+ Artifact dummyArchive = Iterables.getOnlyElement(
+ ruleContext.getPrerequisite("$dummy_lib", Mode.TARGET, ObjcProvider.class).get(LIBRARY));
+
+ CustomCommandLine commandLine = CustomCommandLine.builder()
+ .addExecPath("--input_archive", j2objcArchive)
+ .addExecPath("--output_archive", prunedJ2ObjcArchive)
+ .addExecPath("--dummy_archive", dummyArchive)
+ .addExecPath("--xcrunwrapper", xcrunwrapper(ruleContext).getExecutable())
+ .addJoinExecPaths("--dependency_mapping_files", ",", j2ObjcDependencyMappingFiles)
+ .addJoinExecPaths("--header_mapping_files", ",", j2ObjcHeaderMappingFiles)
+ .addJoinExecPaths("--archive_source_mapping_files", ",", j2ObjcArchiveSourceMappingFiles)
+ .add("--entry_classes").add(Joiner.on(",").join(entryClasses))
+ .build();
ruleContext.registerAction(new ParameterFileWriteAction(
ruleContext.getActionOwner(),
paramFile,
commandLine,
ParameterFile.ParameterFileType.UNQUOTED, ISO_8859_1));
- ruleContext.registerAction(new SpawnAction.Builder()
+ ruleContext.registerAction(ObjcRuleClasses.spawnXcrunActionBuilder(ruleContext)
.setMnemonic("DummyPruner")
.setExecutable(pruner)
+ .addInput(dummyArchive)
.addInput(pruner)
.addInput(paramFile)
- .addInputs(sourceArtifacts)
+ .addInput(j2objcArchive)
+ .addInput(xcrunwrapper(ruleContext).getExecutable())
.addTransitiveInputs(j2ObjcDependencyMappingFiles)
.addTransitiveInputs(j2ObjcHeaderMappingFiles)
+ .addTransitiveInputs(j2ObjcArchiveSourceMappingFiles)
.setCommandLine(CustomCommandLine.builder()
.addPaths("@%s", paramFile.getExecPath())
.build())
- .addOutputs(prunedSourceArtifacts)
+ .addOutput(prunedJ2ObjcArchive)
.build(ruleContext));
- }
}
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/IntermediateArtifacts.java b/src/main/java/com/google/devtools/build/lib/rules/objc/IntermediateArtifacts.java
index ad3c3e8..1ff60eb 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/IntermediateArtifacts.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/IntermediateArtifacts.java
@@ -14,7 +14,6 @@
package com.google.devtools.build.lib.rules.objc;
-import com.google.common.base.Optional;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.actions.Root;
import com.google.devtools.build.lib.analysis.RuleConfiguredTarget.Mode;
@@ -41,21 +40,8 @@
private final RuleContext ruleContext;
private final String archiveFileNameSuffix;
- /**
- * Label to scope the output paths of generated artifacts, in addition to label of the rule that
- * is being analyzed.
- */
- private final Optional<Label> scopingLabel;
-
IntermediateArtifacts(RuleContext ruleContext, String archiveFileNameSuffix) {
this.ruleContext = ruleContext;
- this.scopingLabel = Optional.<Label>absent();
- this.archiveFileNameSuffix = Preconditions.checkNotNull(archiveFileNameSuffix);
- }
-
- IntermediateArtifacts(RuleContext ruleContext, Label scopingLabel, String archiveFileNameSuffix) {
- this.ruleContext = ruleContext;
- this.scopingLabel = Optional.of(Preconditions.checkNotNull(scopingLabel));
this.archiveFileNameSuffix = Preconditions.checkNotNull(archiveFileNameSuffix);
}
@@ -178,23 +164,9 @@
inGenfiles
? ruleContext.getConfiguration().getGenfilesDirectory()
: ruleContext.getConfiguration().getBinDirectory();
- if (scopingLabel.isPresent()) {
- // The path of this artifact will be
- // RULE_PACKAGE/_intermediate_scoped/RULE_LABEL/SCOPING_PACKAGE/SCOPING_LABEL/SCOPERELATIVE
- return ruleContext.getUniqueDirectoryArtifact(
- "_intermediate_scoped",
- scopingLabel
- .get()
- .getPackageIdentifier()
- .getPathFragment()
- .getRelative(scopingLabel.get().getName())
- .getRelative(scopeRelative),
- root);
- } else {
- // The path of this artifact will be
- // RULE_PACKAGE/SCOPERELATIVE
- return ruleContext.getPackageRelativeArtifact(scopeRelative, root);
- }
+
+ // The path of this artifact will be RULE_PACKAGE/SCOPERELATIVE
+ return ruleContext.getPackageRelativeArtifact(scopeRelative, root);
}
private Artifact scopedArtifact(PathFragment scopeRelative) {
@@ -205,12 +177,8 @@
* The {@code .a} file which contains all the compiled sources for a rule.
*/
public Artifact archive() {
- // If scopingLabel is present, the path will be
- // RULE_PACKAGE/_intermediate_scoped/RULE_LABEL/SCOPE_PACKAGE/SCOPE_LABEL/libRULEBASENAME.a
- //
- // If it's not, the path will be RULE_PACKAGE/libRULEBASENAME.a .
- String basename = new PathFragment(scopingLabel.isPresent()
- ? scopingLabel.get().getName() : ruleContext.getLabel().getName()).getBaseName();
+ // The path will be RULE_PACKAGE/libRULEBASENAME.a
+ String basename = new PathFragment(ruleContext.getLabel().getName()).getBaseName();
return scopedArtifact(new PathFragment(String.format(
"lib%s%s.a", basename, archiveFileNameSuffix)));
}
@@ -381,4 +349,17 @@
// parent directory in the module map search paths.
return new CppModuleMap(appendExtensionInGenfiles(".modulemaps/module.modulemap"), moduleName);
}
+
+ /**
+ * Returns a static library archive with dead code/objects removed by J2ObjC dead code removal,
+ * given the original unpruned static library containing J2ObjC-translated code.
+ */
+ public Artifact j2objcPrunedArchive(Artifact unprunedArchive) {
+ PathFragment prunedSourceArtifactPath = FileSystemUtils.appendWithoutExtension(
+ unprunedArchive.getRootRelativePath(), "_pruned");
+ return ruleContext.getUniqueDirectoryArtifact(
+ "_j2objc_pruned",
+ prunedSourceArtifactPath,
+ ruleContext.getBinOrGenfilesDirectory());
+ }
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/IosExtensionBinaryRule.java b/src/main/java/com/google/devtools/build/lib/rules/objc/IosExtensionBinaryRule.java
index 6879e36..846e2a9 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/IosExtensionBinaryRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/IosExtensionBinaryRule.java
@@ -20,7 +20,6 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
/**
* Rule definition for ios_extension_binary.
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/IosFrameworkBinaryRule.java b/src/main/java/com/google/devtools/build/lib/rules/objc/IosFrameworkBinaryRule.java
index 3ee1bc7..209d53e 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/IosFrameworkBinaryRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/IosFrameworkBinaryRule.java
@@ -20,7 +20,6 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
/**
* Rule definition for ios_framework_binary.
@@ -62,4 +61,4 @@
${IMPLICIT_OUTPUTS}
-<!-- #END_BLAZE_RULE -->*/
\ No newline at end of file
+<!-- #END_BLAZE_RULE -->*/
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/IosTest.java b/src/main/java/com/google/devtools/build/lib/rules/objc/IosTest.java
index 92b3f9d..cfb6873 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/IosTest.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/IosTest.java
@@ -122,7 +122,6 @@
new CompilationSupport(ruleContext)
.registerLinkActions(common.getObjcProvider(), extraLinkArgs, extraLinkInputs)
- .registerJ2ObjcCompileAndArchiveActions(common.getObjcProvider())
.registerCompileAndArchiveActions(common)
.addXcodeSettings(xcodeProviderBuilder, common)
.validateAttributes();
@@ -225,7 +224,6 @@
.add(ruleContext.getPrerequisite(MEMLEAKS_DEP, Mode.TARGET, ObjcProvider.class));
}
return ObjcLibrary.common(ruleContext, extraSdkFrameworks, /*alwayslink=*/false,
- new ObjcLibrary.ExtraImportLibraries(ObjcRuleClasses.j2ObjcLibraries(ruleContext)),
extraDepObjcProviders);
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/IosTestRule.java b/src/main/java/com/google/devtools/build/lib/rules/objc/IosTestRule.java
index 75cff59..d7b29f4 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/IosTestRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/IosTestRule.java
@@ -35,7 +35,6 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder.RuleClassType;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.syntax.Type;
import com.google.devtools.build.lib.util.FileType;
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcAspect.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcAspect.java
index ab1aa8a..5103e56 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcAspect.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcAspect.java
@@ -17,10 +17,13 @@
import static com.google.devtools.build.lib.packages.Attribute.ConfigurationTransition.HOST;
import static com.google.devtools.build.lib.packages.Attribute.attr;
import static com.google.devtools.build.lib.packages.BuildType.LABEL;
+import static com.google.devtools.build.lib.rules.objc.XcodeProductType.LIBRARY_STATIC;
import static java.nio.charset.StandardCharsets.ISO_8859_1;
+import com.google.common.base.Optional;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Iterables;
import com.google.devtools.build.lib.Constants;
import com.google.devtools.build.lib.actions.Artifact;
import com.google.devtools.build.lib.actions.ParameterFile;
@@ -34,13 +37,13 @@
import com.google.devtools.build.lib.analysis.actions.ParameterFileWriteAction;
import com.google.devtools.build.lib.analysis.actions.SpawnAction;
import com.google.devtools.build.lib.cmdline.Label;
-import com.google.devtools.build.lib.cmdline.LabelSyntaxException;
import com.google.devtools.build.lib.collect.nestedset.NestedSet;
import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
import com.google.devtools.build.lib.packages.AspectDefinition;
import com.google.devtools.build.lib.packages.AspectParameters;
import com.google.devtools.build.lib.packages.BuildType;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
+import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
+import com.google.devtools.build.lib.rules.apple.AppleToolchain;
import com.google.devtools.build.lib.rules.java.JavaCompilationArgsProvider;
import com.google.devtools.build.lib.rules.java.JavaCompilationHelper;
import com.google.devtools.build.lib.rules.java.JavaSourceInfoProvider;
@@ -56,10 +59,18 @@
*/
public class J2ObjcAspect implements ConfiguredNativeAspectFactory {
public static final String NAME = "J2ObjcAspect";
+
+ private static final Iterable<Attribute> DEPENDENT_ATTRIBUTES = ImmutableList.of(
+ new Attribute("$jre_emul_lib", Mode.TARGET),
+ new Attribute("deps", Mode.TARGET),
+ new Attribute("exports", Mode.TARGET),
+ new Attribute("runtime_deps", Mode.TARGET));
+
/**
- * Adds the attribute aspect args to the given AspectDefinition.Builder.
+ * Adds additional attribute aspects and attributes to the given AspectDefinition.Builder.
*/
- protected AspectDefinition.Builder addAttributeAspects(AspectDefinition.Builder builder) {
+ protected AspectDefinition.Builder addAdditionalAttributes(
+ AspectDefinition.Builder builder) {
return builder.attributeAspect("deps", J2ObjcAspect.class, BazelJ2ObjcProtoAspect.class)
.attributeAspect("exports", J2ObjcAspect.class, BazelJ2ObjcProtoAspect.class)
.attributeAspect("runtime_deps", J2ObjcAspect.class, BazelJ2ObjcProtoAspect.class);
@@ -67,67 +78,109 @@
@Override
public AspectDefinition getDefinition(AspectParameters aspectParameters) {
- return addAttributeAspects(new AspectDefinition.Builder("J2ObjCAspect"))
+ return addAdditionalAttributes(new AspectDefinition.Builder("J2ObjCAspect"))
.requireProvider(JavaSourceInfoProvider.class)
.requireProvider(JavaCompilationArgsProvider.class)
+ .requiresConfigurationFragments(
+ AppleConfiguration.class,
+ J2ObjcConfiguration.class,
+ ObjcConfiguration.class)
.add(attr("$j2objc", LABEL).cfg(HOST).exec()
- .value(parseLabel(Constants.TOOLS_REPOSITORY + "//tools/j2objc:j2objc_deploy.jar")))
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/j2objc:j2objc_deploy.jar")))
.add(attr("$j2objc_wrapper", LABEL)
.allowedFileTypes(FileType.of(".py"))
.cfg(HOST)
.exec()
.singleArtifact()
- .value(parseLabel(Constants.TOOLS_REPOSITORY + "//tools/j2objc:j2objc_wrapper")))
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/j2objc:j2objc_wrapper")))
+ .add(attr("$jre_emul_lib", LABEL)
+ .value(Label.parseAbsoluteUnchecked("//third_party/java/j2objc:jre_emul_lib")))
+ .add(attr("$xcrunwrapper", LABEL).cfg(HOST).exec()
+ .value(Label.parseAbsoluteUnchecked(
+ Constants.TOOLS_REPOSITORY + "//tools/objc:xcrunwrapper")))
+ .add(attr(":xcode_config", LABEL)
+ .allowedRuleClasses("xcode_config")
+ .checkConstraints()
+ .direct_compile_time_input()
+ .cfg(HOST)
+ .value(AppleToolchain.RequiresXcodeConfigRule.XCODE_CONFIG_LABEL))
.build();
}
- private static Label parseLabel(String from) {
- try {
- return Label.parseAbsolute(from);
- } catch (LabelSyntaxException e) {
- throw new IllegalArgumentException(from);
- }
- }
-
@Override
public ConfiguredAspect create(
- ConfiguredTarget base, RuleContext ruleContext, AspectParameters parameters) {
+ ConfiguredTarget base, RuleContext ruleContext, AspectParameters parameters)
+ throws InterruptedException {
ConfiguredAspect.Builder builder = new ConfiguredAspect.Builder(NAME, ruleContext);
-
JavaCompilationArgsProvider compilationArgsProvider =
base.getProvider(JavaCompilationArgsProvider.class);
JavaSourceInfoProvider sourceInfoProvider =
base.getProvider(JavaSourceInfoProvider.class);
-
ImmutableSet<Artifact> javaInputFiles = ImmutableSet.<Artifact>builder()
.addAll(sourceInfoProvider.getSourceFiles())
.addAll(sourceInfoProvider.getSourceJars())
.addAll(sourceInfoProvider.getSourceJarsForJarFiles())
.build();
- NestedSetBuilder<Artifact> depsHeaderMappingsBuilder = NestedSetBuilder.stableOrder();
- NestedSetBuilder<Artifact> depsClassMappingsBuilder = NestedSetBuilder.stableOrder();
- NestedSetBuilder<Artifact> depsDependencyMappingsBuilder = NestedSetBuilder.stableOrder();
-
- for (J2ObjcMappingFileProvider provider : getJ2ObjCMappings(ruleContext)) {
- depsHeaderMappingsBuilder.addTransitive(provider.getHeaderMappingFiles());
- depsClassMappingsBuilder.addTransitive(provider.getClassMappingFiles());
- depsDependencyMappingsBuilder.addTransitive(provider.getDependencyMappingFiles());
- }
-
- NestedSet<Artifact> depsHeaderMappings = depsHeaderMappingsBuilder.build();
- NestedSet<Artifact> depsClassMappings = depsClassMappingsBuilder.build();
- NestedSet<Artifact> depsDependencyMappings = depsDependencyMappingsBuilder.build();
-
- J2ObjcSrcsProvider.Builder srcsBuilder = new J2ObjcSrcsProvider.Builder();
- J2ObjcMappingFileProvider j2ObjcMappingFileProvider;
+ XcodeProvider xcodeProvider;
+ ObjcCommon common;
if (!javaInputFiles.isEmpty()) {
J2ObjcSource j2ObjcSource = buildJ2ObjcSource(ruleContext, javaInputFiles);
+ J2ObjcMappingFileProvider depJ2ObjcMappingFileProvider =
+ depJ2ObjcMappingFileProvider(ruleContext);
+ createJ2ObjcTranspilationAction(
+ ruleContext,
+ depJ2ObjcMappingFileProvider.getHeaderMappingFiles(),
+ depJ2ObjcMappingFileProvider.getClassMappingFiles(),
+ javaInputFiles,
+ compilationArgsProvider,
+ j2ObjcSource);
+ common = common(
+ ruleContext,
+ j2ObjcSource.getObjcSrcs(),
+ j2ObjcSource.getObjcHdrs(),
+ j2ObjcSource.getHeaderSearchPaths(),
+ DEPENDENT_ATTRIBUTES);
+ xcodeProvider = xcodeProvider(
+ ruleContext,
+ common,
+ j2ObjcSource.getObjcHdrs(),
+ j2ObjcSource.getHeaderSearchPaths(),
+ DEPENDENT_ATTRIBUTES);
- createJ2ObjcTranspilationAction(ruleContext, depsHeaderMappings, depsClassMappings,
- javaInputFiles, compilationArgsProvider, j2ObjcSource);
+ new CompilationSupport(ruleContext).registerCompileAndArchiveActions(common);
+ } else {
+ common = common(
+ ruleContext,
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<PathFragment>of(),
+ DEPENDENT_ATTRIBUTES);
+ xcodeProvider = xcodeProvider(
+ ruleContext,
+ common,
+ ImmutableList.<Artifact>of(),
+ ImmutableList.<PathFragment>of(),
+ DEPENDENT_ATTRIBUTES);
+ }
+ return builder
+ .addProvider(J2ObjcMappingFileProvider.class,
+ j2ObjcMappingFileProvider(ruleContext, !javaInputFiles.isEmpty()))
+ .addProvider(ObjcProvider.class, common.getObjcProvider())
+ .addProvider(XcodeProvider.class, xcodeProvider)
+ .build();
+ }
+
+ private J2ObjcMappingFileProvider j2ObjcMappingFileProvider(RuleContext ruleContext,
+ boolean hasTranslatedSource) {
+ J2ObjcMappingFileProvider depJ2ObjcMappingFileProvider =
+ depJ2ObjcMappingFileProvider(ruleContext);
+ J2ObjcMappingFileProvider j2ObjcMappingFileProvider = depJ2ObjcMappingFileProvider;
+ if (hasTranslatedSource) {
// J2ObjC merges all input header mapping files into the output header mapping file, so we
// only need to export the output header mapping file here.
NestedSet<Artifact> headerMappingFiles = NestedSetBuilder.<Artifact>stableOrder()
@@ -135,23 +188,22 @@
.build();
NestedSet<Artifact> dependencyMappingFiles = NestedSetBuilder.<Artifact>stableOrder()
.add(j2ObjcOutputDependencyMappingFile(ruleContext))
- .addTransitive(depsDependencyMappings)
+ .addTransitive(depJ2ObjcMappingFileProvider.getDependencyMappingFiles())
.build();
- srcsBuilder.addSource(j2ObjcSource);
+ NestedSet<Artifact> archiveSourceMappingFiles = NestedSetBuilder.<Artifact>stableOrder()
+ .add(j2ObjcOutputArchiveSourceMappingFile(ruleContext))
+ .addTransitive(depJ2ObjcMappingFileProvider.getArchiveSourceMappingFiles())
+ .build();
+
j2ObjcMappingFileProvider = new J2ObjcMappingFileProvider(
- headerMappingFiles, depsClassMappings, dependencyMappingFiles);
- } else {
- j2ObjcMappingFileProvider = new J2ObjcMappingFileProvider(
- depsHeaderMappings, depsClassMappings, depsDependencyMappings);
+ headerMappingFiles,
+ depJ2ObjcMappingFileProvider.getClassMappingFiles(),
+ dependencyMappingFiles,
+ archiveSourceMappingFiles);
}
- srcsBuilder.addTransitiveJ2ObjcSrcs(ruleContext);
-
- return builder
- .addProvider(J2ObjcSrcsProvider.class, srcsBuilder.build())
- .addProvider(J2ObjcMappingFileProvider.class, j2ObjcMappingFileProvider)
- .build();
+ return j2ObjcMappingFileProvider;
}
private static void createJ2ObjcTranspilationAction(
@@ -192,6 +244,12 @@
argBuilder.addJoinExecPaths("--mapping", ",", depsClassMappingFiles);
}
+ Artifact archiveSourceMappingFile = j2ObjcOutputArchiveSourceMappingFile(ruleContext);
+ argBuilder.addExecPath("--output_archive_source_mapping_file", archiveSourceMappingFile);
+
+ Artifact compiledLibrary = ObjcRuleClasses.j2objcIntermediateArtifacts(ruleContext).archive();
+ argBuilder.addExecPath("--compiled_archive_file_path", compiledLibrary);
+
argBuilder.add("-d").addPath(j2ObjcSource.getObjcFilePath());
// In J2ObjC, the jars you pass as dependencies must be precisely the same as the
@@ -228,11 +286,32 @@
.addOutputs(j2ObjcSource.getObjcSrcs())
.addOutputs(j2ObjcSource.getObjcHdrs())
.addOutput(outputHeaderMappingFile)
- .addOutput(outputDependencyMappingFile);
+ .addOutput(outputDependencyMappingFile)
+ .addOutput(archiveSourceMappingFile);
ruleContext.registerAction(builder.build(ruleContext));
}
+ private J2ObjcMappingFileProvider depJ2ObjcMappingFileProvider(RuleContext ruleContext) {
+ NestedSetBuilder<Artifact> depsHeaderMappingsBuilder = NestedSetBuilder.stableOrder();
+ NestedSetBuilder<Artifact> depsClassMappingsBuilder = NestedSetBuilder.stableOrder();
+ NestedSetBuilder<Artifact> depsDependencyMappingsBuilder = NestedSetBuilder.stableOrder();
+ NestedSetBuilder<Artifact> depsArchiveSourceMappingsBuilder = NestedSetBuilder.stableOrder();
+
+ for (J2ObjcMappingFileProvider mapping : getJ2ObjCMappings(ruleContext)) {
+ depsHeaderMappingsBuilder.addTransitive(mapping.getHeaderMappingFiles());
+ depsClassMappingsBuilder.addTransitive(mapping.getClassMappingFiles());
+ depsDependencyMappingsBuilder.addTransitive(mapping.getDependencyMappingFiles());
+ depsArchiveSourceMappingsBuilder.addTransitive(mapping.getArchiveSourceMappingFiles());
+ }
+
+ return new J2ObjcMappingFileProvider(
+ depsHeaderMappingsBuilder.build(),
+ depsClassMappingsBuilder.build(),
+ depsDependencyMappingsBuilder.build(),
+ depsArchiveSourceMappingsBuilder.build());
+ }
+
private static List<? extends J2ObjcMappingFileProvider> getJ2ObjCMappings(RuleContext context) {
ImmutableList.Builder<J2ObjcMappingFileProvider> mappingFileProviderBuilder =
new ImmutableList.Builder<>();
@@ -269,6 +348,11 @@
return ObjcRuleClasses.artifactByAppendingToBaseName(ruleContext, ".param.j2objc");
}
+ private static Artifact j2ObjcOutputArchiveSourceMappingFile(RuleContext ruleContext) {
+ return ObjcRuleClasses.artifactByAppendingToBaseName(
+ ruleContext, ".archive_source_mapping.j2objc");
+ }
+
private J2ObjcSource buildJ2ObjcSource(RuleContext ruleContext,
Iterable<Artifact> javaInputSourceFiles) {
PathFragment objcFileRootRelativePath = ruleContext.getUniqueDirectory("_j2objc");
@@ -303,4 +387,72 @@
return objcSources.build();
}
+
+ /**
+ * Sets up and returns an {@link ObjcCommon} object containing the J2ObjC-translated code.
+ *
+ */
+ static ObjcCommon common(RuleContext ruleContext, Iterable<Artifact> transpiledSources,
+ Iterable<Artifact> transpiledHeaders, Iterable<PathFragment> headerSearchPaths,
+ Iterable<Attribute> dependentAttributes) {
+ ObjcCommon.Builder builder = new ObjcCommon.Builder(ruleContext);
+ IntermediateArtifacts intermediateArtifacts =
+ ObjcRuleClasses.j2objcIntermediateArtifacts(ruleContext);
+
+ if (!Iterables.isEmpty(transpiledSources) || !Iterables.isEmpty(transpiledHeaders)) {
+ CompilationArtifacts compilationArtifacts = new CompilationArtifacts.Builder()
+ .addNonArcSrcs(transpiledSources)
+ .setIntermediateArtifacts(intermediateArtifacts)
+ .setPchFile(Optional.<Artifact>absent())
+ .addAdditionalHdrs(transpiledHeaders)
+ .build();
+ builder.setCompilationArtifacts(compilationArtifacts);
+ }
+
+ for (Attribute dependentAttribute : dependentAttributes) {
+ if (ruleContext.getAttribute(dependentAttribute.getName()) != null) {
+ builder.addDepObjcProviders(ruleContext.getPrerequisites(
+ dependentAttribute.getName(),
+ dependentAttribute.getAccessMode(),
+ ObjcProvider.class));
+ }
+ }
+
+ return builder
+ .addUserHeaderSearchPaths(headerSearchPaths)
+ .setIntermediateArtifacts(intermediateArtifacts)
+ .setHasModuleMap()
+ .build();
+ }
+
+ /**
+ * Sets up and returns an {@link XcodeProvider} object containing the J2ObjC-translated code.
+ *
+ */
+ static XcodeProvider xcodeProvider(RuleContext ruleContext, ObjcCommon common,
+ Iterable<Artifact> transpiledHeaders, Iterable<PathFragment> headerSearchPaths,
+ Iterable<Attribute> dependentAttributes) {
+ XcodeProvider.Builder xcodeProviderBuilder = new XcodeProvider.Builder();
+ XcodeSupport xcodeSupport = new XcodeSupport(ruleContext);
+ xcodeSupport.addXcodeSettings(xcodeProviderBuilder, common.getObjcProvider(), LIBRARY_STATIC);
+
+ for (Attribute dependentAttribute : dependentAttributes) {
+ if (ruleContext.getAttribute(dependentAttribute.getName()) != null) {
+ xcodeSupport.addDependencies(xcodeProviderBuilder, dependentAttribute);
+ }
+ }
+
+ if (!Iterables.isEmpty(transpiledHeaders)) {
+ xcodeProviderBuilder
+ .addUserHeaderSearchPaths(headerSearchPaths)
+ .addCopts(ruleContext.getFragment(ObjcConfiguration.class).getCopts())
+ .addHeaders(transpiledHeaders);
+ }
+
+ if (common.getCompilationArtifacts().isPresent()) {
+ xcodeProviderBuilder.setCompilationArtifacts(common.getCompilationArtifacts().get());
+ }
+
+ return xcodeProviderBuilder.build();
+ }
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcCommandLineOptions.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcCommandLineOptions.java
similarity index 97%
rename from src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcCommandLineOptions.java
rename to src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcCommandLineOptions.java
index 9b872aa..64b9069 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcCommandLineOptions.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcCommandLineOptions.java
@@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-package com.google.devtools.build.lib.rules.java;
+package com.google.devtools.build.lib.rules.objc;
import com.google.common.collect.Multimap;
import com.google.devtools.build.lib.analysis.config.FragmentOptions;
diff --git a/src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcConfiguration.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcConfiguration.java
similarity index 97%
rename from src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcConfiguration.java
rename to src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcConfiguration.java
index d71d9c0..8c8ae80 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/java/J2ObjcConfiguration.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcConfiguration.java
@@ -12,7 +12,7 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-package com.google.devtools.build.lib.rules.java;
+package com.google.devtools.build.lib.rules.objc;
import com.google.common.base.Joiner;
import com.google.common.collect.ImmutableSet;
@@ -79,7 +79,7 @@
}
}
- private final ImmutableSet<String> translationFlags;
+ private final Set<String> translationFlags;
private final boolean removeDeadCode;
J2ObjcConfiguration(J2ObjcCommandLineOptions j2ObjcOptions) {
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcEntryClassProvider.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcEntryClassProvider.java
new file mode 100644
index 0000000..6bbc6a5
--- /dev/null
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcEntryClassProvider.java
@@ -0,0 +1,124 @@
+// Copyright 2014 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.
+
+package com.google.devtools.build.lib.rules.objc;
+
+import com.google.devtools.build.lib.analysis.RuleConfiguredTarget.Mode;
+import com.google.devtools.build.lib.analysis.RuleContext;
+import com.google.devtools.build.lib.analysis.TransitiveInfoProvider;
+import com.google.devtools.build.lib.collect.nestedset.NestedSet;
+import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
+import com.google.devtools.build.lib.concurrent.ThreadSafety.Immutable;
+import com.google.devtools.build.lib.packages.BuildType;
+
+/**
+ * This provider is exported by j2objc_library to export entry class information necessary for
+ * J2ObjC dead code removal performed at the binary level in ObjC rules.
+ */
+@Immutable
+public final class J2ObjcEntryClassProvider implements TransitiveInfoProvider {
+ private final NestedSet<String> entryClasses;
+
+ /**
+ * A builder for J2ObjcEntryClassProvider.
+ */
+ public static class Builder {
+ private final NestedSetBuilder<String> entryClassesBuilder = NestedSetBuilder.stableOrder();
+
+ /**
+ * Constructs a new, empty J2ObjcEntryClassProvider builder.
+ */
+ public Builder() {}
+
+ /**
+ * Transitively adds the given {@link J2ObjcEntryClassProvider}
+ * and all its properties to this builder.
+ *
+ * @param provider the J2ObjcEntryClassProvider to add
+ * @return this builder
+ */
+ public Builder addTransitive(J2ObjcEntryClassProvider provider) {
+ entryClassesBuilder.addTransitive(provider.getEntryClasses());
+ return this;
+ }
+
+ /**
+ * Transitively adds all the J2ObjcEntryClassProviders and all their properties
+ * that can be reached through the "deps" attribute.
+ *
+ * @param ruleContext the rule context
+ * @return this builder
+ */
+ public Builder addTransitive(RuleContext ruleContext) {
+ if (ruleContext.attributes().has("deps", BuildType.LABEL_LIST)) {
+ for (J2ObjcEntryClassProvider provider :
+ ruleContext.getPrerequisites("deps", Mode.TARGET, J2ObjcEntryClassProvider.class)) {
+ addTransitive(provider);
+ }
+ }
+
+ return this;
+ }
+
+ /**
+ * Adds the given entry classes to this builder. See {@link #getEntryClasses()}.
+ *
+ * @param entryClasses the entry classes to add
+ * @return this builder
+ */
+ public Builder addEntryClasses(Iterable<String> entryClasses) {
+ entryClassesBuilder.addAll(entryClasses);
+ return this;
+ }
+
+ /**
+ * Builds a J2ObjcEntryClassProvider from the information in this builder.
+ *
+ * @return the J2ObjcEntryClassProvider to be built
+ */
+ public J2ObjcEntryClassProvider build() {
+ return new J2ObjcEntryClassProvider(entryClassesBuilder.build());
+ }
+ }
+
+ /**
+ * Constructs a new J2ObjcEntryClassProvider that contains all the information
+ * that can be transitively reached through the "deps" attribute of the given rule context.
+ *
+ * @param ruleContext the rule context in which to look for deps
+ */
+ public static J2ObjcEntryClassProvider buildFrom(RuleContext ruleContext) {
+ return new Builder().addTransitive(ruleContext).build();
+ }
+
+ /**
+ * Constructs a {@link J2ObjcEntryClassProvider} to supply J2ObjC-translated ObjC sources to
+ * objc_binary for compilation and linking.
+ *
+ * @param entryClasses a set of names of Java classes to used as entry point for J2ObjC dead code
+ * analysis. The Java class names should be in canonical format as defined by the Java
+ * Language Specification.
+ */
+ private J2ObjcEntryClassProvider(NestedSet<String> entryClasses) {
+ this.entryClasses = entryClasses;
+ }
+
+ /**
+ * Returns a set of entry classes specified on attribute entry_classes of j2objc_library targets
+ * transitively.
+ */
+ public NestedSet<String> getEntryClasses() {
+ return entryClasses;
+ }
+}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibrary.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibrary.java
index e072c0d..fd37871 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibrary.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibrary.java
@@ -27,8 +27,6 @@
import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
import com.google.devtools.build.lib.packages.BuildType;
import com.google.devtools.build.lib.rules.RuleConfiguredTargetFactory;
-import com.google.devtools.build.lib.rules.cpp.CppModuleMap;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.syntax.Type;
import com.google.devtools.build.lib.vfs.PathFragment;
@@ -45,6 +43,11 @@
"Entry classes must be specified when flag --compilationMode=opt is on in order to"
+ " perform J2ObjC dead code stripping.";
+ public static final List<String> J2OBJC_SUPPORTED_RULES = ImmutableList.of(
+ "java_import",
+ "java_library",
+ "proto_library");
+
@Override
public ConfiguredTarget create(RuleContext ruleContext) throws InterruptedException {
checkAttributes(ruleContext);
@@ -53,51 +56,28 @@
return null;
}
- J2ObjcSrcsProvider j2ObjcSrcsProvider = new J2ObjcSrcsProvider.Builder()
- .addTransitiveJ2ObjcSrcs(ruleContext)
+ J2ObjcEntryClassProvider j2ObjcEntryClassProvider = new J2ObjcEntryClassProvider.Builder()
+ .addTransitive(ruleContext)
.addEntryClasses(ruleContext.attributes().get("entry_classes", Type.STRING_LIST))
.build();
ObjcProvider.Builder objcProviderBuilder =
new ObjcProvider.Builder()
- .addJ2ObjcTransitiveAndPropagate(
- ruleContext.getPrerequisite("$jre_emul_lib", Mode.TARGET, ObjcProvider.class))
- .addJ2ObjcTransitiveAndPropagate(
+ .addTransitiveAndPropagate(
ruleContext.getPrerequisites("deps", Mode.TARGET, ObjcProvider.class));
XcodeProvider.Builder xcodeProviderBuilder = new XcodeProvider.Builder();
XcodeSupport xcodeSupport =
new XcodeSupport(ruleContext)
- .addDependencies(xcodeProviderBuilder, new Attribute("$jre_emul_lib", Mode.TARGET))
.addDependencies(xcodeProviderBuilder, new Attribute("deps", Mode.TARGET));
- if (j2ObjcSrcsProvider.hasProtos()) {
- // Public J2 in Bazel provides no protobuf_lib, and if OSS users try to sneakily use
- // undocumented functionality to reach here, the below code will error.
- objcProviderBuilder.addJ2ObjcTransitiveAndPropagate(
- ruleContext.getPrerequisite("$protobuf_lib", Mode.TARGET, ObjcProvider.class));
- xcodeSupport.addDependencies(
- xcodeProviderBuilder, new Attribute("$protobuf_lib", Mode.TARGET));
- }
-
- for (J2ObjcSource j2objcSource : j2ObjcSrcsProvider.getSrcs()) {
- objcProviderBuilder.addJ2ObjcAll(ObjcProvider.HEADER, j2objcSource.getObjcHdrs());
- objcProviderBuilder.addJ2ObjcAll(ObjcProvider.INCLUDE, j2objcSource.getHeaderSearchPaths());
- xcodeProviderBuilder.addHeaders(j2objcSource.getObjcHdrs());
- xcodeProviderBuilder.addUserHeaderSearchPaths(j2objcSource.getHeaderSearchPaths());
- }
-
- if (ObjcRuleClasses.objcConfiguration(ruleContext).moduleMapsEnabled()) {
- configureModuleMap(ruleContext, objcProviderBuilder, j2ObjcSrcsProvider);
- }
-
ObjcProvider objcProvider = objcProviderBuilder.build();
xcodeSupport.addXcodeSettings(xcodeProviderBuilder, objcProvider, LIBRARY_STATIC);
return new RuleConfiguredTargetBuilder(ruleContext)
.setFilesToBuild(NestedSetBuilder.<Artifact>emptySet(STABLE_ORDER))
.add(RunfilesProvider.class, RunfilesProvider.EMPTY)
- .addProvider(J2ObjcSrcsProvider.class, j2ObjcSrcsProvider)
+ .addProvider(J2ObjcEntryClassProvider.class, j2ObjcEntryClassProvider)
.addProvider(
J2ObjcMappingFileProvider.class, ObjcRuleClasses.j2ObjcMappingFileProvider(ruleContext))
.addProvider(ObjcProvider.class, objcProvider)
@@ -129,21 +109,6 @@
return headerSearchPaths.build();
}
- /**
- * Configures a module map for all the sources in {@code j2ObjcSrcsProvider}, registering
- * an action to generate the module map and exposing that module map through {@code objcProvider}.
- */
- private void configureModuleMap(
- RuleContext ruleContext,
- ObjcProvider.Builder objcProvider,
- J2ObjcSrcsProvider j2ObjcSrcsProvider) {
- new CompilationSupport(ruleContext).registerJ2ObjcGenerateModuleMapAction(j2ObjcSrcsProvider);
-
- CppModuleMap moduleMap = ObjcRuleClasses.intermediateArtifacts(ruleContext).moduleMap();
- objcProvider.add(ObjcProvider.MODULE_MAP, moduleMap.getArtifact());
- objcProvider.add(ObjcProvider.TOP_LEVEL_MODULE_MAP, moduleMap);
- }
-
private static void checkAttributes(RuleContext ruleContext) {
checkAttributes(ruleContext, "deps");
checkAttributes(ruleContext, "exports");
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibraryBaseRule.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibraryBaseRule.java
index 2da4068..d8a860d 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibraryBaseRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcLibraryBaseRule.java
@@ -15,7 +15,6 @@
package com.google.devtools.build.lib.rules.objc;
import static com.google.devtools.build.lib.packages.Attribute.attr;
-import static com.google.devtools.build.lib.packages.BuildType.LABEL;
import static com.google.devtools.build.lib.syntax.Type.STRING_LIST;
import com.google.devtools.build.lib.analysis.BaseRuleClasses;
@@ -44,12 +43,6 @@
Unused classes will then be removed from the final ObjC app bundle.
<!-- #END_BLAZE_RULE.ATTRIBUTE -->*/
.add(attr("entry_classes", STRING_LIST))
- .add(attr("$jre_emul_lib", LABEL)
- .value(env.getLabel(
- env.getToolsRepository() + "//third_party/java/j2objc:jre_emul_lib")))
- .add(attr("$protobuf_lib", LABEL)
- .value(env.getLabel(
- env.getToolsRepository() + "//third_party/java/j2objc:proto_runtime")))
.build();
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcMappingFileProvider.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcMappingFileProvider.java
index b80c8ec..e785130 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcMappingFileProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcMappingFileProvider.java
@@ -30,6 +30,7 @@
private final NestedSet<Artifact> headerMappingFiles;
private final NestedSet<Artifact> classMappingFiles;
private final NestedSet<Artifact> dependencyMappingFiles;
+ private final NestedSet<Artifact> archiveSourceMappingFiles;
/**
* Constructs a {@link J2ObjcMappingFileProvider} with mapping files to export mappings required
@@ -43,12 +44,16 @@
* @param dependencyMappingFiles a nested set of dependency mapping files which map translated
* ObjC files to their translated direct dependency files. Used to support J2ObjC dead code
* analysis and removal.
+ * @param archiveSourceMappingFiles a nested set of files containing mappings between J2ObjC
+ * static library archives and their associated J2ObjC-translated source files.
*/
public J2ObjcMappingFileProvider(NestedSet<Artifact> headerMappingFiles,
- NestedSet<Artifact> classMappingFiles, NestedSet<Artifact> dependencyMappingFiles) {
+ NestedSet<Artifact> classMappingFiles, NestedSet<Artifact> dependencyMappingFiles,
+ NestedSet<Artifact> archiveSourceMappingFiles) {
this.headerMappingFiles = headerMappingFiles;
this.classMappingFiles = classMappingFiles;
this.dependencyMappingFiles = dependencyMappingFiles;
+ this.archiveSourceMappingFiles = archiveSourceMappingFiles;
}
/**
@@ -71,14 +76,24 @@
/**
* Returns the mapping files containing file dependency information among the translated ObjC
- * source files. They are used to strip unused translated files before the compilation and linking
- * actions at binary level.
+ * source files. When flag --j2objc_dead_code_removal is specified, they are used to strip unused
+ * object files inside J2ObjC static libraries before the linking action at binary level.
*/
public NestedSet<Artifact> getDependencyMappingFiles() {
return dependencyMappingFiles;
}
/**
+ * Returns the files containing mappings between J2ObjC static library archives and their
+ * associated J2ObjC-translated source files. When flag --j2objc_dead_code_removal is specified,
+ * they are used to strip unused object files inside J2ObjC static libraries before the linking
+ * action at binary level.
+ */
+ public NestedSet<Artifact> getArchiveSourceMappingFiles() {
+ return archiveSourceMappingFiles;
+ }
+
+ /**
* A builder for this provider that is optimized for collection information from transitive
* dependencies.
*/
@@ -86,18 +101,24 @@
private final NestedSetBuilder<Artifact> headerMappingFiles = NestedSetBuilder.stableOrder();
private final NestedSetBuilder<Artifact> classMappingFiles = NestedSetBuilder.stableOrder();
private final NestedSetBuilder<Artifact> depEntryFiles = NestedSetBuilder.stableOrder();
+ private final NestedSetBuilder<Artifact> archiveSourceMappingFiles =
+ NestedSetBuilder.stableOrder();
public Builder addTransitive(J2ObjcMappingFileProvider provider) {
headerMappingFiles.addTransitive(provider.getHeaderMappingFiles());
classMappingFiles.addTransitive(provider.getClassMappingFiles());
depEntryFiles.addTransitive(provider.getDependencyMappingFiles());
+ archiveSourceMappingFiles.addTransitive(provider.getArchiveSourceMappingFiles());
return this;
}
public J2ObjcMappingFileProvider build() {
return new J2ObjcMappingFileProvider(
- headerMappingFiles.build(), classMappingFiles.build(), depEntryFiles.build());
+ headerMappingFiles.build(),
+ classMappingFiles.build(),
+ depEntryFiles.build(),
+ archiveSourceMappingFiles.build());
}
}
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcSrcsProvider.java b/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcSrcsProvider.java
deleted file mode 100644
index 4f54079..0000000
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/J2ObjcSrcsProvider.java
+++ /dev/null
@@ -1,172 +0,0 @@
-// Copyright 2014 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.
-
-package com.google.devtools.build.lib.rules.objc;
-
-import com.google.devtools.build.lib.analysis.RuleConfiguredTarget.Mode;
-import com.google.devtools.build.lib.analysis.RuleContext;
-import com.google.devtools.build.lib.analysis.TransitiveInfoProvider;
-import com.google.devtools.build.lib.collect.nestedset.NestedSet;
-import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
-import com.google.devtools.build.lib.concurrent.ThreadSafety.Immutable;
-import com.google.devtools.build.lib.packages.BuildType;
-import com.google.devtools.build.lib.rules.objc.J2ObjcSource.SourceType;
-
-/**
- * This provider is exported by java_library rules to supply J2ObjC-translated ObjC sources to
- * objc_binary for compilation and linking.
- */
-@Immutable
-public final class J2ObjcSrcsProvider implements TransitiveInfoProvider {
- private final NestedSet<J2ObjcSource> srcs;
- private final NestedSet<String> entryClasses;
- private final boolean hasProtos;
-
- /**
- * A builder for J2ObjCSrcsProvider.
- */
- public static class Builder {
- private final NestedSetBuilder<J2ObjcSource> srcsBuilder = NestedSetBuilder.stableOrder();
- private final NestedSetBuilder<String> entryClassesBuilder = NestedSetBuilder.stableOrder();
- private boolean hasProtos = false;
-
- /**
- * Constructs a new, empty J2ObjCSrcsProvider builder.
- */
- public Builder() {}
-
- /**
- * Transitively adds the given {@link J2ObjcSrcsProvider}
- * and all its properties to this builder.
- *
- * @param provider the J2ObjcSrcsProvider to add
- * @return this builder
- */
- public Builder addTransitive(J2ObjcSrcsProvider provider) {
- srcsBuilder.addTransitive(provider.getSrcs());
- entryClassesBuilder.addTransitive(provider.getEntryClasses());
- hasProtos |= provider.hasProtos();
- return this;
- }
-
- /**
- * Transitively adds all the J2ObjcSrcsProviders and all their properties
- * that can be reached through the "deps", "exports" and "runtime_deps" attributes.
- *
- * @param ruleContext the rule context
- * @return this builder
- */
- public Builder addTransitiveJ2ObjcSrcs(RuleContext ruleContext) {
- return addTransitiveJ2ObjcSrcs(ruleContext, "deps")
- .addTransitiveJ2ObjcSrcs(ruleContext, "exports")
- .addTransitiveJ2ObjcSrcs(ruleContext, "runtime_deps");
- }
-
- /**
- * Transitively adds the J2ObjCSrcsProviders of a given attribute to this Builder.
- *
- * @param ruleContext the rule context
- * @param attribute the attribute to which to add sources
- * @return this builder
- */
- public Builder addTransitiveJ2ObjcSrcs(RuleContext ruleContext, String attribute) {
- if (ruleContext.attributes().has(attribute, BuildType.LABEL_LIST)) {
- for (J2ObjcSrcsProvider provider :
- ruleContext.getPrerequisites(attribute, Mode.TARGET, J2ObjcSrcsProvider.class)) {
- addTransitive(provider);
- }
- }
-
- return this;
- }
-
- /**
- * Adds the given {@link J2ObjcSource} to this builder.
- *
- * @param source the source to add
- * @return this builder
- */
- public Builder addSource(J2ObjcSource source) {
- srcsBuilder.add(source);
- hasProtos |= source.getSourceType() == SourceType.PROTO;
- return this;
- }
-
- /**
- * Adds the given entry classes to this builder. See {@link #getEntryClasses()}.
- *
- * @param entryClasses the entry classes to add
- * @return this builder
- */
- public Builder addEntryClasses(Iterable<String> entryClasses) {
- entryClassesBuilder.addAll(entryClasses);
- return this;
- }
-
- /**
- * Builds a J2ObjCSrcsProvider from the information in this builder.
- *
- * @return the J2ObjCSrcsProvider to be built
- */
- public J2ObjcSrcsProvider build() {
- return new J2ObjcSrcsProvider(srcsBuilder.build(), entryClassesBuilder.build(), hasProtos);
- }
- }
-
- /**
- * Constructs a new J2ObjCSrcsProvider that contains all the information
- * that can be transitively reached through the "deps" attribute of the given rule context.
- *
- * @param ruleContext the rule context in which to look for deps
- */
- public static J2ObjcSrcsProvider buildFrom(RuleContext ruleContext) {
- return new Builder().addTransitiveJ2ObjcSrcs(ruleContext).build();
- }
-
- /**
- * Constructs a {@link J2ObjcSrcsProvider} to supply J2ObjC-translated ObjC sources to
- * objc_binary for compilation and linking.
- *
- * @param srcs a nested set of {@link J2ObjcSource}s containing translated source files
- * @param entryClasses a set of names of Java classes to used as entry point for J2ObjC dead code
- * analysis. The Java class names should be in canonical format as defined by the Java
- * Language Specification.
- * @param hasProtos whether the translated files in this provider have J2ObjC proto files
- */
- private J2ObjcSrcsProvider(NestedSet<J2ObjcSource> srcs, NestedSet<String> entryClasses,
- boolean hasProtos) {
- this.srcs = srcs;
- this.entryClasses = entryClasses;
- this.hasProtos = hasProtos;
- }
-
- public NestedSet<J2ObjcSource> getSrcs() {
- return srcs;
- }
-
- /**
- * Returns a set of entry classes specified on attribute entry_classes of j2objc_library targets
- * transitively.
- */
- public NestedSet<String> getEntryClasses() {
- return entryClasses;
- }
-
- /**
- * Returns whether the translated source files in the provider has proto files.
- */
- public boolean hasProtos() {
- return hasProtos;
- }
-}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcBinaryRule.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcBinaryRule.java
index d8fde99..34b5b8e 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcBinaryRule.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcBinaryRule.java
@@ -26,7 +26,6 @@
import com.google.devtools.build.lib.packages.RuleClass;
import com.google.devtools.build.lib.packages.RuleClass.Builder;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
/**
* Rule definition for objc_binary.
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcCommon.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcCommon.java
index 4b8412e..abf35a1 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcCommon.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcCommon.java
@@ -33,6 +33,7 @@
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.IMPORTED_LIBRARY;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.INCLUDE;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.INCLUDE_SYSTEM;
+import static com.google.devtools.build.lib.rules.objc.ObjcProvider.J2OBJC_LIBRARY;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.LIBRARY;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.LINKED_BINARY;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.LINKOPT;
@@ -575,6 +576,11 @@
.addAll(LIBRARY, artifacts.getArchive().asSet())
.addAll(SOURCE, allSources);
+ if (artifacts.getArchive().isPresent()
+ && J2ObjcLibrary.J2OBJC_SUPPORTED_RULES.contains(context.getRule().getRuleClass())) {
+ objcProvider.addAll(J2OBJC_LIBRARY, artifacts.getArchive().asSet());
+ }
+
boolean usesCpp = false;
boolean usesSwift = false;
for (Artifact sourceFile :
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcLibrary.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcLibrary.java
index 34a6305..6c9d26c 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcLibrary.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcLibrary.java
@@ -41,21 +41,6 @@
public class ObjcLibrary implements RuleConfiguredTargetFactory {
/**
- * An {@link IterableWrapper} containing extra library {@link Artifact}s to be linked into the
- * final ObjC application bundle.
- */
- static final class ExtraImportLibraries extends IterableWrapper<Artifact> {
-
- ExtraImportLibraries(Artifact... extraImportLibraries) {
- super(extraImportLibraries);
- }
-
- ExtraImportLibraries(Iterable<Artifact> extraImportLibraries) {
- super(extraImportLibraries);
- }
- }
-
- /**
* A {@link CcLinkParamsStore} to be propagated to dependent cc_{library, binary} targets.
*/
private static class ObjcLibraryCcLinkParamsStore extends CcLinkParamsStore {
@@ -87,8 +72,7 @@
* should inherit from {@link ObjcLibraryRule}..
*/
static ObjcCommon common(RuleContext ruleContext, Iterable<SdkFramework> extraSdkFrameworks,
- boolean alwayslink, ExtraImportLibraries extraImportLibraries,
- Iterable<ObjcProvider> extraDepObjcProviders) {
+ boolean alwayslink, Iterable<ObjcProvider> extraDepObjcProviders) {
CompilationArtifacts compilationArtifacts =
CompilationSupport.compilationArtifacts(ruleContext);
@@ -109,7 +93,6 @@
.setIntermediateArtifacts(ObjcRuleClasses.intermediateArtifacts(ruleContext))
.setAlwayslink(alwayslink)
.setHasModuleMap()
- .addExtraImportLibraries(extraImportLibraries)
.addDepObjcProviders(extraDepObjcProviders)
.build();
}
@@ -121,7 +104,6 @@
ruleContext,
ImmutableList.<SdkFramework>of(),
ruleContext.attributes().get("alwayslink", Type.BOOLEAN),
- new ExtraImportLibraries(),
ImmutableList.<ObjcProvider>of());
XcodeProvider.Builder xcodeProviderBuilder = new XcodeProvider.Builder();
@@ -150,7 +132,8 @@
return ObjcRuleClasses.ruleConfiguredTarget(ruleContext, filesToBuild.build())
.addProvider(XcodeProvider.class, xcodeProviderBuilder.build())
.addProvider(ObjcProvider.class, common.getObjcProvider())
- .addProvider(J2ObjcSrcsProvider.class, J2ObjcSrcsProvider.buildFrom(ruleContext))
+ .addProvider(
+ J2ObjcEntryClassProvider.class, J2ObjcEntryClassProvider.buildFrom(ruleContext))
.addProvider(
J2ObjcMappingFileProvider.class, ObjcRuleClasses.j2ObjcMappingFileProvider(ruleContext))
.addProvider(
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
index d257330..ee95b6e 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcProvider.java
@@ -213,6 +213,11 @@
public static final Key<String> LINKOPT = new Key<>(LINK_ORDER);
/**
+ * Static libraries that are built from J2ObjC-translated Java code.
+ */
+ public static final Key<Artifact> J2OBJC_LIBRARY = new Key<>(LINK_ORDER);
+
+ /**
* Flags that apply to a transitive build dependency tree. Each item in the enum corresponds to a
* flag. If the item is included in the key {@link #FLAG}, then the flag is considered set.
*/
@@ -241,16 +246,11 @@
// Items which should be passed to direct dependers, but not transitive dependers.
private final ImmutableMap<Key<?>, NestedSet<?>> nonPropagatedItems;
- // Items which are relevent only for J2ObjC-translated sources.
- private final ImmutableMap<Key<?>, NestedSet<?>> j2ObjcOnlyItems;
-
private ObjcProvider(
ImmutableMap<Key<?>, NestedSet<?>> items,
- ImmutableMap<Key<?>, NestedSet<?>> nonPropagatedItems,
- ImmutableMap<Key<?>, NestedSet<?>> j2ObjcOnlyItems) {
+ ImmutableMap<Key<?>, NestedSet<?>> nonPropagatedItems) {
this.items = Preconditions.checkNotNull(items);
this.nonPropagatedItems = Preconditions.checkNotNull(nonPropagatedItems);
- this.j2ObjcOnlyItems = Preconditions.checkNotNull(j2ObjcOnlyItems);
}
/**
@@ -285,25 +285,12 @@
}
/**
- * Returns a corresponding provider that contains only information relevent for J2ObjC-translated
- * code. This trimmed provider offers a view that is used for compilation actions of
- * J2ObjC-translated sources to avoid pulling in unnecessary dependent information from the rest
- * of the transitive closure.
- */
- // TODO(rduan): Roll this back once J2ObjC compilation is moved to the edges in the dep graph.
- public ObjcProvider toJ2ObjcOnlyProvider() {
- return new ObjcProvider(j2ObjcOnlyItems, ImmutableMap.<Key<?>, NestedSet<?>>of(),
- j2ObjcOnlyItems);
- }
-
- /**
* A builder for this context with an API that is optimized for collecting information from
* several transitive dependencies.
*/
public static final class Builder {
private final Map<Key<?>, NestedSetBuilder<?>> items = new HashMap<>();
private final Map<Key<?>, NestedSetBuilder<?>> nonPropagatedItems = new HashMap<>();
- private final Map<Key<?>, NestedSetBuilder<?>> j2ObjcPropagatedItems = new HashMap<>();
private static void maybeAddEmptyBuilder(Map<Key<?>, NestedSetBuilder<?>> set, Key<?> key) {
if (!set.containsKey(key)) {
@@ -341,25 +328,6 @@
for (Map.Entry<Key<?>, NestedSet<?>> typeEntry : provider.items.entrySet()) {
uncheckedAddTransitive(typeEntry.getKey(), typeEntry.getValue(), this.items);
}
- for (Map.Entry<Key<?>, NestedSet<?>> typeEntry : provider.j2ObjcOnlyItems.entrySet()) {
- uncheckedAddTransitive(typeEntry.getKey(), typeEntry.getValue(),
- this.j2ObjcPropagatedItems);
- }
- return this;
- }
-
- /**
- * Add all elements from provider relevent to J2ObjC (providers directly exporting
- * J2ObjC-translated code, J2ObjC runtime deps, etc.), and propagate them to any (transitive)
- * dependers on this ObjcProvider.
- */
- // TODO(rduan): Roll this back once J2ObjC compilation is moved to the edges in the dep graph.
- public Builder addJ2ObjcTransitiveAndPropagate(ObjcProvider provider) {
- addTransitiveAndPropagate(provider);
- for (Map.Entry<Key<?>, NestedSet<?>> typeEntry : provider.items.entrySet()) {
- uncheckedAddTransitive(typeEntry.getKey(), typeEntry.getValue(),
- this.j2ObjcPropagatedItems);
- }
return this;
}
@@ -384,19 +352,6 @@
}
/**
- * Add all elements from providers relevent to J2ObjC (providers directly exporting
- * J2ObjC-translated code, J2ObjC runtime deps, etc.), and propagate them to any (transitive)
- * dependers on this ObjcProvider.
- */
- // TODO(rduan): Roll this back once J2ObjC compilation is moved to the edges in the dep graph.
- public Builder addJ2ObjcTransitiveAndPropagate(Iterable<ObjcProvider> providers) {
- for (ObjcProvider provider : providers) {
- addJ2ObjcTransitiveAndPropagate(provider);
- }
- return this;
- }
-
- /**
* Add elements from providers, but don't propagate them to any dependers on this ObjcProvider.
* These elements will be exposed to {@link #get(Key)} calls, but not to any ObjcProviders
* which add this provider to themselves.
@@ -419,17 +374,6 @@
}
/**
- * Add element relevent to J2ObjC (elements containing information for J2ObjC-translated code),
- * and propagate it to any (transitive) dependers on this ObjcProvider.
- */
- // TODO(rduan): Roll this back once J2ObjC compilation is moved to the edges in the dep graph.
- public <E> Builder addJ2Objc(Key<E> key, E toAdd) {
- uncheckedAddAll(key, ImmutableList.of(toAdd), this.items);
- uncheckedAddAll(key, ImmutableList.of(toAdd), this.j2ObjcPropagatedItems);
- return this;
- }
-
- /**
* Add elements in toAdd, and propagate them to any (transitive) dependers on this ObjcProvider.
*/
public <E> Builder addAll(Key<E> key, Iterable<? extends E> toAdd) {
@@ -437,17 +381,6 @@
return this;
}
- /**
- * Add elements relevent to J2ObjC (elements containing information for J2ObjC-translated code),
- * and propagate them to any (transitive) dependers on this ObjcProvider.
- */
- // TODO(rduan): Roll this back once J2ObjC compilation is moved to the edges in the dep graph.
- public <E> Builder addJ2ObjcAll(Key<E> key, Iterable<? extends E> toAdd) {
- uncheckedAddAll(key, toAdd, this.items);
- uncheckedAddAll(key, toAdd, this.j2ObjcPropagatedItems);
- return this;
- }
-
public ObjcProvider build() {
ImmutableMap.Builder<Key<?>, NestedSet<?>> propagated = new ImmutableMap.Builder<>();
for (Map.Entry<Key<?>, NestedSetBuilder<?>> typeEntry : items.entrySet()) {
@@ -457,11 +390,7 @@
for (Map.Entry<Key<?>, NestedSetBuilder<?>> typeEntry : nonPropagatedItems.entrySet()) {
nonPropagated.put(typeEntry.getKey(), typeEntry.getValue().build());
}
- ImmutableMap.Builder<Key<?>, NestedSet<?>> j2ObjcPropagated = new ImmutableMap.Builder<>();
- for (Map.Entry<Key<?>, NestedSetBuilder<?>> typeEntry : j2ObjcPropagatedItems.entrySet()) {
- j2ObjcPropagated.put(typeEntry.getKey(), typeEntry.getValue().build());
- }
- return new ObjcProvider(propagated.build(), nonPropagated.build(), j2ObjcPropagated.build());
+ return new ObjcProvider(propagated.build(), nonPropagated.build());
}
}
}
diff --git a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcRuleClasses.java b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcRuleClasses.java
index 9849565..65b98ca 100644
--- a/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcRuleClasses.java
+++ b/src/main/java/com/google/devtools/build/lib/rules/objc/ObjcRuleClasses.java
@@ -81,41 +81,18 @@
/**
* Returns a {@link IntermediateArtifacts} to be used to compile and link the ObjC source files
- * in {@code j2ObjcSource}.
+ * generated by J2ObjC.
*/
- static IntermediateArtifacts j2objcIntermediateArtifacts(RuleContext ruleContext,
- J2ObjcSource j2ObjcSource) {
+ static IntermediateArtifacts j2objcIntermediateArtifacts(RuleContext ruleContext) {
// We need to append "_j2objc" to the name of the generated archive file to distinguish it from
// the C/C++ archive file created by proto_library targets with attribute cc_api_version
// specified.
return new IntermediateArtifacts(
ruleContext,
- j2ObjcSource.getTargetLabel(),
/*archiveFileNameSuffix=*/"_j2objc");
}
/**
- * Returns an {@link Iterable} of {@link Artifact}s containing all the j2objc archives from the
- * transitive closure of the rule through the "deps" attribute. This is useful for ensuring that
- * the j2objc archives are present for linking.
- *
- * @param ruleContext the {@link RuleContext} of the current rule
- * @return an {@link Iterable} of j2objc library archive artifacts.
- */
- static Iterable<Artifact> j2ObjcLibraries(RuleContext ruleContext) {
- ImmutableList.Builder<Artifact> j2objcLibraries = new ImmutableList.Builder<>();
-
- // TODO(bazel-team): Refactor the code to stop flattening the nested set here.
- for (J2ObjcSource j2ObjcSource : J2ObjcSrcsProvider.buildFrom(ruleContext).getSrcs()) {
- if (j2ObjcSource.hasSourceFiles()) {
- j2objcLibraries.add(j2objcIntermediateArtifacts(ruleContext, j2ObjcSource).archive());
- }
- }
-
- return j2objcLibraries.build();
- }
-
- /**
* Returns a {@link J2ObjcMappingFileProvider} containing J2ObjC mapping files from rules
* that can be reached transitively through the "deps" attribute.
*
@@ -763,6 +740,8 @@
.singleArtifact()
.value(env.getLabel(
env.getToolsRepository() + "//tools/objc:j2objc_dead_code_pruner")))
+ .add(attr("$dummy_lib", LABEL)
+ .value(env.getLabel("//tools/objc:dummy_lib")))
.build();
}
@Override
diff --git a/src/test/java/com/google/devtools/build/lib/BUILD b/src/test/java/com/google/devtools/build/lib/BUILD
index 62cc9e3..e6b6b93 100644
--- a/src/test/java/com/google/devtools/build/lib/BUILD
+++ b/src/test/java/com/google/devtools/build/lib/BUILD
@@ -397,6 +397,7 @@
"//src/main/java/com/google/devtools/build/lib:util",
"//src/main/java/com/google/devtools/build/lib:vfs",
"//src/main/java/com/google/devtools/build/lib/rules/cpp",
+ "//src/main/java/com/google/devtools/build/lib/rules/objc",
"//src/main/java/com/google/devtools/common/options",
"//src/main/protobuf:extra_actions_base_proto",
"//third_party:guava",
diff --git a/src/test/java/com/google/devtools/build/lib/analysis/config/BuildConfigurationTest.java b/src/test/java/com/google/devtools/build/lib/analysis/config/BuildConfigurationTest.java
index 48bb5cf..4daaa08 100644
--- a/src/test/java/com/google/devtools/build/lib/analysis/config/BuildConfigurationTest.java
+++ b/src/test/java/com/google/devtools/build/lib/analysis/config/BuildConfigurationTest.java
@@ -27,8 +27,8 @@
import com.google.devtools.build.lib.cmdline.Label;
import com.google.devtools.build.lib.rules.cpp.CppConfiguration;
import com.google.devtools.build.lib.rules.cpp.CppOptions;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.java.JavaConfiguration;
+import com.google.devtools.build.lib.rules.objc.J2ObjcConfiguration;
import com.google.devtools.build.lib.testutil.TestConstants;
import com.google.devtools.build.lib.testutil.TestRuleClassProvider;
import com.google.devtools.common.options.Options;
diff --git a/src/test/java/com/google/devtools/build/lib/analysis/mock/BazelAnalysisMock.java b/src/test/java/com/google/devtools/build/lib/analysis/mock/BazelAnalysisMock.java
index c1da7d3..fb6d064 100644
--- a/src/test/java/com/google/devtools/build/lib/analysis/mock/BazelAnalysisMock.java
+++ b/src/test/java/com/google/devtools/build/lib/analysis/mock/BazelAnalysisMock.java
@@ -34,9 +34,9 @@
import com.google.devtools.build.lib.rules.android.AndroidConfiguration;
import com.google.devtools.build.lib.rules.apple.AppleConfiguration;
import com.google.devtools.build.lib.rules.cpp.CppConfigurationLoader;
-import com.google.devtools.build.lib.rules.java.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.java.JavaConfigurationLoader;
import com.google.devtools.build.lib.rules.java.JvmConfigurationLoader;
+import com.google.devtools.build.lib.rules.objc.J2ObjcConfiguration;
import com.google.devtools.build.lib.rules.objc.ObjcConfigurationLoader;
import com.google.devtools.build.lib.rules.python.PythonConfigurationLoader;
import com.google.devtools.build.lib.testutil.TestRuleClassProvider;
diff --git a/tools/objc/BUILD b/tools/objc/BUILD
index b9eb66b..4b6b56c 100644
--- a/tools/objc/BUILD
+++ b/tools/objc/BUILD
@@ -119,3 +119,8 @@
name = "j2objc_dead_code_pruner",
srcs = ["j2objc_dead_code_pruner.py"],
)
+
+objc_library(
+ name = "dummy_lib",
+ srcs = ["dummy.c"],
+)