diff options
Diffstat (limited to 'java/dex.go')
-rw-r--r-- | java/dex.go | 105 |
1 files changed, 74 insertions, 31 deletions
diff --git a/java/dex.go b/java/dex.go index cd45a9319..6bf0143b1 100644 --- a/java/dex.go +++ b/java/dex.go @@ -15,6 +15,7 @@ package java import ( + "strconv" "strings" "github.com/google/blueprint" @@ -38,6 +39,10 @@ type DexProperties struct { // True if the module containing this has it set by default. EnabledByDefault bool `blueprint:"mutated"` + // If true, runs R8 in Proguard compatibility mode (default). + // Otherwise, runs R8 in full mode. + Proguard_compatibility *bool + // If true, optimize for size by removing unused code. Defaults to true for apps, // false for libraries and tests. Shrink *bool @@ -72,13 +77,19 @@ type dexer struct { // list of extra proguard flag files extraProguardFlagFiles android.Paths proguardDictionary android.OptionalPath + proguardUsageZip android.OptionalPath } func (d *dexer) effectiveOptimizeEnabled() bool { return BoolDefault(d.dexProperties.Optimize.Enabled, d.dexProperties.Optimize.EnabledByDefault) } -var d8, d8RE = remoteexec.MultiCommandStaticRules(pctx, "d8", +func init() { + pctx.HostBinToolVariable("runWithTimeoutCmd", "run_with_timeout") + pctx.SourcePathVariable("jstackCmd", "${config.JavaToolchain}/jstack") +} + +var d8, d8RE = pctx.MultiCommandRemoteStaticRules("d8", blueprint.RuleParams{ Command: `rm -rf "$outDir" && mkdir -p "$outDir" && ` + `$d8Template${config.D8Cmd} ${config.DexFlags} --output $outDir $d8Flags $in && ` + @@ -106,27 +117,35 @@ var d8, d8RE = remoteexec.MultiCommandStaticRules(pctx, "d8", }, }, []string{"outDir", "d8Flags", "zipFlags"}, nil) -var r8, r8RE = remoteexec.MultiCommandStaticRules(pctx, "r8", +var r8, r8RE = pctx.MultiCommandRemoteStaticRules("r8", blueprint.RuleParams{ Command: `rm -rf "$outDir" && mkdir -p "$outDir" && ` + - `rm -f "$outDict" && ` + - `$r8Template${config.R8Cmd} ${config.DexFlags} -injars $in --output $outDir ` + - `--force-proguard-compatibility ` + + `rm -f "$outDict" && rm -rf "${outUsageDir}" && ` + + `mkdir -p $$(dirname ${outUsage}) && ` + + // TODO(b/181095653): remove R8 timeout and go back to config.R8Cmd. + `${runWithTimeoutCmd} -timeout 30m -on_timeout '${jstackCmd} $$PID' -- ` + + `$r8Template${config.JavaCmd} ${config.DexJavaFlags} -cp ${config.R8Jar} ` + + `com.android.tools.r8.compatproguard.CompatProguard -injars $in --output $outDir ` + `--no-data-resources ` + - `-printmapping $outDict ` + + `-printmapping ${outDict} ` + + `-printusage ${outUsage} ` + `$r8Flags && ` + - `touch "$outDict" && ` + + `touch "${outDict}" "${outUsage}" && ` + + `${config.SoongZipCmd} -o ${outUsageZip} -C ${outUsageDir} -f ${outUsage} && ` + + `rm -rf ${outUsageDir} && ` + `$zipTemplate${config.SoongZipCmd} $zipFlags -o $outDir/classes.dex.jar -C $outDir -f "$outDir/classes*.dex" && ` + `${config.MergeZipsCmd} -D -stripFile "**/*.class" $out $outDir/classes.dex.jar $in`, CommandDeps: []string{ - "${config.R8Cmd}", + "${config.R8Jar}", "${config.SoongZipCmd}", "${config.MergeZipsCmd}", + "${runWithTimeoutCmd}", }, }, map[string]*remoteexec.REParams{ "$r8Template": &remoteexec.REParams{ Labels: map[string]string{"type": "compile", "compiler": "r8"}, Inputs: []string{"$implicits", "${config.R8Jar}"}, + OutputFiles: []string{"${outUsage}"}, ExecStrategy: "${config.RER8ExecStrategy}", ToolchainInputs: []string{"${config.JavaCmd}"}, Platform: map[string]string{remoteexec.PoolKey: "${config.REJavaPool}"}, @@ -138,9 +157,17 @@ var r8, r8RE = remoteexec.MultiCommandStaticRules(pctx, "r8", ExecStrategy: "${config.RER8ExecStrategy}", Platform: map[string]string{remoteexec.PoolKey: "${config.REJavaPool}"}, }, - }, []string{"outDir", "outDict", "r8Flags", "zipFlags"}, []string{"implicits"}) + "$zipUsageTemplate": &remoteexec.REParams{ + Labels: map[string]string{"type": "tool", "name": "soong_zip"}, + Inputs: []string{"${config.SoongZipCmd}", "${outUsage}"}, + OutputFiles: []string{"${outUsageZip}"}, + ExecStrategy: "${config.RER8ExecStrategy}", + Platform: map[string]string{remoteexec.PoolKey: "${config.REJavaPool}"}, + }, + }, []string{"outDir", "outDict", "outUsage", "outUsageZip", "outUsageDir", + "r8Flags", "zipFlags"}, []string{"implicits"}) -func (d *dexer) dexCommonFlags(ctx android.ModuleContext, minSdkVersion sdkSpec) []string { +func (d *dexer) dexCommonFlags(ctx android.ModuleContext, minSdkVersion android.SdkSpec) []string { flags := d.dexProperties.Dxflags // Translate all the DX flags to D8 ones until all the build files have been migrated // to D8 flags. See: b/69377755 @@ -157,12 +184,12 @@ func (d *dexer) dexCommonFlags(ctx android.ModuleContext, minSdkVersion sdkSpec) "--verbose") } - effectiveVersion, err := minSdkVersion.effectiveVersion(ctx) + effectiveVersion, err := minSdkVersion.EffectiveVersion(ctx) if err != nil { ctx.PropertyErrorf("min_sdk_version", "%s", err) } - flags = append(flags, "--min-api "+effectiveVersion.asNumberString()) + flags = append(flags, "--min-api "+strconv.Itoa(effectiveVersion.FinalOrFutureInt())) return flags } @@ -187,8 +214,9 @@ func (d *dexer) r8Flags(ctx android.ModuleContext, flags javaBuilderFlags) (r8Fl // - prevent ProGuard stripping subclass in the support library that extends class added in the higher SDK version. // See b/20667396 var proguardRaiseDeps classpath - ctx.VisitDirectDepsWithTag(proguardRaiseTag, func(dep android.Module) { - proguardRaiseDeps = append(proguardRaiseDeps, dep.(Dependency).HeaderJars()...) + ctx.VisitDirectDepsWithTag(proguardRaiseTag, func(m android.Module) { + dep := ctx.OtherModuleProvider(m, JavaInfoProvider).(JavaInfo) + proguardRaiseDeps = append(proguardRaiseDeps, dep.HeaderJars...) }) r8Flags = append(r8Flags, proguardRaiseDeps.FormJavaClassPath("-libraryjars")) @@ -217,6 +245,10 @@ func (d *dexer) r8Flags(ctx android.ModuleContext, flags javaBuilderFlags) (r8Fl r8Flags = append(r8Flags, opt.Proguard_flags...) + if BoolDefault(opt.Proguard_compatibility, true) { + r8Flags = append(r8Flags, "--force-proguard-compatibility") + } + // TODO(ccross): Don't shrink app instrumentation tests by default. if !Bool(opt.Shrink) { r8Flags = append(r8Flags, "-dontshrink") @@ -238,14 +270,17 @@ func (d *dexer) r8Flags(ctx android.ModuleContext, flags javaBuilderFlags) (r8Fl r8Flags = append(r8Flags, "--debug") } + // TODO(b/180878971): missing classes should be added to the relevant builds. + r8Flags = append(r8Flags, "-ignorewarnings") + return r8Flags, r8Deps } -func (d *dexer) compileDex(ctx android.ModuleContext, flags javaBuilderFlags, minSdkVersion sdkSpec, - classesJar android.Path, jarName string) android.ModuleOutPath { +func (d *dexer) compileDex(ctx android.ModuleContext, flags javaBuilderFlags, minSdkVersion android.SdkSpec, + classesJar android.Path, jarName string) android.OutputPath { // Compile classes.jar into classes.dex and then javalib.jar - javalibJar := android.PathForModuleOut(ctx, "dex", jarName) + javalibJar := android.PathForModuleOut(ctx, "dex", jarName).OutputPath outDir := android.PathForModuleOut(ctx, "dex") zipFlags := "--ignore_missing_files" @@ -259,31 +294,39 @@ func (d *dexer) compileDex(ctx android.ModuleContext, flags javaBuilderFlags, mi if useR8 { proguardDictionary := android.PathForModuleOut(ctx, "proguard_dictionary") d.proguardDictionary = android.OptionalPathForPath(proguardDictionary) + proguardUsageDir := android.PathForModuleOut(ctx, "proguard_usage") + proguardUsage := proguardUsageDir.Join(ctx, ctx.Namespace().Path, + android.ModuleNameWithPossibleOverride(ctx), "unused.txt") + proguardUsageZip := android.PathForModuleOut(ctx, "proguard_usage.zip") + d.proguardUsageZip = android.OptionalPathForPath(proguardUsageZip) r8Flags, r8Deps := d.r8Flags(ctx, flags) rule := r8 args := map[string]string{ - "r8Flags": strings.Join(append(commonFlags, r8Flags...), " "), - "zipFlags": zipFlags, - "outDict": proguardDictionary.String(), - "outDir": outDir.String(), + "r8Flags": strings.Join(append(commonFlags, r8Flags...), " "), + "zipFlags": zipFlags, + "outDict": proguardDictionary.String(), + "outUsageDir": proguardUsageDir.String(), + "outUsage": proguardUsage.String(), + "outUsageZip": proguardUsageZip.String(), + "outDir": outDir.String(), } - if ctx.Config().IsEnvTrue("RBE_R8") { + if ctx.Config().UseRBE() && ctx.Config().IsEnvTrue("RBE_R8") { rule = r8RE args["implicits"] = strings.Join(r8Deps.Strings(), ",") } ctx.Build(pctx, android.BuildParams{ - Rule: rule, - Description: "r8", - Output: javalibJar, - ImplicitOutput: proguardDictionary, - Input: classesJar, - Implicits: r8Deps, - Args: args, + Rule: rule, + Description: "r8", + Output: javalibJar, + ImplicitOutputs: android.WritablePaths{proguardDictionary, proguardUsageZip}, + Input: classesJar, + Implicits: r8Deps, + Args: args, }) } else { d8Flags, d8Deps := d8Flags(flags) rule := d8 - if ctx.Config().IsEnvTrue("RBE_D8") { + if ctx.Config().UseRBE() && ctx.Config().IsEnvTrue("RBE_D8") { rule = d8RE } ctx.Build(pctx, android.BuildParams{ @@ -300,7 +343,7 @@ func (d *dexer) compileDex(ctx android.ModuleContext, flags javaBuilderFlags, mi }) } if proptools.Bool(d.dexProperties.Uncompress_dex) { - alignedJavalibJar := android.PathForModuleOut(ctx, "aligned", jarName) + alignedJavalibJar := android.PathForModuleOut(ctx, "aligned", jarName).OutputPath TransformZipAlign(ctx, alignedJavalibJar, javalibJar) javalibJar = alignedJavalibJar } |