Skip to content

Commit

Permalink
Sign bundles for device if ios_multi_cpu contains device cpus.
Browse files Browse the repository at this point in the history
Introduces a restriction that prohibits using both simulator and device architectures for ios_multi_cpus in the same build.

--
MOS_MIGRATED_REVID=89597247
  • Loading branch information
aragos authored and hanwen committed Mar 26, 2015
1 parent 1fc10c0 commit e7c06eb
Show file tree
Hide file tree
Showing 10 changed files with 116 additions and 91 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ public final ConfiguredTarget create(RuleContext ruleContext) throws Interrupted
.validateAttributes();

Optional<XcTestAppProvider> xcTestAppProvider;
Optional<RunfilesSupport> maybeRunfilesSupport = Optional.<RunfilesSupport>absent();
Optional<RunfilesSupport> maybeRunfilesSupport = Optional.absent();
switch (hasReleaseBundlingSupport) {
case YES:
// TODO(bazel-team): Remove once all bundle users are migrated to ios_application.
Expand All @@ -100,8 +100,10 @@ public final ConfiguredTarget create(RuleContext ruleContext) throws Interrupted
.addFilesToBuild(filesToBuild)
.validateResources()
.validateAttributes();

ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
xcTestAppProvider = Optional.of(releaseBundlingSupport.xcTestAppProvider());
if (ObjcRuleClasses.objcConfiguration(ruleContext).getPlatform() == Platform.SIMULATOR) {
if (objcConfiguration.getBundlingPlatform() == Platform.SIMULATOR) {
Artifact runnerScript = intermediateArtifacts.runnerScript();
Artifact ipaFile = ruleContext.getImplicitOutputArtifact(ReleaseBundlingSupport.IPA);
releaseBundlingSupport.registerGenerateRunnerScriptAction(runnerScript, ipaFile);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -69,7 +69,7 @@ private Control control(String mergeZipPrefix, Bundling bundling) {
// TODO(bazel-team): Add rule attribute for specifying targeted device family
.setMinimumOsVersion(objcConfiguration.getMinimumOs())
.setSdkVersion(objcConfiguration.getIosSdkVersion())
.setPlatform(objcConfiguration.getPlatform().name())
.setPlatform(objcConfiguration.getBundlingPlatform().name())
.setBundleRoot(bundling.getBundleDir());

for (Artifact mergeZip : bundling.getMergeZips()) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,9 @@

package com.google.devtools.build.lib.rules.objc;

import static com.google.devtools.build.lib.rules.objc.ObjcProvider.ASSET_CATALOG;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.STRINGS;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.XCASSETS_DIR;

import com.google.common.base.Optional;
import com.google.common.base.Verify;
Expand All @@ -23,14 +25,17 @@
import com.google.devtools.build.lib.analysis.FilesToRunProvider;
import com.google.devtools.build.lib.analysis.RuleConfiguredTarget.Mode;
import com.google.devtools.build.lib.analysis.RuleContext;
import com.google.devtools.build.lib.analysis.actions.CommandLine;
import com.google.devtools.build.lib.analysis.actions.CustomCommandLine;
import com.google.devtools.build.lib.analysis.actions.SpawnAction;
import com.google.devtools.build.lib.collect.nestedset.NestedSetBuilder;
import com.google.devtools.build.lib.rules.objc.ObjcActionsBuilder.ExtraActoolArgs;
import com.google.devtools.build.lib.rules.objc.XcodeProvider.Builder;
import com.google.devtools.build.lib.vfs.FileSystemUtils;
import com.google.devtools.build.lib.vfs.PathFragment;

import java.util.HashMap;
import java.util.Locale;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
Expand Down Expand Up @@ -228,7 +233,7 @@ static Iterable<String> commonMomczipArguments(ObjcConfiguration configuration)
return ImmutableList.of(
"-XD_MOMC_SDKROOT=" + IosSdkCommands.sdkDir(configuration),
"-XD_MOMC_IOS_TARGET_VERSION=" + configuration.getMinimumOs(),
"-MOMC_PLATFORMS", configuration.getPlatform().getLowerCaseNameInPlist(),
"-MOMC_PLATFORMS", configuration.getBundlingPlatform().getLowerCaseNameInPlist(),
"-XD_MOMC_TARGET_VERSION=10.6");
}

Expand Down Expand Up @@ -288,18 +293,53 @@ private void registerActoolActionIfNecessary(ObjcProvider objcProvider) {
return;
}

ObjcActionsBuilder actionsBuilder = ObjcRuleClasses.actionsBuilder(ruleContext);

Artifact actoolPartialInfoplist = actoolPartialInfoplist(ruleContext, objcProvider).get();
actionsBuilder.registerActoolzipAction(
new ObjcRuleClasses.Tools(ruleContext),
objcProvider,
actoolzipOutput.get(),
actoolPartialInfoplist,
extraActoolArgs,
targetDeviceFamilies);
Artifact zipOutput = actoolzipOutput.get();

// TODO(bazel-team): Do not use the deploy jar explicitly here. There is currently a bug where
// we cannot .setExecutable({java_binary target}) and set REQUIRES_DARWIN in the execution info.
// Note that below we set the archive root to the empty string. This means that the generated
// zip file will be rooted at the bundle root, and we have to prepend the bundle root to each
// entry when merging it with the final .ipa file.
ruleContext.registerAction(
ObjcActionsBuilder.spawnJavaOnDarwinActionBuilder(attributes.actoolzipDeployJar())
.setMnemonic("AssetCatalogCompile")
.addTransitiveInputs(objcProvider.get(ASSET_CATALOG))
.addOutput(zipOutput)
.addOutput(actoolPartialInfoplist)
.setCommandLine(actoolzipCommandLine(
objcProvider,
zipOutput,
actoolPartialInfoplist))
.build(ruleContext));
}

private CommandLine actoolzipCommandLine(
final ObjcProvider provider,
final Artifact zipOutput,
final Artifact partialInfoPlist) {
ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
CustomCommandLine.Builder commandLine = CustomCommandLine.builder()
// The next three arguments are positional, i.e. they don't have flags before them.
.addPath(zipOutput.getExecPath())
.add("") // archive root
.add(IosSdkCommands.ACTOOL_PATH)

.add("--platform").add(objcConfiguration.getBundlingPlatform().getLowerCaseNameInPlist())
.addExecPath("--output-partial-info-plist", partialInfoPlist)
.add("--minimum-deployment-target").add(objcConfiguration.getMinimumOs());

for (TargetDeviceFamily targetDeviceFamily : targetDeviceFamilies) {
commandLine.add("--target-device").add(targetDeviceFamily.name().toLowerCase(Locale.US));
}

return commandLine
.add(PathFragment.safePathStrings(provider.get(XCASSETS_DIR)))
.add(extraActoolArgs)
.build();
}


/**
* Returns the artifact that is a plist file generated by an invocation of {@code actool} or
* {@link Optional#absent()} if no asset catalogues are present in this target and its
Expand Down Expand Up @@ -350,5 +390,12 @@ Artifact ibtoolzipDeployJar() {
Artifact momczipDeployJar() {
return ruleContext.getPrerequisiteArtifact("$momczip_deploy", Mode.HOST);
}

/**
* Returns the location of the actoolzip deploy jar.
*/
Artifact actoolzipDeployJar() {
return ruleContext.getPrerequisiteArtifact("$actoolzip_deploy", Mode.HOST);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,8 @@ protected OptionsProvider optionsProvider(RuleContext ruleContext) {
protected void configureTarget(RuleConfiguredTargetBuilder target, RuleContext ruleContext,
ReleaseBundlingSupport releaseBundlingSupport) {
// If this is an application built for the simulator, make it runnable.
if (ObjcRuleClasses.objcConfiguration(ruleContext).getPlatform() == Platform.SIMULATOR) {
ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
if (objcConfiguration.getBundlingPlatform() == Platform.SIMULATOR) {
Artifact runnerScript = ObjcRuleClasses.intermediateArtifacts(ruleContext).runnerScript();
Artifact ipaFile = ruleContext.getImplicitOutputArtifact(ReleaseBundlingSupport.IPA);
releaseBundlingSupport.registerGenerateRunnerScriptAction(runnerScript, ipaFile);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,14 +67,17 @@ private IosSdkCommands() {
throw new UnsupportedOperationException("static-only");
}

private static String getPlatformPlistName(ObjcConfiguration configuration) {
return Platform.forArch(configuration.getIosCpu()).getNameInPlist();
}

private static String platformDir(ObjcConfiguration configuration) {
return DEVELOPER_DIR + "/Platforms/" + configuration.getPlatform().getNameInPlist()
+ ".platform";
return DEVELOPER_DIR + "/Platforms/" + getPlatformPlistName(configuration) + ".platform";
}

public static String sdkDir(ObjcConfiguration configuration) {
return platformDir(configuration) + "/Developer/SDKs/"
+ configuration.getPlatform().getNameInPlist() + configuration.getIosSdkVersion() + ".sdk";
+ getPlatformPlistName(configuration) + configuration.getIosSdkVersion() + ".sdk";
}

public static String frameworkDir(ObjcConfiguration configuration) {
Expand All @@ -92,7 +95,7 @@ private static Iterable<PathFragment> uniqueParentDirectories(Iterable<PathFragm
public static List<String> commonLinkAndCompileArgsForClang(
ObjcProvider provider, ObjcConfiguration configuration) {
ImmutableList.Builder<String> builder = new ImmutableList.Builder<>();
if (configuration.getPlatform() == Platform.SIMULATOR) {
if (Platform.forArch(configuration.getIosCpu()) == Platform.SIMULATOR) {
builder.add("-mios-simulator-version-min=" + configuration.getMinimumOs());
} else {
builder.add("-miphoneos-version-min=" + configuration.getMinimumOs());
Expand Down Expand Up @@ -125,7 +128,7 @@ public static Iterable<String> compileArgsForClang(ObjcConfiguration configurati
}

private static List<String> platformSpecificCompileArgsForClang(ObjcConfiguration configuration) {
switch (configuration.getPlatform()) {
switch (Platform.forArch(configuration.getIosCpu())) {
case DEVICE:
return ImmutableList.of();
case SIMULATOR:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
package com.google.devtools.build.lib.rules.objc;

import static com.google.devtools.build.lib.rules.objc.IosSdkCommands.BIN_DIR;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.ASSET_CATALOG;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.DEFINE;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.FORCE_LOAD_LIBRARY;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.FRAMEWORK_DIR;
Expand All @@ -28,14 +27,12 @@
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.SDK_DYLIB;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.SDK_FRAMEWORK;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.WEAK_SDK_FRAMEWORK;
import static com.google.devtools.build.lib.rules.objc.ObjcProvider.XCASSETS_DIR;

import com.google.common.base.Joiner;
import com.google.common.base.Optional;
import com.google.common.base.Preconditions;
import com.google.common.collect.ImmutableList;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Iterables;
import com.google.common.io.ByteSource;
import com.google.devtools.build.lib.actions.Action;
Expand All @@ -55,8 +52,6 @@
import java.io.InputStream;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;
import java.util.Set;

import javax.annotation.CheckReturnValue;

Expand Down Expand Up @@ -278,62 +273,6 @@ static final class ExtraActoolArgs extends IterableWrapper<String> {
}
}

void registerActoolzipAction(
ObjcRuleClasses.Tools tools,
ObjcProvider provider,
Artifact zipOutput,
Artifact partialInfoPlist,
ExtraActoolArgs extraActoolArgs,
Set<TargetDeviceFamily> families) {
// TODO(bazel-team): Do not use the deploy jar explicitly here. There is currently a bug where
// we cannot .setExecutable({java_binary target}) and set REQUIRES_DARWIN in the execution info.
// Note that below we set the archive root to the empty string. This means that the generated
// zip file will be rooted at the bundle root, and we have to prepend the bundle root to each
// entry when merging it with the final .ipa file.
register(spawnJavaOnDarwinActionBuilder(tools.actoolzipDeployJar())
.setMnemonic("AssetCatalogCompile")
.addTransitiveInputs(provider.get(ASSET_CATALOG))
.addOutput(zipOutput)
.addOutput(partialInfoPlist)
.setCommandLine(actoolzipCommandLine(
objcConfiguration,
provider,
zipOutput,
partialInfoPlist,
extraActoolArgs,
ImmutableSet.copyOf(families)))
.build(context));
}

private static CommandLine actoolzipCommandLine(
final ObjcConfiguration objcConfiguration,
final ObjcProvider provider,
final Artifact zipOutput,
final Artifact partialInfoPlist,
final ExtraActoolArgs extraActoolArgs,
final ImmutableSet<TargetDeviceFamily> families) {
return new CommandLine() {
@Override
public Iterable<String> arguments() {
ImmutableList.Builder<String> args = new ImmutableList.Builder<String>()
// The next three arguments are positional, i.e. they don't have flags before them.
.add(zipOutput.getExecPathString())
.add("") // archive root
.add(IosSdkCommands.ACTOOL_PATH)
.add("--platform")
.add(objcConfiguration.getPlatform().getLowerCaseNameInPlist())
.add("--output-partial-info-plist").add(partialInfoPlist.getExecPathString())
.add("--minimum-deployment-target").add(objcConfiguration.getMinimumOs());
for (TargetDeviceFamily targetDeviceFamily : families) {
args.add("--target-device").add(targetDeviceFamily.name().toLowerCase(Locale.US));
}
return args
.addAll(PathFragment.safePathStrings(provider.get(XCASSETS_DIR)))
.addAll(extraActoolArgs)
.build();
}
};
}

private static final String FRAMEWORK_SUFFIX = ".framework";

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,24 @@ public String getIosCpu() {
return iosCpu;
}

public Platform getPlatform() {
/**
* Returns the platform of the configuration for the current bundle, based on configured
* architectures (for example, {@code i386} maps to {@link Platform#SIMULATOR}).
*
* <p>If {@link #getIosMultiCpus()} is set, returns {@link Platform#DEVICE} if any of the
* architectures matches it, otherwise returns the mapping for {@link #getIosCpu()}.
*
* <p>Note that this method should not be used to determine the platform for code compilation.
* Derive the platform from {@link #getIosCpu()} instead.
*/
// TODO(bazel-team): This method should be enabled to return multiple values once all call sites
// (in particular actool, bundlemerge, momc) have been upgraded to support multiple values.
public Platform getBundlingPlatform() {
for (String architecture : getIosMultiCpus()) {
if (Platform.forArch(architecture) == Platform.DEVICE) {
return Platform.DEVICE;
}
}
return Platform.forArch(getIosCpu());
}

Expand Down Expand Up @@ -238,5 +255,17 @@ public void reportInvalidOptions(EventHandler reporter, BuildOptions buildOption
reporter.handle(Event.error(
"--objc_generate_debug_symbols is not supported when --ios_multi_cpus is set"));
}

// TODO(bazel-team): Remove this constraint once getBundlingPlatform can return multiple values.
Platform platform = null;
for (String architecture : iosMultiCpus) {
if (platform == null) {
platform = Platform.forArch(architecture);
} else if (platform != Platform.forArch(architecture)) {
reporter.handle(Event.error(
String.format("--ios_multi_cpus does not currently allow values for both simulator and "
+ "device builds but was %s", iosMultiCpus)));
}
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ public ObjcConfiguration create(ConfigurationEnvironment env, BuildOptions build
}

Label defaultProvisioningProfileLabel = null;
if (Platform.forArch(objcOptions.iosCpu) == Platform.DEVICE) {
if (getPlatform(objcOptions) == Platform.DEVICE) {
defaultProvisioningProfileLabel = forceLoad(env, "//tools/objc:default_provisioning_profile");
}

Expand All @@ -60,11 +60,19 @@ public Class<? extends BuildConfiguration.Fragment> creates() {
return ObjcConfiguration.class;
}

private Platform getPlatform(ObjcCommandLineOptions objcOptions) {
for (String architecture : objcOptions.iosMultiCpus) {
if (Platform.forArch(architecture) == Platform.DEVICE) {
return Platform.DEVICE;
}
}
return Platform.forArch(objcOptions.iosCpu);
}

private static Label forceLoad(ConfigurationEnvironment env, String target)
throws InvalidConfigurationException {
Label label = null;
try {
label = Label.parseAbsolute(target);
Label label = Label.parseAbsolute(target);
env.getTarget(label);
return label;
} catch (Label.SyntaxException | NoSuchPackageException | NoSuchTargetException e) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -845,7 +845,7 @@ The provisioning profile (.mobileprovision file) to use when bundling
public Label getDefault(Rule rule, BuildConfiguration configuration) {
ObjcConfiguration objcConfiguration =
configuration.getFragment(ObjcConfiguration.class);
if (objcConfiguration.getPlatform() != Platform.DEVICE) {
if (objcConfiguration.getBundlingPlatform() != Platform.DEVICE) {
return null;
}
if (rule.isAttributeValueExplicitlySpecified("provisioning_profile")) {
Expand Down Expand Up @@ -950,10 +950,6 @@ static final class Tools {
this.ruleContext = Preconditions.checkNotNull(ruleContext);
}

Artifact actoolzipDeployJar() {
return ruleContext.getPrerequisiteArtifact("$actoolzip_deploy", Mode.HOST);
}

FilesToRunProvider xcodegen() {
return ruleContext.getExecutablePrerequisite("$xcodegen", Mode.HOST);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -224,7 +224,7 @@ ReleaseBundlingSupport registerActions() {
Artifact ipaOutput = ruleContext.getImplicitOutputArtifact(IPA);

Artifact maybeSignedIpa;
if (objcConfiguration.getPlatform() == Platform.SIMULATOR) {
if (objcConfiguration.getBundlingPlatform() == Platform.SIMULATOR) {
maybeSignedIpa = ipaOutput;
} else if (attributes.provisioningProfile() == null) {
throw new IllegalStateException(DEVICE_NO_PROVISIONING_PROFILE);
Expand Down Expand Up @@ -371,7 +371,7 @@ private static Bundling bundling(
String bundleDirFormat) {
ImmutableList<BundleableFile> extraBundleFiles;
ObjcConfiguration objcConfiguration = ObjcRuleClasses.objcConfiguration(ruleContext);
if (objcConfiguration.getPlatform() == Platform.DEVICE) {
if (objcConfiguration.getBundlingPlatform() == Platform.DEVICE) {
extraBundleFiles = ImmutableList.of(new BundleableFile(
new Attributes(ruleContext).provisioningProfile(),
PROVISIONING_PROFILE_BUNDLE_FILE));
Expand Down

0 comments on commit e7c06eb

Please sign in to comment.