Add Darwin x86_64+arm64 universal binary support
This is configured from Make by setting up Darwin+Arm64 as a HOST_CROSS target (which is largely true, as binaries can't be executed on X86_64 machines). On the Soong side, it's a bit blurier, as we don't current have any other users that are the same OS but not natively executable (Linux/musl is executable, Windows/x86 is a different OS). Instead of requiring cc_binary/etc to become multi-architecture-aware and using something like common_first/MultiTarget, this defaults all non-multi-architecture-aware modules to be built with both architectures. It then adds a dependency with the DarwinUniversalVariantTag so that supporting modules can get the outputs of the other variant. Cc uses that dependency tag to run lipo on shared libraries and binaries so that the output of the x86_64 variant is actually a fat binary including both architectures. Bug: 203607969 Test: build sdk-repo targets on a Mac Change-Id: Icbddb0a177c0ba19d3e0d11f8cf568e0d1ea3245
This commit is contained in:
@@ -345,6 +345,12 @@ func (binary *binaryDecorator) link(ctx ModuleContext,
|
||||
flags.Local.LdFlags = append(flags.Local.LdFlags, "-Wl,--no-dynamic-linker")
|
||||
}
|
||||
|
||||
if ctx.Darwin() && deps.DarwinSecondArchOutput.Valid() {
|
||||
fatOutputFile := outputFile
|
||||
outputFile = android.PathForModuleOut(ctx, "pre-fat", fileName)
|
||||
transformDarwinUniversalBinary(ctx, fatOutputFile, outputFile, deps.DarwinSecondArchOutput.Path())
|
||||
}
|
||||
|
||||
builderFlags := flagsToBuilderFlags(flags)
|
||||
stripFlags := flagsToStripFlags(flags)
|
||||
if binary.stripper.NeedsStrip(ctx) {
|
||||
|
@@ -165,6 +165,12 @@ var (
|
||||
}
|
||||
}()
|
||||
|
||||
darwinLipo = pctx.AndroidStaticRule("darwinLipo",
|
||||
blueprint.RuleParams{
|
||||
Command: "${config.MacLipoPath} -create -output $out $in",
|
||||
CommandDeps: []string{"${config.MacLipoPath}"},
|
||||
})
|
||||
|
||||
_ = pctx.SourcePathVariable("archiveRepackPath", "build/soong/scripts/archive_repack.sh")
|
||||
|
||||
// Rule to repack an archive (.a) file with a subset of object files.
|
||||
@@ -1060,6 +1066,15 @@ func transformDarwinStrip(ctx android.ModuleContext, inputFile android.Path,
|
||||
})
|
||||
}
|
||||
|
||||
func transformDarwinUniversalBinary(ctx android.ModuleContext, outputFile android.WritablePath, inputFiles ...android.Path) {
|
||||
ctx.Build(pctx, android.BuildParams{
|
||||
Rule: darwinLipo,
|
||||
Description: "lipo " + outputFile.Base(),
|
||||
Output: outputFile,
|
||||
Inputs: inputFiles,
|
||||
})
|
||||
}
|
||||
|
||||
// Registers build statement to zip one or more coverage files.
|
||||
func transformCoverageFilesToZip(ctx android.ModuleContext,
|
||||
inputs Objects, baseName string) android.OptionalPath {
|
||||
|
9
cc/cc.go
9
cc/cc.go
@@ -167,6 +167,10 @@ type PathDeps struct {
|
||||
|
||||
// Path to the dynamic linker binary
|
||||
DynamicLinker android.OptionalPath
|
||||
|
||||
// For Darwin builds, the path to the second architecture's output that should
|
||||
// be combined with this architectures's output into a FAT MachO file.
|
||||
DarwinSecondArchOutput android.OptionalPath
|
||||
}
|
||||
|
||||
// LocalOrGlobalFlags contains flags that need to have values set globally by the build system or locally by the module
|
||||
@@ -2578,6 +2582,11 @@ func (c *Module) depsToPaths(ctx android.ModuleContext) PathDeps {
|
||||
depName := ctx.OtherModuleName(dep)
|
||||
depTag := ctx.OtherModuleDependencyTag(dep)
|
||||
|
||||
if depTag == android.DarwinUniversalVariantTag {
|
||||
depPaths.DarwinSecondArchOutput = dep.(*Module).OutputFile()
|
||||
return
|
||||
}
|
||||
|
||||
ccDep, ok := dep.(LinkableInterface)
|
||||
if !ok {
|
||||
|
||||
|
@@ -87,6 +87,10 @@ func init() {
|
||||
return getMacTools(ctx).arPath
|
||||
})
|
||||
|
||||
pctx.VariableFunc("MacLipoPath", func(ctx android.PackageVarContext) string {
|
||||
return getMacTools(ctx).lipoPath
|
||||
})
|
||||
|
||||
pctx.VariableFunc("MacStripPath", func(ctx android.PackageVarContext) string {
|
||||
return getMacTools(ctx).stripPath
|
||||
})
|
||||
@@ -118,6 +122,7 @@ type macPlatformTools struct {
|
||||
|
||||
sdkRoot string
|
||||
arPath string
|
||||
lipoPath string
|
||||
stripPath string
|
||||
toolPath string
|
||||
}
|
||||
@@ -157,6 +162,7 @@ func getMacTools(ctx android.PathContext) *macPlatformTools {
|
||||
macTools.sdkRoot = xcrun("--show-sdk-path")
|
||||
|
||||
macTools.arPath = xcrun("--find", "ar")
|
||||
macTools.lipoPath = xcrun("--find", "lipo")
|
||||
macTools.stripPath = xcrun("--find", "strip")
|
||||
macTools.toolPath = filepath.Dir(xcrun("--find", "ld"))
|
||||
})
|
||||
|
@@ -1429,6 +1429,12 @@ func (library *libraryDecorator) linkShared(ctx ModuleContext,
|
||||
|
||||
builderFlags := flagsToBuilderFlags(flags)
|
||||
|
||||
if ctx.Darwin() && deps.DarwinSecondArchOutput.Valid() {
|
||||
fatOutputFile := outputFile
|
||||
outputFile = android.PathForModuleOut(ctx, "pre-fat", fileName)
|
||||
transformDarwinUniversalBinary(ctx, fatOutputFile, outputFile, deps.DarwinSecondArchOutput.Path())
|
||||
}
|
||||
|
||||
// Optimize out relinking against shared libraries whose interface hasn't changed by
|
||||
// depending on a table of contents file instead of the library itself.
|
||||
tocFile := outputFile.ReplaceExtension(ctx, flags.Toolchain.ShlibSuffix()[1:]+".toc")
|
||||
|
Reference in New Issue
Block a user