diff options
Diffstat (limited to 'java')
-rw-r--r-- | java/aar.go | 12 | ||||
-rw-r--r-- | java/androidmk.go | 8 | ||||
-rw-r--r-- | java/app.go | 16 | ||||
-rw-r--r-- | java/app_test.go | 159 | ||||
-rw-r--r-- | java/builder.go | 23 | ||||
-rw-r--r-- | java/dexpreopt.go | 7 | ||||
-rw-r--r-- | java/dexpreopt_bootjars.go | 61 | ||||
-rw-r--r-- | java/dexpreopt_config.go | 48 | ||||
-rw-r--r-- | java/droiddoc.go | 20 | ||||
-rw-r--r-- | java/java.go | 48 | ||||
-rw-r--r-- | java/java_test.go | 15 | ||||
-rw-r--r-- | java/robolectric.go | 84 | ||||
-rw-r--r-- | java/robolectric_test.go | 88 | ||||
-rw-r--r-- | java/sdk.go | 31 | ||||
-rw-r--r-- | java/sdk_library.go | 28 | ||||
-rw-r--r-- | java/sdk_test.go | 16 | ||||
-rw-r--r-- | java/system_modules.go | 35 | ||||
-rw-r--r-- | java/testing.go | 12 |
18 files changed, 563 insertions, 148 deletions
diff --git a/java/aar.go b/java/aar.go index 1e8e6d8c4..47f6e5f6a 100644 --- a/java/aar.go +++ b/java/aar.go @@ -188,8 +188,7 @@ func (a *aapt) aapt2Flags(ctx android.ModuleContext, sdkContext sdkContext, mani return linkFlags, linkDeps, resDirs, overlayDirs, rroDirs, resourceZips } -func (a *aapt) deps(ctx android.BottomUpMutatorContext, sdkContext sdkContext) { - sdkDep := decodeSdkDep(ctx, sdkContext) +func (a *aapt) deps(ctx android.BottomUpMutatorContext, sdkDep sdkDep) { if sdkDep.frameworkResModule != "" { ctx.AddVariationDependencies(nil, frameworkResTag, sdkDep.frameworkResModule) } @@ -401,8 +400,9 @@ var _ AndroidLibraryDependency = (*AndroidLibrary)(nil) func (a *AndroidLibrary) DepsMutator(ctx android.BottomUpMutatorContext) { a.Module.deps(ctx) - if !Bool(a.properties.No_framework_libs) && !Bool(a.properties.No_standard_libs) { - a.aapt.deps(ctx, sdkContext(a)) + sdkDep := decodeSdkDep(ctx, sdkContext(a)) + if sdkDep.hasFrameworkLibs() { + a.aapt.deps(ctx, sdkDep) } } @@ -513,6 +513,10 @@ func (a *AARImport) targetSdkVersion() string { return a.sdkVersion() } +func (a *AARImport) noFrameworkLibs() bool { + return false +} + var _ AndroidLibraryDependency = (*AARImport)(nil) func (a *AARImport) ExportPackage() android.Path { diff --git a/java/androidmk.go b/java/androidmk.go index 5491b3eba..39c2d1342 100644 --- a/java/androidmk.go +++ b/java/androidmk.go @@ -97,14 +97,6 @@ func (library *Library) AndroidMk() android.AndroidMkData { if library.proguardDictionary != nil { fmt.Fprintln(w, "LOCAL_SOONG_PROGUARD_DICT :=", library.proguardDictionary.String()) } - - // Temporary hack: export sources used to compile framework.jar to Make - // to be used for droiddoc - // TODO(ccross): remove this once droiddoc is in soong - if (library.Name() == "framework") || (library.Name() == "framework-annotation-proc") { - fmt.Fprintln(w, "SOONG_FRAMEWORK_SRCS :=", strings.Join(library.compiledJavaSrcs.Strings(), " ")) - fmt.Fprintln(w, "SOONG_FRAMEWORK_SRCJARS :=", strings.Join(library.compiledSrcJars.Strings(), " ")) - } }, }, Custom: func(w io.Writer, name, prefix, moduleDir string, data android.AndroidMkData) { diff --git a/java/app.go b/java/app.go index 78e05012c..cab97de45 100644 --- a/java/app.go +++ b/java/app.go @@ -159,8 +159,9 @@ func (a *AndroidApp) DepsMutator(ctx android.BottomUpMutatorContext) { ctx.PropertyErrorf("stl", "sdk_version must be set in order to use c++_shared") } - if !Bool(a.properties.No_framework_libs) && !Bool(a.properties.No_standard_libs) { - a.aapt.deps(ctx, sdkContext(a)) + sdkDep := decodeSdkDep(ctx, sdkContext(a)) + if sdkDep.hasFrameworkLibs() { + a.aapt.deps(ctx, sdkDep) } embedJni := a.shouldEmbedJnis(ctx) @@ -180,7 +181,7 @@ func (a *AndroidApp) DepsMutator(ctx android.BottomUpMutatorContext) { } } - a.usesLibrary.deps(ctx, Bool(a.properties.No_framework_libs)) + a.usesLibrary.deps(ctx, sdkDep.hasFrameworkLibs()) } func (a *AndroidApp) OverridablePropertiesDepsMutator(ctx android.BottomUpMutatorContext) { @@ -783,7 +784,7 @@ func (a *AndroidAppImport) DepsMutator(ctx android.BottomUpMutatorContext) { ctx.AddDependency(ctx.Module(), certificateTag, cert) } - a.usesLibrary.deps(ctx, false) + a.usesLibrary.deps(ctx, true) } func (a *AndroidAppImport) uncompressEmbeddedJniLibs( @@ -937,11 +938,14 @@ type usesLibrary struct { usesLibraryProperties UsesLibraryProperties } -func (u *usesLibrary) deps(ctx android.BottomUpMutatorContext, noFrameworkLibs bool) { +func (u *usesLibrary) deps(ctx android.BottomUpMutatorContext, hasFrameworkLibs bool) { if !ctx.Config().UnbundledBuild() { ctx.AddVariationDependencies(nil, usesLibTag, u.usesLibraryProperties.Uses_libs...) ctx.AddVariationDependencies(nil, usesLibTag, u.presentOptionalUsesLibs(ctx)...) - if !noFrameworkLibs { + // Only add these extra dependencies if the module depends on framework libs. This avoids + // creating a cyclic dependency: + // e.g. framework-res -> org.apache.http.legacy -> ... -> framework-res. + if hasFrameworkLibs { // dexpreopt/dexpreopt.go needs the paths to the dex jars of these libraries in case construct_context.sh needs // to pass them to dex2oat. Add them as a dependency so we can determine the path to the dex jar of each // library to dexpreopt. diff --git a/java/app_test.go b/java/app_test.go index bb39c165c..27802cd21 100644 --- a/java/app_test.go +++ b/java/app_test.go @@ -546,7 +546,7 @@ func TestAppSdkVersion(t *testing.T) { } } -func TestJNIABI(t *testing.T) { +func TestJNIABI_no_framework_libs_true(t *testing.T) { ctx := testJava(t, cc.GatherRequiredDepsForTest(android.Android)+` cc_library { name: "libjni", @@ -619,7 +619,80 @@ func TestJNIABI(t *testing.T) { } } -func TestJNIPackaging(t *testing.T) { +func TestJNIABI(t *testing.T) { + ctx := testJava(t, cc.GatherRequiredDepsForTest(android.Android)+` + cc_library { + name: "libjni", + system_shared_libs: [], + stl: "none", + } + + android_test { + name: "test", + sdk_version: "core_platform", + jni_libs: ["libjni"], + } + + android_test { + name: "test_first", + sdk_version: "core_platform", + compile_multilib: "first", + jni_libs: ["libjni"], + } + + android_test { + name: "test_both", + sdk_version: "core_platform", + compile_multilib: "both", + jni_libs: ["libjni"], + } + + android_test { + name: "test_32", + sdk_version: "core_platform", + compile_multilib: "32", + jni_libs: ["libjni"], + } + + android_test { + name: "test_64", + sdk_version: "core_platform", + compile_multilib: "64", + jni_libs: ["libjni"], + } + `) + + testCases := []struct { + name string + abis []string + }{ + {"test", []string{"arm64-v8a"}}, + {"test_first", []string{"arm64-v8a"}}, + {"test_both", []string{"arm64-v8a", "armeabi-v7a"}}, + {"test_32", []string{"armeabi-v7a"}}, + {"test_64", []string{"arm64-v8a"}}, + } + + for _, test := range testCases { + t.Run(test.name, func(t *testing.T) { + app := ctx.ModuleForTests(test.name, "android_common") + jniLibZip := app.Output("jnilibs.zip") + var abis []string + args := strings.Fields(jniLibZip.Args["jarArgs"]) + for i := 0; i < len(args); i++ { + if args[i] == "-P" { + abis = append(abis, filepath.Base(args[i+1])) + i++ + } + } + if !reflect.DeepEqual(abis, test.abis) { + t.Errorf("want abis %v, got %v", test.abis, abis) + } + }) + } +} + +func TestJNIPackaging_no_framework_libs_true(t *testing.T) { ctx := testJava(t, cc.GatherRequiredDepsForTest(android.Android)+` cc_library { name: "libjni", @@ -700,7 +773,89 @@ func TestJNIPackaging(t *testing.T) { } }) } +} + +func TestJNIPackaging(t *testing.T) { + ctx := testJava(t, cc.GatherRequiredDepsForTest(android.Android)+` + cc_library { + name: "libjni", + system_shared_libs: [], + stl: "none", + } + + android_app { + name: "app", + jni_libs: ["libjni"], + } + + android_app { + name: "app_noembed", + jni_libs: ["libjni"], + use_embedded_native_libs: false, + } + + android_app { + name: "app_embed", + jni_libs: ["libjni"], + use_embedded_native_libs: true, + } + + android_test { + name: "test", + sdk_version: "core_platform", + jni_libs: ["libjni"], + } + + android_test { + name: "test_noembed", + sdk_version: "core_platform", + jni_libs: ["libjni"], + use_embedded_native_libs: false, + } + + android_test_helper_app { + name: "test_helper", + sdk_version: "core_platform", + jni_libs: ["libjni"], + } + + android_test_helper_app { + name: "test_helper_noembed", + sdk_version: "core_platform", + jni_libs: ["libjni"], + use_embedded_native_libs: false, + } + `) + + testCases := []struct { + name string + packaged bool + compressed bool + }{ + {"app", false, false}, + {"app_noembed", false, false}, + {"app_embed", true, false}, + {"test", true, false}, + {"test_noembed", true, true}, + {"test_helper", true, false}, + {"test_helper_noembed", true, true}, + } + + for _, test := range testCases { + t.Run(test.name, func(t *testing.T) { + app := ctx.ModuleForTests(test.name, "android_common") + jniLibZip := app.MaybeOutput("jnilibs.zip") + if g, w := (jniLibZip.Rule != nil), test.packaged; g != w { + t.Errorf("expected jni packaged %v, got %v", w, g) + } + if jniLibZip.Rule != nil { + if g, w := !strings.Contains(jniLibZip.Args["jarArgs"], "-L 0"), test.compressed; g != w { + t.Errorf("expected jni compressed %v, got %v", w, g) + } + } + }) + } } func TestCertificates(t *testing.T) { diff --git a/java/builder.go b/java/builder.go index e1a912b2f..a48e8b1a2 100644 --- a/java/builder.go +++ b/java/builder.go @@ -148,15 +148,16 @@ func init() { } type javaBuilderFlags struct { - javacFlags string - bootClasspath classpath - classpath classpath - processorPath classpath - processor string - systemModules classpath - aidlFlags string - aidlDeps android.Paths - javaVersion string + javacFlags string + bootClasspath classpath + classpath classpath + processorPath classpath + processor string + systemModules classpath + systemModulesDeps android.Paths + aidlFlags string + aidlDeps android.Paths + javaVersion string errorProneExtraJavacFlags string errorProneProcessorPath classpath @@ -248,7 +249,7 @@ func transformJavaToClasses(ctx android.ModuleContext, outputFile android.Writab var bootClasspath string if flags.javaVersion == "1.9" { - deps = append(deps, flags.systemModules...) + deps = append(deps, flags.systemModulesDeps...) bootClasspath = flags.systemModules.FormJavaSystemModulesPath("--system=", ctx.Device()) } else { deps = append(deps, flags.bootClasspath...) @@ -430,7 +431,7 @@ func (x *classpath) FormJavaSystemModulesPath(optName string, forceEmpty bool) s if len(*x) > 1 { panic("more than one system module") } else if len(*x) == 1 { - return optName + strings.TrimSuffix((*x)[0].String(), "lib/modules") + return optName + (*x)[0].String() } else if forceEmpty { return optName + "none" } else { diff --git a/java/dexpreopt.go b/java/dexpreopt.go index 23d2aa6e3..ed12fe6d2 100644 --- a/java/dexpreopt.go +++ b/java/dexpreopt.go @@ -132,8 +132,10 @@ func (d *dexpreopter) dexpreopt(ctx android.ModuleContext, dexJarFile android.Mo } var images android.Paths + var imagesDeps []android.Paths for _, arch := range archs { images = append(images, bootImage.images[arch]) + imagesDeps = append(imagesDeps, bootImage.imagesDeps[arch]) } dexLocation := android.InstallPathToOnDevicePath(ctx, d.installPath) @@ -173,8 +175,9 @@ func (d *dexpreopter) dexpreopt(ctx android.ModuleContext, dexJarFile android.Mo UsesLibraries: d.usesLibs, LibraryPaths: d.libraryPaths, - Archs: archs, - DexPreoptImages: images, + Archs: archs, + DexPreoptImages: images, + DexPreoptImagesDeps: imagesDeps, // We use the dex paths and dex locations of the default boot image, as it // contains the full dexpreopt boot classpath. Other images may just contain a subset of diff --git a/java/dexpreopt_bootjars.go b/java/dexpreopt_bootjars.go index 2a1a901b7..eb735c162 100644 --- a/java/dexpreopt_bootjars.go +++ b/java/dexpreopt_bootjars.go @@ -58,9 +58,32 @@ type bootImageConfig struct { symbolsDir android.OutputPath targets []android.Target images map[android.ArchType]android.OutputPath + imagesDeps map[android.ArchType]android.Paths zip android.WritablePath } +func (image bootImageConfig) moduleFiles(ctx android.PathContext, dir android.OutputPath, exts ...string) []android.OutputPath { + ret := make([]android.OutputPath, 0, len(image.modules)*len(exts)) + + // dex preopt on the bootclasspath produces multiple files. The first dex file + // is converted into to 'name'.art (to match the legacy assumption that 'name'.art + // exists), and the rest are converted to 'name'-<jar>.art. + // In addition, each .art file has an associated .oat and .vdex file, and an + // unstripped .oat file + for i, m := range image.modules { + name := image.name + if i != 0 { + name += "-" + m + } + + for _, ext := range exts { + ret = append(ret, dir.Join(ctx, name+ext)) + } + } + + return ret +} + type bootImage struct { bootImageConfig @@ -302,49 +325,38 @@ func buildBootImageRuleForArch(ctx android.SingletonContext, image *bootImage, installDir := filepath.Join("/system/framework", arch.String()) vdexInstallDir := filepath.Join("/system/framework") - var extraFiles android.WritablePaths var vdexInstalls android.RuleBuilderInstalls var unstrippedInstalls android.RuleBuilderInstalls var zipFiles android.WritablePaths - // dex preopt on the bootclasspath produces multiple files. The first dex file - // is converted into to 'name'.art (to match the legacy assumption that 'name'.art - // exists), and the rest are converted to 'name'-<jar>.art. - // In addition, each .art file has an associated .oat and .vdex file, and an - // unstripped .oat file - for i, m := range image.modules { - name := image.name - if i != 0 { - name += "-" + m - } - - art := outputDir.Join(ctx, name+".art") - oat := outputDir.Join(ctx, name+".oat") - vdex := outputDir.Join(ctx, name+".vdex") - unstrippedOat := symbolsDir.Join(ctx, name+".oat") - - extraFiles = append(extraFiles, art, oat, vdex, unstrippedOat) + for _, artOrOat := range image.moduleFiles(ctx, outputDir, ".art", ".oat") { + cmd.ImplicitOutput(artOrOat) + zipFiles = append(zipFiles, artOrOat) - zipFiles = append(zipFiles, art, oat, vdex) + // Install the .oat and .art files + rule.Install(artOrOat, filepath.Join(installDir, artOrOat.Base())) + } - // Install the .oat and .art files. - rule.Install(art, filepath.Join(installDir, art.Base())) - rule.Install(oat, filepath.Join(installDir, oat.Base())) + for _, vdex := range image.moduleFiles(ctx, outputDir, ".vdex") { + cmd.ImplicitOutput(vdex) + zipFiles = append(zipFiles, vdex) // The vdex files are identical between architectures, install them to a shared location. The Make rules will // only use the install rules for one architecture, and will create symlinks into the architecture-specific // directories. vdexInstalls = append(vdexInstalls, android.RuleBuilderInstall{vdex, filepath.Join(vdexInstallDir, vdex.Base())}) + } + + for _, unstrippedOat := range image.moduleFiles(ctx, symbolsDir, ".oat") { + cmd.ImplicitOutput(unstrippedOat) // Install the unstripped oat files. The Make rules will put these in $(TARGET_OUT_UNSTRIPPED) unstrippedInstalls = append(unstrippedInstalls, android.RuleBuilderInstall{unstrippedOat, filepath.Join(installDir, unstrippedOat.Base())}) } - cmd.ImplicitOutputs(extraFiles) - rule.Build(pctx, ctx, image.name+"JarsDexpreopt_"+arch.String(), "dexpreopt "+image.name+" jars "+arch.String()) // save output and installed files for makevars @@ -496,6 +508,7 @@ func (d *dexpreoptBootJars) MakeVars(ctx android.MakeVarsContext) { for _, arch := range arches { ctx.Strict("DEXPREOPT_IMAGE_VDEX_BUILT_INSTALLED_"+current.name+"_"+arch.String(), current.vdexInstalls[arch].String()) ctx.Strict("DEXPREOPT_IMAGE_"+current.name+"_"+arch.String(), current.images[arch].String()) + ctx.Strict("DEXPREOPT_IMAGE_DEPS_"+current.name+"_"+arch.String(), strings.Join(current.imagesDeps[arch].Strings(), " ")) ctx.Strict("DEXPREOPT_IMAGE_BUILT_INSTALLED_"+current.name+"_"+arch.String(), current.installs[arch].String()) ctx.Strict("DEXPREOPT_IMAGE_UNSTRIPPED_BUILT_INSTALLED_"+current.name+"_"+arch.String(), current.unstrippedInstalls[arch].String()) if current.zip != nil { diff --git a/java/dexpreopt_config.go b/java/dexpreopt_config.go index d903f456a..c396d3ea0 100644 --- a/java/dexpreopt_config.go +++ b/java/dexpreopt_config.go @@ -137,27 +137,35 @@ func defaultBootImageConfig(ctx android.PathContext) bootImageConfig { dir := android.PathForOutput(ctx, ctx.Config().DeviceName(), "dex_bootjars") symbolsDir := android.PathForOutput(ctx, ctx.Config().DeviceName(), "dex_bootjars_unstripped") - images := make(map[android.ArchType]android.OutputPath) zip := dir.Join(ctx, "boot.zip") targets := dexpreoptTargets(ctx) - for _, target := range targets { - images[target.Arch.ArchType] = dir.Join(ctx, - "system/framework", target.Arch.ArchType.String()).Join(ctx, "boot.art") - } - - return bootImageConfig{ + imageConfig := bootImageConfig{ name: "boot", modules: nonUpdatableBootModules, dexLocations: nonUpdatableBootLocations, dexPaths: nonUpdatableBootDexPaths, dir: dir, symbolsDir: symbolsDir, - images: images, + images: make(map[android.ArchType]android.OutputPath), + imagesDeps: make(map[android.ArchType]android.Paths), targets: targets, zip: zip, } + + for _, target := range targets { + imageDir := dir.Join(ctx, "system/framework", target.Arch.ArchType.String()) + imageConfig.images[target.Arch.ArchType] = imageDir.Join(ctx, "boot.art") + + imagesDeps := make([]android.Path, 0, len(imageConfig.modules)*3) + for _, dep := range imageConfig.moduleFiles(ctx, imageDir, ".art", ".oat", ".vdex") { + imagesDeps = append(imagesDeps, dep) + } + imageConfig.imagesDeps[target.Arch.ArchType] = imagesDeps + } + + return imageConfig }).(bootImageConfig) } @@ -196,16 +204,10 @@ func apexBootImageConfig(ctx android.PathContext) bootImageConfig { dir := android.PathForOutput(ctx, ctx.Config().DeviceName(), "dex_apexjars") symbolsDir := android.PathForOutput(ctx, ctx.Config().DeviceName(), "dex_apexjars_unstripped") - images := make(map[android.ArchType]android.OutputPath) targets := dexpreoptTargets(ctx) - for _, target := range targets { - images[target.Arch.ArchType] = dir.Join(ctx, - "system/framework", target.Arch.ArchType.String(), "apex.art") - } - - return bootImageConfig{ + imageConfig := bootImageConfig{ name: "apex", modules: imageModules, dexLocations: bootLocations, @@ -213,8 +215,22 @@ func apexBootImageConfig(ctx android.PathContext) bootImageConfig { dir: dir, symbolsDir: symbolsDir, targets: targets, - images: images, + images: make(map[android.ArchType]android.OutputPath), + imagesDeps: make(map[android.ArchType]android.Paths), } + + for _, target := range targets { + imageDir := dir.Join(ctx, "system/framework", target.Arch.ArchType.String()) + imageConfig.images[target.Arch.ArchType] = imageDir.Join(ctx, "apex.art") + + imagesDeps := make([]android.Path, 0, len(imageConfig.modules)*3) + for _, dep := range imageConfig.moduleFiles(ctx, imageDir, ".art", ".oat", ".vdex") { + imagesDeps = append(imagesDeps, dep) + } + imageConfig.imagesDeps[target.Arch.ArchType] = imagesDeps + } + + return imageConfig }).(bootImageConfig) } diff --git a/java/droiddoc.go b/java/droiddoc.go index 992c8b57c..be1b28153 100644 --- a/java/droiddoc.go +++ b/java/droiddoc.go @@ -171,10 +171,6 @@ type JavadocProperties struct { // list of java libraries that will be in the classpath. Libs []string `android:"arch_variant"` - // don't build against the default libraries (bootclasspath, ext, and framework for device - // targets) - No_standard_libs *bool - // don't build against the framework libraries (ext, and framework for device targets) No_framework_libs *bool @@ -538,16 +534,20 @@ func (j *Javadoc) targetSdkVersion() string { return j.sdkVersion() } +func (j *Javadoc) noFrameworkLibs() bool { + return Bool(j.properties.No_framework_libs) +} + func (j *Javadoc) addDeps(ctx android.BottomUpMutatorContext) { if ctx.Device() { - if !Bool(j.properties.No_standard_libs) { - sdkDep := decodeSdkDep(ctx, sdkContext(j)) + sdkDep := decodeSdkDep(ctx, sdkContext(j)) + if sdkDep.hasStandardLibs() { if sdkDep.useDefaultLibs { ctx.AddVariationDependencies(nil, bootClasspathTag, config.DefaultBootclasspathLibraries...) if ctx.Config().TargetOpenJDK9() { ctx.AddVariationDependencies(nil, systemModulesTag, config.DefaultSystemModules) } - if !Bool(j.properties.No_framework_libs) { + if sdkDep.hasFrameworkLibs() { ctx.AddVariationDependencies(nil, libTag, config.DefaultLibraries...) } } else if sdkDep.useModule { @@ -692,10 +692,11 @@ func (j *Javadoc) collectDeps(ctx android.ModuleContext) deps { panic("Found two system module dependencies") } sm := module.(*SystemModules) - if sm.outputFile == nil { + if sm.outputDir == nil && len(sm.outputDeps) == 0 { panic("Missing directory for system module dependency") } - deps.systemModules = sm.outputFile + deps.systemModules = sm.outputDir + deps.systemModulesDeps = sm.outputDeps } }) // do not pass exclude_srcs directly when expanding srcFiles since exclude_srcs @@ -776,6 +777,7 @@ func (j *Javadoc) GenerateAndroidBuildActions(ctx android.ModuleContext) { if deps.systemModules != nil { systemModules = append(systemModules, deps.systemModules) } + implicits = append(implicits, deps.systemModulesDeps...) bootClasspathArgs = systemModules.FormJavaSystemModulesPath("--system ", ctx.Device()) bootClasspathArgs = bootClasspathArgs + " --patch-module java.base=." } diff --git a/java/java.go b/java/java.go index a1addb38c..a2e9ab023 100644 --- a/java/java.go +++ b/java/java.go @@ -82,10 +82,6 @@ type CompilerProperties struct { // list of files that should be excluded from java_resources and java_resource_dirs Exclude_java_resources []string `android:"path,arch_variant"` - // don't build against the default libraries (bootclasspath, ext, and framework for device - // targets) - No_standard_libs *bool - // don't build against the framework libraries (ext, and framework for device targets) No_framework_libs *bool @@ -440,6 +436,16 @@ type sdkDep struct { jars android.Paths aidl android.OptionalPath + + noStandardLibs, noFrameworksLibs bool +} + +func (s sdkDep) hasStandardLibs() bool { + return !s.noStandardLibs +} + +func (s sdkDep) hasFrameworkLibs() bool { + return !s.noStandardLibs && !s.noFrameworksLibs } type jniLib struct { @@ -476,14 +482,18 @@ func (j *Module) targetSdkVersion() string { return j.sdkVersion() } +func (j *Module) noFrameworkLibs() bool { + return Bool(j.properties.No_framework_libs) +} + func (j *Module) deps(ctx android.BottomUpMutatorContext) { if ctx.Device() { - if !Bool(j.properties.No_standard_libs) { - sdkDep := decodeSdkDep(ctx, sdkContext(j)) + sdkDep := decodeSdkDep(ctx, sdkContext(j)) + if sdkDep.hasStandardLibs() { if sdkDep.useDefaultLibs { ctx.AddVariationDependencies(nil, bootClasspathTag, config.DefaultBootclasspathLibraries...) ctx.AddVariationDependencies(nil, systemModulesTag, config.DefaultSystemModules) - if !Bool(j.properties.No_framework_libs) { + if sdkDep.hasFrameworkLibs() { ctx.AddVariationDependencies(nil, libTag, config.DefaultLibraries...) } } else if sdkDep.useModule { @@ -495,8 +505,8 @@ func (j *Module) deps(ctx android.BottomUpMutatorContext) { } } } else if j.deviceProperties.System_modules == nil { - ctx.PropertyErrorf("no_standard_libs", - "system_modules is required to be set when no_standard_libs is true, did you mean no_framework_libs?") + ctx.PropertyErrorf("sdk_version", + `system_modules is required to be set when sdk_version is "none", did you mean no_framework_libs?`) } else if *j.deviceProperties.System_modules != "none" { ctx.AddVariationDependencies(nil, systemModulesTag, *j.deviceProperties.System_modules) } @@ -618,6 +628,7 @@ type deps struct { srcs android.Paths srcJars android.Paths systemModules android.Path + systemModulesDeps android.Paths aidlPreprocess android.OptionalPath kotlinStdlib android.Paths kotlinAnnotations android.Paths @@ -664,7 +675,7 @@ func getLinkType(m *Module, name string) (ret linkType, stubs bool) { return javaSdk, true case ver == "current": return javaSdk, false - case ver == "": + case ver == "" || ver == "none" || ver == "core_platform": return javaPlatform, false default: if _, err := strconv.Atoi(ver); err != nil { @@ -825,10 +836,11 @@ func (j *Module) collectDeps(ctx android.ModuleContext) deps { panic("Found two system module dependencies") } sm := module.(*SystemModules) - if sm.outputFile == nil { + if sm.outputDir == nil || len(sm.outputDeps) == 0 { panic("Missing directory for system module dependency") } - deps.systemModules = sm.outputFile + deps.systemModules = sm.outputDir + deps.systemModulesDeps = sm.outputDeps } } }) @@ -842,7 +854,8 @@ func getJavaVersion(ctx android.ModuleContext, javaVersion string, sdkContext sd var ret string v := sdkContext.sdkVersion() // For PDK builds, use the latest SDK version instead of "current" - if ctx.Config().IsPdkBuild() && (v == "" || v == "current") { + if ctx.Config().IsPdkBuild() && + (v == "" || v == "none" || v == "core_platform" || v == "current") { sdkVersions := ctx.Config().Get(sdkVersionsKey).([]int) latestSdkVersion := 0 if len(sdkVersions) > 0 { @@ -861,7 +874,11 @@ func getJavaVersion(ctx android.ModuleContext, javaVersion string, sdkContext sd ret = "1.7" } else if ctx.Device() && sdk <= 29 || !ctx.Config().TargetOpenJDK9() { ret = "1.8" - } else if ctx.Device() && sdkContext.sdkVersion() != "" && sdk == android.FutureApiLevel { + } else if ctx.Device() && + sdkContext.sdkVersion() != "" && + sdkContext.sdkVersion() != "none" && + sdkContext.sdkVersion() != "core_platform" && + sdk == android.FutureApiLevel { // TODO(ccross): once we generate stubs we should be able to use 1.9 for sdk_version: "current" ret = "1.8" } else { @@ -913,7 +930,7 @@ func (j *Module) collectBuilderFlags(ctx android.ModuleContext, deps deps) javaB flags.processor = strings.Join(deps.processorClasses, ",") if len(flags.bootClasspath) == 0 && ctx.Host() && flags.javaVersion != "1.9" && - !Bool(j.properties.No_standard_libs) && + decodeSdkDep(ctx, sdkContext(j)).hasStandardLibs() && inList(flags.javaVersion, []string{"1.6", "1.7", "1.8"}) { // Give host-side tools a version of OpenJDK's standard libraries // close to what they're targeting. As of Dec 2017, AOSP is only @@ -953,6 +970,7 @@ func (j *Module) collectBuilderFlags(ctx android.ModuleContext, deps deps) javaB // systemModules if deps.systemModules != nil { flags.systemModules = append(flags.systemModules, deps.systemModules) + flags.systemModulesDeps = append(flags.systemModulesDeps, deps.systemModulesDeps...) } // aidl flags. diff --git a/java/java_test.go b/java/java_test.go index 4c8367bb9..22dec073f 100644 --- a/java/java_test.go +++ b/java/java_test.go @@ -842,6 +842,19 @@ func TestExcludeFileGroupInSrcs(t *testing.T) { } } +func TestJavaLibrary(t *testing.T) { + config := testConfig(nil) + ctx := testContext(config, "", map[string][]byte{ + "libcore/Android.bp": []byte(` + java_library { + name: "core", + sdk_version: "none", + system_modules: "none", + }`), + }) + run(t, ctx, config) +} + func TestJavaSdkLibrary(t *testing.T) { ctx := testJava(t, ` droiddoc_template { @@ -1000,7 +1013,7 @@ func TestPatchModule(t *testing.T) { java_library { name: "bar", srcs: ["b.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "none", patch_module: "java.base", } diff --git a/java/robolectric.go b/java/robolectric.go index b87ee0d6d..1de56a5cd 100644 --- a/java/robolectric.go +++ b/java/robolectric.go @@ -17,6 +17,7 @@ package java import ( "fmt" "io" + "strconv" "strings" "android/soong/android" @@ -40,6 +41,9 @@ type robolectricProperties struct { Test_options struct { // Timeout in seconds when running the tests. Timeout *int64 + + // Number of shards to use when running the tests. + Shards *int64 } } @@ -48,7 +52,8 @@ type robolectricTest struct { robolectricProperties robolectricProperties - libs []string + libs []string + tests []string } func (r *robolectricTest) DepsMutator(ctx android.BottomUpMutatorContext) { @@ -69,6 +74,39 @@ func (r *robolectricTest) GenerateAndroidBuildActions(ctx android.ModuleContext) for _, dep := range ctx.GetDirectDepsWithTag(libTag) { r.libs = append(r.libs, ctx.OtherModuleName(dep)) } + + // TODO: this could all be removed if tradefed was used as the test runner, it will find everything + // annotated as a test and run it. + for _, src := range r.compiledJavaSrcs { + s := src.Rel() + if !strings.HasSuffix(s, "Test.java") { + continue + } else if strings.HasSuffix(s, "/BaseRobolectricTest.java") { + continue + } else if strings.HasPrefix(s, "src/") { + s = strings.TrimPrefix(s, "src/") + } + r.tests = append(r.tests, s) + } +} + +func shardTests(paths []string, shards int) [][]string { + if shards > len(paths) { + shards = len(paths) + } + if shards == 0 { + return nil + } + ret := make([][]string, 0, shards) + shardSize := (len(paths) + shards - 1) / shards + for len(paths) > shardSize { + ret = append(ret, paths[0:shardSize]) + paths = paths[shardSize:] + } + if len(paths) > 0 { + ret = append(ret, paths) + } + return ret } func (r *robolectricTest) AndroidMk() android.AndroidMkData { @@ -77,24 +115,50 @@ func (r *robolectricTest) AndroidMk() android.AndroidMkData { data.Custom = func(w io.Writer, name, prefix, moduleDir string, data android.AndroidMkData) { android.WriteAndroidMkData(w, data) - fmt.Fprintln(w, "") - fmt.Fprintln(w, "include $(CLEAR_VARS)") - fmt.Fprintln(w, "LOCAL_MODULE := Run"+name) - fmt.Fprintln(w, "LOCAL_JAVA_LIBRARIES :=", name) - fmt.Fprintln(w, "LOCAL_JAVA_LIBRARIES += ", strings.Join(r.libs, " ")) - fmt.Fprintln(w, "LOCAL_TEST_PACKAGE :=", String(r.robolectricProperties.Instrumentation_for)) - if t := r.robolectricProperties.Test_options.Timeout; t != nil { - fmt.Fprintln(w, "LOCAL_ROBOTEST_TIMEOUT :=", *t) + if s := r.robolectricProperties.Test_options.Shards; s != nil && *s > 1 { + shards := shardTests(r.tests, int(*s)) + for i, shard := range shards { + r.writeTestRunner(w, name, "Run"+name+strconv.Itoa(i), shard) + } + + // TODO: add rules to dist the outputs of the individual tests, or combine them together? + fmt.Fprintln(w, "") + fmt.Fprintln(w, ".PHONY:", "Run"+name) + fmt.Fprintln(w, "Run"+name, ": \\") + for i := range shards { + fmt.Fprintln(w, " ", "Run"+name+strconv.Itoa(i), "\\") + } + fmt.Fprintln(w, "") + } else { + r.writeTestRunner(w, name, "Run"+name, r.tests) } - fmt.Fprintln(w, "-include external/robolectric-shadows/run_robotests.mk") } return data } +func (r *robolectricTest) writeTestRunner(w io.Writer, module, name string, tests []string) { + fmt.Fprintln(w, "") + fmt.Fprintln(w, "include $(CLEAR_VARS)") + fmt.Fprintln(w, "LOCAL_MODULE :=", name) + fmt.Fprintln(w, "LOCAL_JAVA_LIBRARIES :=", module) + fmt.Fprintln(w, "LOCAL_JAVA_LIBRARIES += ", strings.Join(r.libs, " ")) + fmt.Fprintln(w, "LOCAL_TEST_PACKAGE :=", String(r.robolectricProperties.Instrumentation_for)) + fmt.Fprintln(w, "LOCAL_ROBOTEST_FILES :=", strings.Join(tests, " ")) + if t := r.robolectricProperties.Test_options.Timeout; t != nil { + fmt.Fprintln(w, "LOCAL_ROBOTEST_TIMEOUT :=", *t) + } + fmt.Fprintln(w, "-include external/robolectric-shadows/run_robotests.mk") + +} + // An android_robolectric_test module compiles tests against the Robolectric framework that can run on the local host // instead of on a device. It also generates a rule with the name of the module prefixed with "Run" that can be // used to run the tests. Running the tests with build rule will eventually be deprecated and replaced with atest. +// +// The test runner considers any file listed in srcs whose name ends with Test.java to be a test class, unless +// it is named BaseRobolectricTest.java. The path to the each source file must exactly match the package +// name, or match the package name when the prefix "src/" is removed. func RobolectricTestFactory() android.Module { module := &robolectricTest{} diff --git a/java/robolectric_test.go b/java/robolectric_test.go new file mode 100644 index 000000000..e89c6e74c --- /dev/null +++ b/java/robolectric_test.go @@ -0,0 +1,88 @@ +// Copyright 2019 Google Inc. 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 java + +import ( + "reflect" + "testing" +) + +func Test_shardTests(t *testing.T) { + type args struct { + paths []string + shards int + } + tests := []struct { + name string + args args + want [][]string + }{ + { + name: "empty", + args: args{ + paths: nil, + shards: 1, + }, + want: [][]string(nil), + }, + { + name: "too many shards", + args: args{ + paths: []string{"a", "b"}, + shards: 3, + }, + want: [][]string{{"a"}, {"b"}}, + }, + { + name: "single shard", + args: args{ + paths: []string{"a", "b"}, + shards: 1, + }, + want: [][]string{{"a", "b"}}, + }, + { + name: "shard per input", + args: args{ + paths: []string{"a", "b", "c"}, + shards: 3, + }, + want: [][]string{{"a"}, {"b"}, {"c"}}, + }, + { + name: "balanced shards", + args: args{ + paths: []string{"a", "b", "c", "d"}, + shards: 2, + }, + want: [][]string{{"a", "b"}, {"c", "d"}}, + }, + { + name: "unbalanced shards", + args: args{ + paths: []string{"a", "b", "c"}, + shards: 2, + }, + want: [][]string{{"a", "b"}, {"c"}}, + }, + } + for _, tt := range tests { + t.Run(tt.name, func(t *testing.T) { + if got := shardTests(tt.args.paths, tt.args.shards); !reflect.DeepEqual(got, tt.want) { + t.Errorf("shardTests() = %v, want %v", got, tt.want) + } + }) + } +} diff --git a/java/sdk.go b/java/sdk.go index 90b8fac28..6ffe399fb 100644 --- a/java/sdk.go +++ b/java/sdk.go @@ -38,17 +38,20 @@ var sdkFrameworkAidlPathKey = android.NewOnceKey("sdkFrameworkAidlPathKey") var apiFingerprintPathKey = android.NewOnceKey("apiFingerprintPathKey") type sdkContext interface { - // sdkVersion eturns the sdk_version property of the current module, or an empty string if it is not set. + // sdkVersion returns the sdk_version property of the current module, or an empty string if it is not set. sdkVersion() string // minSdkVersion returns the min_sdk_version property of the current module, or sdkVersion() if it is not set. minSdkVersion() string // targetSdkVersion returns the target_sdk_version property of the current module, or sdkVersion() if it is not set. targetSdkVersion() string + + // Temporarily provide access to the no_frameworks_libs property (where present). + noFrameworkLibs() bool } func sdkVersionOrDefault(ctx android.BaseModuleContext, v string) string { switch v { - case "", "current", "system_current", "test_current", "core_current": + case "", "none", "current", "test_current", "system_current", "core_current", "core_platform": return ctx.Config().DefaultAppTargetSdk() default: return v @@ -59,7 +62,7 @@ func sdkVersionOrDefault(ctx android.BaseModuleContext, v string) string { // it returns android.FutureApiLevel (10000). func sdkVersionToNumber(ctx android.BaseModuleContext, v string) (int, error) { switch v { - case "", "current", "test_current", "system_current", "core_current": + case "", "none", "current", "test_current", "system_current", "core_current", "core_platform": return ctx.Config().DefaultAppTargetSdkInt(), nil default: n := android.GetNumericSdkVersion(v) @@ -138,6 +141,9 @@ func decodeSdkDep(ctx android.BaseModuleContext, sdkContext sdkContext) sdkDep { useFiles: true, jars: android.Paths{jarPath.Path(), lambdaStubsPath}, aidl: android.OptionalPathForPath(aidlPath.Path()), + + // Pass value straight through for now to match previous behavior. + noFrameworksLibs: sdkContext.noFrameworkLibs(), } } @@ -148,6 +154,9 @@ func decodeSdkDep(ctx android.BaseModuleContext, sdkContext sdkContext) sdkDep { systemModules: m + "_system_modules", frameworkResModule: r, aidl: android.OptionalPathForPath(aidl), + + // Pass value straight through for now to match previous behavior. + noFrameworksLibs: sdkContext.noFrameworkLibs(), } if m == "core.current.stubs" { @@ -173,7 +182,8 @@ func decodeSdkDep(ctx android.BaseModuleContext, sdkContext sdkContext) sdkDep { } } - if ctx.Config().UnbundledBuildUsePrebuiltSdks() && v != "" { + if ctx.Config().UnbundledBuildUsePrebuiltSdks() && + v != "" && v != "none" && v != "core_platform" { return toPrebuilt(v) } @@ -182,6 +192,19 @@ func decodeSdkDep(ctx android.BaseModuleContext, sdkContext sdkContext) sdkDep { return sdkDep{ useDefaultLibs: true, frameworkResModule: "framework-res", + + // Pass value straight through for now to match previous behavior. + noFrameworksLibs: sdkContext.noFrameworkLibs(), + } + case "none": + return sdkDep{ + noStandardLibs: true, + } + case "core_platform": + return sdkDep{ + useDefaultLibs: true, + frameworkResModule: "framework-res", + noFrameworksLibs: true, } case "current": return toModule("android_stubs_current", "framework-res", sdkFrameworkAidlPath(ctx)) diff --git a/java/sdk_library.go b/java/sdk_library.go index e38353340..b4a3f296c 100644 --- a/java/sdk_library.go +++ b/java/sdk_library.go @@ -159,7 +159,8 @@ func (module *SdkLibrary) DepsMutator(ctx android.BottomUpMutatorContext) { ctx.AddVariationDependencies(nil, publicApiStubsTag, module.stubsName(apiScopePublic)) ctx.AddVariationDependencies(nil, publicApiFileTag, module.docsName(apiScopePublic)) - if !Bool(module.properties.No_standard_libs) { + sdkDep := decodeSdkDep(ctx, sdkContext(&module.Library)) + if sdkDep.hasStandardLibs() { ctx.AddVariationDependencies(nil, systemApiStubsTag, module.stubsName(apiScopeSystem)) ctx.AddVariationDependencies(nil, systemApiFileTag, module.docsName(apiScopeSystem)) ctx.AddVariationDependencies(nil, testApiFileTag, module.docsName(apiScopeTest)) @@ -384,7 +385,6 @@ func (module *SdkLibrary) createStubsLibrary(mctx android.LoadHookContext, apiSc Device_specific *bool Product_specific *bool Compile_dex *bool - No_standard_libs *bool System_modules *string Java_version *string Product_variables struct { @@ -401,17 +401,22 @@ func (module *SdkLibrary) createStubsLibrary(mctx android.LoadHookContext, apiSc } }{} + sdkVersion := module.sdkVersion(apiScope) + sdkDep := decodeSdkDep(mctx, sdkContext(&module.Library)) + if !sdkDep.hasStandardLibs() { + sdkVersion = "none" + } + props.Name = proptools.StringPtr(module.stubsName(apiScope)) // sources are generated from the droiddoc props.Srcs = []string{":" + module.docsName(apiScope)} - props.Sdk_version = proptools.StringPtr(module.sdkVersion(apiScope)) + props.Sdk_version = proptools.StringPtr(sdkVersion) props.Libs = module.sdkLibraryProperties.Stub_only_libs // Unbundled apps will use the prebult one from /prebuilts/sdk if mctx.Config().UnbundledBuildUsePrebuiltSdks() { props.Product_variables.Unbundled_build.Enabled = proptools.BoolPtr(false) } props.Product_variables.Pdk.Enabled = proptools.BoolPtr(false) - props.No_standard_libs = module.Library.Module.properties.No_standard_libs props.System_modules = module.Library.Module.deviceProperties.System_modules props.Openjdk9.Srcs = module.Library.Module.properties.Openjdk9.Srcs props.Openjdk9.Javacflags = module.Library.Module.properties.Openjdk9.Javacflags @@ -441,13 +446,13 @@ func (module *SdkLibrary) createDocs(mctx android.LoadHookContext, apiScope apiS Srcs_lib *string Srcs_lib_whitelist_dirs []string Srcs_lib_whitelist_pkgs []string + Sdk_version *string Libs []string Arg_files []string Args *string Api_tag_name *string Api_filename *string Removed_api_filename *string - No_standard_libs *bool Java_version *string Merge_annotations_dirs []string Merge_inclusion_annotations_dirs []string @@ -462,9 +467,16 @@ func (module *SdkLibrary) createDocs(mctx android.LoadHookContext, apiScope apiS } }{} + sdkDep := decodeSdkDep(mctx, sdkContext(&module.Library)) + sdkVersion := "" + if !sdkDep.hasStandardLibs() { + sdkVersion = "none" + } + props.Name = proptools.StringPtr(module.docsName(apiScope)) props.Srcs = append(props.Srcs, module.Library.Module.properties.Srcs...) props.Srcs = append(props.Srcs, module.sdkLibraryProperties.Api_srcs...) + props.Sdk_version = proptools.StringPtr(sdkVersion) props.Installable = proptools.BoolPtr(false) // A droiddoc module has only one Libs property and doesn't distinguish between // shared libs and static libs. So we need to add both of these libs to Libs property. @@ -472,7 +484,6 @@ func (module *SdkLibrary) createDocs(mctx android.LoadHookContext, apiScope apiS props.Libs = append(props.Libs, module.Library.Module.properties.Static_libs...) props.Aidl.Include_dirs = module.Library.Module.deviceProperties.Aidl.Include_dirs props.Aidl.Local_include_dirs = module.Library.Module.deviceProperties.Aidl.Local_include_dirs - props.No_standard_libs = module.Library.Module.properties.No_standard_libs props.Java_version = module.Library.Module.properties.Java_version props.Merge_annotations_dirs = module.sdkLibraryProperties.Merge_annotations_dirs @@ -593,7 +604,7 @@ func (module *SdkLibrary) createXmlFile(mctx android.LoadHookContext) { func (module *SdkLibrary) PrebuiltJars(ctx android.BaseModuleContext, sdkVersion string) android.Paths { var api, v string - if sdkVersion == "" { + if sdkVersion == "" || sdkVersion == "none" { api = "system" v = "current" } else if strings.Contains(sdkVersion, "_") { @@ -701,7 +712,8 @@ func (module *SdkLibrary) CreateInternalModules(mctx android.LoadHookContext) { module.createStubsLibrary(mctx, apiScopePublic) module.createDocs(mctx, apiScopePublic) - if !Bool(module.properties.No_standard_libs) { + sdkDep := decodeSdkDep(mctx, sdkContext(&module.Library)) + if sdkDep.hasStandardLibs() { // for system API stubs module.createStubsLibrary(mctx, apiScopeSystem) module.createDocs(mctx, apiScopeSystem) diff --git a/java/sdk_test.go b/java/sdk_test.go index 23d7a98be..953c3722f 100644 --- a/java/sdk_test.go +++ b/java/sdk_test.go @@ -55,6 +55,14 @@ func TestClasspath(t *testing.T) { aidl: "", }, { + name: `sdk_version:"core_platform"`, + properties: `sdk_version:"core_platform"`, + bootclasspath: config.DefaultBootclasspathLibraries, + system: config.DefaultSystemModules, + classpath: []string{}, + aidl: "", + }, + { name: "blank sdk version", properties: `sdk_version: "",`, bootclasspath: config.DefaultBootclasspathLibraries, @@ -114,7 +122,7 @@ func TestClasspath(t *testing.T) { { name: "nostdlib", - properties: `no_standard_libs: true, system_modules: "none"`, + properties: `sdk_version: "none", system_modules: "none"`, system: "none", bootclasspath: []string{`""`}, classpath: []string{}, @@ -122,7 +130,7 @@ func TestClasspath(t *testing.T) { { name: "nostdlib system_modules", - properties: `no_standard_libs: true, system_modules: "core-platform-api-stubs-system-modules"`, + properties: `sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules"`, system: "core-platform-api-stubs-system-modules", bootclasspath: []string{`""`}, classpath: []string{}, @@ -147,7 +155,7 @@ func TestClasspath(t *testing.T) { { name: "host supported nostdlib", host: android.Host, - properties: `host_supported: true, no_standard_libs: true, system_modules: "none"`, + properties: `host_supported: true, sdk_version: "none", system_modules: "none"`, classpath: []string{}, }, { @@ -246,7 +254,7 @@ func TestClasspath(t *testing.T) { if testcase.system == "none" { system = "--system=none" } else if testcase.system != "" { - system = "--system=" + filepath.Join(buildDir, ".intermediates", testcase.system, "android_common", "system") + "/" + system = "--system=" + filepath.Join(buildDir, ".intermediates", testcase.system, "android_common", "system") } checkClasspath := func(t *testing.T, ctx *android.TestContext) { diff --git a/java/system_modules.go b/java/system_modules.go index 2ec3dfbd5..f71f4523f 100644 --- a/java/system_modules.go +++ b/java/system_modules.go @@ -61,7 +61,7 @@ var ( "moduleName", "classpath", "outDir", "workDir") ) -func TransformJarsToSystemModules(ctx android.ModuleContext, moduleName string, jars android.Paths) android.WritablePath { +func TransformJarsToSystemModules(ctx android.ModuleContext, moduleName string, jars android.Paths) (android.Path, android.Paths) { outDir := android.PathForModuleOut(ctx, "system") workDir := android.PathForModuleOut(ctx, "modules") outputFile := android.PathForModuleOut(ctx, "system/lib/modules") @@ -84,7 +84,7 @@ func TransformJarsToSystemModules(ctx android.ModuleContext, moduleName string, }, }) - return outputFile + return outDir, outputs.Paths() } func SystemModulesFactory() android.Module { @@ -101,18 +101,13 @@ type SystemModules struct { properties SystemModulesProperties - outputFile android.Path + outputDir android.Path + outputDeps android.Paths } type SystemModulesProperties struct { // List of java library modules that should be included in the system modules Libs []string - - // List of prebuilt jars that should be included in the system modules - Jars []string - - // Sdk version that should be included in the system modules - Sdk_version *string } func (system *SystemModules) GenerateAndroidBuildActions(ctx android.ModuleContext) { @@ -123,9 +118,7 @@ func (system *SystemModules) GenerateAndroidBuildActions(ctx android.ModuleConte jars = append(jars, dep.HeaderJars()...) }) - jars = append(jars, android.PathsForModuleSrc(ctx, system.properties.Jars)...) - - system.outputFile = TransformJarsToSystemModules(ctx, "java.base", jars) + system.outputDir, system.outputDeps = TransformJarsToSystemModules(ctx, "java.base", jars) } func (system *SystemModules) DepsMutator(ctx android.BottomUpMutatorContext) { @@ -135,16 +128,22 @@ func (system *SystemModules) DepsMutator(ctx android.BottomUpMutatorContext) { func (system *SystemModules) AndroidMk() android.AndroidMkData { return android.AndroidMkData{ Custom: func(w io.Writer, name, prefix, moduleDir string, data android.AndroidMkData) { + fmt.Fprintln(w) + makevar := "SOONG_SYSTEM_MODULES_" + name + fmt.Fprintln(w, makevar, ":=$=", system.outputDir.String()) fmt.Fprintln(w) - fmt.Fprintln(w, makevar, ":=", system.outputFile.String()) - fmt.Fprintln(w, ".KATI_READONLY", ":=", makevar) + + makevar = "SOONG_SYSTEM_MODULES_LIBS_" + name + fmt.Fprintln(w, makevar, ":=$=", strings.Join(system.properties.Libs, " ")) + fmt.Fprintln(w) + + makevar = "SOONG_SYSTEM_MODULE_DEPS_" + name + fmt.Fprintln(w, makevar, ":=$=", strings.Join(system.outputDeps.Strings(), " ")) + fmt.Fprintln(w) + fmt.Fprintln(w, name+":", "$("+makevar+")") fmt.Fprintln(w, ".PHONY:", name) - fmt.Fprintln(w) - makevar = "SOONG_SYSTEM_MODULES_LIBS_" + name - fmt.Fprintln(w, makevar, ":=", strings.Join(system.properties.Libs, " ")) - fmt.Fprintln(w, ".KATI_READONLY :=", makevar) }, } } diff --git a/java/testing.go b/java/testing.go index a9d4670fc..5d116a787 100644 --- a/java/testing.go +++ b/java/testing.go @@ -54,7 +54,7 @@ func GatherRequiredDepsForTest() string { java_library { name: "%s", srcs: ["a.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules", } `, extra) @@ -64,7 +64,7 @@ func GatherRequiredDepsForTest() string { java_library { name: "framework", srcs: ["a.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules", aidl: { export_include_dirs: ["framework/aidl"], @@ -73,13 +73,13 @@ func GatherRequiredDepsForTest() string { android_app { name: "framework-res", - no_framework_libs: true, + sdk_version: "core_platform", } java_library { name: "android.hidl.base-V1.0-java", srcs: ["a.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules", installable: true, } @@ -87,7 +87,7 @@ func GatherRequiredDepsForTest() string { java_library { name: "android.hidl.manager-V1.0-java", srcs: ["a.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules", installable: true, } @@ -95,7 +95,7 @@ func GatherRequiredDepsForTest() string { java_library { name: "org.apache.http.legacy", srcs: ["a.java"], - no_standard_libs: true, + sdk_version: "none", system_modules: "core-platform-api-stubs-system-modules", installable: true, } |