Merge changes I8466db71,I83180699 into main am: e50b0f5558

Original change: https://android-review.googlesource.com/c/platform/build/soong/+/2752165

Change-Id: Ic32fdf1452442b879c86d52f94f9de03317ae566
Signed-off-by: Automerger Merge Worker <android-build-automerger-merge-worker@system.gserviceaccount.com>
This commit is contained in:
Treehugger Robot 2023-09-18 23:15:08 +00:00 committed by Automerger Merge Worker
commit 0efaada4cd
2 changed files with 99 additions and 21 deletions

View file

@ -64,6 +64,7 @@ func registerJavaBuildComponents(ctx android.RegistrationContext) {
ctx.RegisterModuleType("dex_import", DexImportFactory) ctx.RegisterModuleType("dex_import", DexImportFactory)
ctx.RegisterModuleType("java_api_library", ApiLibraryFactory) ctx.RegisterModuleType("java_api_library", ApiLibraryFactory)
ctx.RegisterModuleType("java_api_contribution", ApiContributionFactory) ctx.RegisterModuleType("java_api_contribution", ApiContributionFactory)
ctx.RegisterModuleType("java_api_contribution_import", ApiContributionImportFactory)
// This mutator registers dependencies on dex2oat for modules that should be // This mutator registers dependencies on dex2oat for modules that should be
// dexpreopted. This is done late when the final variants have been // dexpreopted. This is done late when the final variants have been
@ -1623,7 +1624,8 @@ func ApiContributionFactory() android.Module {
} }
type JavaApiImportInfo struct { type JavaApiImportInfo struct {
ApiFile android.Path ApiFile android.Path
ApiSurface string
} }
var JavaApiImportProvider = blueprint.NewProvider(JavaApiImportInfo{}) var JavaApiImportProvider = blueprint.NewProvider(JavaApiImportInfo{})
@ -1635,7 +1637,8 @@ func (ap *JavaApiContribution) GenerateAndroidBuildActions(ctx android.ModuleCon
} }
ctx.SetProvider(JavaApiImportProvider, JavaApiImportInfo{ ctx.SetProvider(JavaApiImportProvider, JavaApiImportInfo{
ApiFile: apiFile, ApiFile: apiFile,
ApiSurface: proptools.String(ap.properties.Api_surface),
}) })
} }
@ -1821,18 +1824,29 @@ func (al *ApiLibrary) DepsMutator(ctx android.BottomUpMutatorContext) {
var scopeOrderedSourceFileNames = allApiScopes.Strings( var scopeOrderedSourceFileNames = allApiScopes.Strings(
func(s *apiScope) string { return s.apiFilePrefix + "current.txt" }) func(s *apiScope) string { return s.apiFilePrefix + "current.txt" })
func (al *ApiLibrary) sortApiFilesByApiScope(ctx android.ModuleContext, srcFiles android.Paths) android.Paths { func (al *ApiLibrary) sortApiFilesByApiScope(ctx android.ModuleContext, srcFilesInfo []JavaApiImportInfo, apiFiles android.Paths) android.Paths {
sortedSrcFiles := android.Paths{} var sortedSrcFiles android.Paths
for _, scopeSourceFileName := range scopeOrderedSourceFileNames { for i, apiScope := range allApiScopes {
for _, sourceFileName := range srcFiles { for _, srcFileInfo := range srcFilesInfo {
if sourceFileName.Base() == scopeSourceFileName { if srcFileInfo.ApiFile.Base() == scopeOrderedSourceFileNames[i] || srcFileInfo.ApiSurface == apiScope.name {
sortedSrcFiles = append(sortedSrcFiles, sourceFileName) sortedSrcFiles = append(sortedSrcFiles, android.PathForSource(ctx, srcFileInfo.ApiFile.String()))
}
}
// TODO: b/300964421 - Remove when api_files property is removed
for _, apiFileName := range apiFiles {
if apiFileName.Base() == scopeOrderedSourceFileNames[i] {
sortedSrcFiles = append(sortedSrcFiles, apiFileName)
} }
} }
} }
if len(srcFiles) != len(sortedSrcFiles) {
ctx.ModuleErrorf("Unrecognizable source file found within %s", srcFiles) if len(srcFilesInfo)+len(apiFiles) != len(sortedSrcFiles) {
var srcFiles android.Paths
for _, srcFileInfo := range srcFilesInfo {
srcFiles = append(srcFiles, srcFileInfo.ApiFile)
}
ctx.ModuleErrorf("Unrecognizable source file found within %s", append(srcFiles, apiFiles...))
} }
return sortedSrcFiles return sortedSrcFiles
@ -1853,7 +1867,7 @@ func (al *ApiLibrary) GenerateAndroidBuildActions(ctx android.ModuleContext) {
homeDir := android.PathForModuleOut(ctx, "metalava", "home") homeDir := android.PathForModuleOut(ctx, "metalava", "home")
var srcFiles android.Paths var srcFilesInfo []JavaApiImportInfo
var classPaths android.Paths var classPaths android.Paths
var staticLibs android.Paths var staticLibs android.Paths
var depApiSrcsStubsJar android.Path var depApiSrcsStubsJar android.Path
@ -1862,11 +1876,10 @@ func (al *ApiLibrary) GenerateAndroidBuildActions(ctx android.ModuleContext) {
switch tag { switch tag {
case javaApiContributionTag: case javaApiContributionTag:
provider := ctx.OtherModuleProvider(dep, JavaApiImportProvider).(JavaApiImportInfo) provider := ctx.OtherModuleProvider(dep, JavaApiImportProvider).(JavaApiImportInfo)
providerApiFile := provider.ApiFile if provider.ApiFile == nil && !ctx.Config().AllowMissingDependencies() {
if providerApiFile == nil && !ctx.Config().AllowMissingDependencies() {
ctx.ModuleErrorf("Error: %s has an empty api file.", dep.Name()) ctx.ModuleErrorf("Error: %s has an empty api file.", dep.Name())
} }
srcFiles = append(srcFiles, android.PathForSource(ctx, providerApiFile.String())) srcFilesInfo = append(srcFilesInfo, provider)
case libTag: case libTag:
provider := ctx.OtherModuleProvider(dep, JavaInfoProvider).(JavaInfo) provider := ctx.OtherModuleProvider(dep, JavaInfoProvider).(JavaInfo)
classPaths = append(classPaths, provider.HeaderJars...) classPaths = append(classPaths, provider.HeaderJars...)
@ -1880,16 +1893,19 @@ func (al *ApiLibrary) GenerateAndroidBuildActions(ctx android.ModuleContext) {
}) })
// Add the api_files inputs // Add the api_files inputs
// These are api files in the module subdirectory, which are not provided by
// java_api_contribution but provided directly as module property.
var apiFiles android.Paths
for _, api := range al.properties.Api_files { for _, api := range al.properties.Api_files {
srcFiles = append(srcFiles, android.PathForModuleSrc(ctx, api)) apiFiles = append(apiFiles, android.PathForModuleSrc(ctx, api))
} }
srcFiles := al.sortApiFilesByApiScope(ctx, srcFilesInfo, apiFiles)
if srcFiles == nil && !ctx.Config().AllowMissingDependencies() { if srcFiles == nil && !ctx.Config().AllowMissingDependencies() {
ctx.ModuleErrorf("Error: %s has an empty api file.", ctx.ModuleName()) ctx.ModuleErrorf("Error: %s has an empty api file.", ctx.ModuleName())
} }
srcFiles = al.sortApiFilesByApiScope(ctx, srcFiles)
cmd := metalavaStubCmd(ctx, rule, srcFiles, homeDir) cmd := metalavaStubCmd(ctx, rule, srcFiles, homeDir)
al.stubsFlags(ctx, cmd, stubsDir) al.stubsFlags(ctx, cmd, stubsDir)
@ -3428,3 +3444,30 @@ func (i *Import) QueueBazelCall(ctx android.BaseModuleContext) {
func (i *Import) IsMixedBuildSupported(ctx android.BaseModuleContext) bool { func (i *Import) IsMixedBuildSupported(ctx android.BaseModuleContext) bool {
return true return true
} }
type JavaApiContributionImport struct {
JavaApiContribution
prebuilt android.Prebuilt
}
func ApiContributionImportFactory() android.Module {
module := &JavaApiContributionImport{}
android.InitAndroidModule(module)
android.InitDefaultableModule(module)
android.InitPrebuiltModule(module, &[]string{""})
module.AddProperties(&module.properties)
return module
}
func (module *JavaApiContributionImport) Prebuilt() *android.Prebuilt {
return &module.prebuilt
}
func (module *JavaApiContributionImport) Name() string {
return module.prebuilt.Name(module.ModuleBase.Name())
}
func (ap *JavaApiContributionImport) GenerateAndroidBuildActions(ctx android.ModuleContext) {
ap.JavaApiContribution.GenerateAndroidBuildActions(ctx)
}

View file

@ -1865,11 +1865,13 @@ func TestJavaApiLibraryAndProviderLink(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := `java_api_contribution { provider_bp_b := `java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
ctx, _ := testJavaWithFS(t, ` ctx, _ := testJavaWithFS(t, `
@ -1919,24 +1921,28 @@ func TestJavaApiLibraryAndDefaultsLink(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := ` provider_bp_b := `
java_api_contribution { java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_c := ` provider_bp_c := `
java_api_contribution { java_api_contribution {
name: "foo3", name: "foo3",
api_file: "current.txt", api_file: "system-current.txt",
api_surface: "system",
} }
` `
provider_bp_d := ` provider_bp_d := `
java_api_contribution { java_api_contribution {
name: "foo4", name: "foo4",
api_file: "current.txt", api_file: "system-current.txt",
api_surface: "system",
} }
` `
ctx, _ := testJavaWithFS(t, ` ctx, _ := testJavaWithFS(t, `
@ -1992,8 +1998,9 @@ func TestJavaApiLibraryAndDefaultsLink(t *testing.T) {
sourceTextFileDirs: []string{"a/current.txt", "b/current.txt"}, sourceTextFileDirs: []string{"a/current.txt", "b/current.txt"},
}, },
{ {
moduleName: "bar3", moduleName: "bar3",
sourceTextFileDirs: []string{"c/current.txt", "a/current.txt", "b/current.txt", "d/current.txt", "api1/current.txt", "api2/current.txt"}, // API text files need to be sorted from the narrower api scope to the wider api scope
sourceTextFileDirs: []string{"a/current.txt", "b/current.txt", "api1/current.txt", "api2/current.txt", "c/system-current.txt", "d/system-current.txt"},
}, },
} }
for _, c := range testcases { for _, c := range testcases {
@ -2011,12 +2018,14 @@ func TestJavaApiLibraryJarGeneration(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := ` provider_bp_b := `
java_api_contribution { java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
ctx, _ := testJavaWithFS(t, ` ctx, _ := testJavaWithFS(t, `
@ -2064,12 +2073,14 @@ func TestJavaApiLibraryLibsLink(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := ` provider_bp_b := `
java_api_contribution { java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
lib_bp_a := ` lib_bp_a := `
@ -2139,12 +2150,14 @@ func TestJavaApiLibraryStaticLibsLink(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := ` provider_bp_b := `
java_api_contribution { java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
lib_bp_a := ` lib_bp_a := `
@ -2213,12 +2226,14 @@ func TestJavaApiLibraryFullApiSurfaceStub(t *testing.T) {
java_api_contribution { java_api_contribution {
name: "foo1", name: "foo1",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
provider_bp_b := ` provider_bp_b := `
java_api_contribution { java_api_contribution {
name: "foo2", name: "foo2",
api_file: "current.txt", api_file: "current.txt",
api_surface: "public",
} }
` `
lib_bp_a := ` lib_bp_a := `
@ -2388,3 +2403,23 @@ func TestHeadersOnly(t *testing.T) {
javac := ctx.ModuleForTests("foo", "android_common").MaybeRule("javac") javac := ctx.ModuleForTests("foo", "android_common").MaybeRule("javac")
android.AssertDeepEquals(t, "javac rule", nil, javac.Rule) android.AssertDeepEquals(t, "javac rule", nil, javac.Rule)
} }
func TestJavaApiContributionImport(t *testing.T) {
ctx, _ := testJava(t, `
java_api_library {
name: "foo",
api_contributions: ["bar"],
}
java_api_contribution_import {
name: "bar",
api_file: "current.txt",
api_surface: "public",
}
`)
m := ctx.ModuleForTests("foo", "android_common")
manifest := m.Output("metalava.sbox.textproto")
sboxProto := android.RuleBuilderSboxProtoForTests(t, manifest)
manifestCommand := sboxProto.Commands[0].GetCommand()
sourceFilesFlag := "--source-files current.txt"
android.AssertStringDoesContain(t, "source text files not present", manifestCommand, sourceFilesFlag)
}