Refactor around apex aconfig files (#2)
Aconfig files are treated like other files in APEX. This way, we can dedup the code hanlding those files (copy commands, fs_config, etc). Bug: n/a Test: m nothing --no-skip-soong-tests Change-Id: Ia9f2186e4e54e92ad90c7a9c00474cb0f7519a31
This commit is contained in:
25
apex/apex.go
25
apex/apex.go
@@ -2294,26 +2294,6 @@ func (a *apexBundle) depVisitor(vctx *visitorContext, ctx android.ModuleContext,
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
func collectAconfigFiles(ctx android.ModuleContext, apexFiles []apexFile) android.Paths {
|
|
||||||
var aconfigFiles android.Paths
|
|
||||||
for _, file := range apexFiles {
|
|
||||||
if file.module == nil {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if dep, ok := android.OtherModuleProvider(ctx, file.module, android.AconfigPropagatingProviderKey); ok {
|
|
||||||
if len(dep.AconfigFiles) > 0 && dep.AconfigFiles[ctx.ModuleName()] != nil {
|
|
||||||
aconfigFiles = append(aconfigFiles, dep.AconfigFiles[ctx.ModuleName()]...)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
validationFlag := ctx.DeviceConfig().AconfigContainerValidation()
|
|
||||||
if validationFlag == "error" || validationFlag == "warning" {
|
|
||||||
android.VerifyAconfigBuildMode(ctx, ctx.ModuleName(), file.module, validationFlag == "error")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return android.FirstUniquePaths(aconfigFiles)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (a *apexBundle) shouldCheckDuplicate(ctx android.ModuleContext) bool {
|
func (a *apexBundle) shouldCheckDuplicate(ctx android.ModuleContext) bool {
|
||||||
// TODO(b/263308293) remove this
|
// TODO(b/263308293) remove this
|
||||||
if a.properties.IsCoverageVariant {
|
if a.properties.IsCoverageVariant {
|
||||||
@@ -2395,12 +2375,15 @@ func (a *apexBundle) GenerateAndroidBuildActions(ctx android.ModuleContext) {
|
|||||||
// 3) some fields in apexBundle struct are configured
|
// 3) some fields in apexBundle struct are configured
|
||||||
a.installDir = android.PathForModuleInstall(ctx, "apex")
|
a.installDir = android.PathForModuleInstall(ctx, "apex")
|
||||||
a.filesInfo = vctx.filesInfo
|
a.filesInfo = vctx.filesInfo
|
||||||
a.aconfigFiles = collectAconfigFiles(ctx, a.filesInfo)
|
|
||||||
|
|
||||||
a.setPayloadFsType(ctx)
|
a.setPayloadFsType(ctx)
|
||||||
a.setSystemLibLink(ctx)
|
a.setSystemLibLink(ctx)
|
||||||
a.compatSymlinks = makeCompatSymlinks(a.BaseModuleName(), ctx)
|
a.compatSymlinks = makeCompatSymlinks(a.BaseModuleName(), ctx)
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
// 3.a) some artifacts are generated from the collected files
|
||||||
|
a.filesInfo = append(a.filesInfo, a.buildAconfigFiles(ctx)...)
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
// 4) generate the build rules to create the APEX. This is done in builder.go.
|
// 4) generate the build rules to create the APEX. This is done in builder.go.
|
||||||
a.buildManifest(ctx, vctx.provideNativeLibs, vctx.requireNativeLibs)
|
a.buildManifest(ctx, vctx.provideNativeLibs, vctx.requireNativeLibs)
|
||||||
|
@@ -267,6 +267,7 @@ func ensureNotContains(t *testing.T, result string, notExpected string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func ensureMatches(t *testing.T, result string, expectedRex string) {
|
func ensureMatches(t *testing.T, result string, expectedRex string) {
|
||||||
|
t.Helper()
|
||||||
ok, err := regexp.MatchString(expectedRex, result)
|
ok, err := regexp.MatchString(expectedRex, result)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
t.Fatalf("regexp failure trying to match %s against `%s` expression: %s", result, expectedRex, err)
|
t.Fatalf("regexp failure trying to match %s against `%s` expression: %s", result, expectedRex, err)
|
||||||
@@ -277,6 +278,14 @@ func ensureMatches(t *testing.T, result string, expectedRex string) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func ensureListContainsMatch(t *testing.T, result []string, expectedRex string) {
|
||||||
|
t.Helper()
|
||||||
|
p := regexp.MustCompile(expectedRex)
|
||||||
|
if android.IndexListPred(func(s string) bool { return p.MatchString(s) }, result) == -1 {
|
||||||
|
t.Errorf("%q is not found in %v", expectedRex, result)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func ensureListContains(t *testing.T, result []string, expected string) {
|
func ensureListContains(t *testing.T, result []string, expected string) {
|
||||||
t.Helper()
|
t.Helper()
|
||||||
if !android.InList(expected, result) {
|
if !android.InList(expected, result) {
|
||||||
@@ -10791,14 +10800,14 @@ func TestAconfigFilesJavaDeps(t *testing.T) {
|
|||||||
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
||||||
s := mod.Rule("apexRule").Args["copy_commands"]
|
s := mod.Rule("apexRule").Args["copy_commands"]
|
||||||
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
||||||
if len(copyCmds) != 8 {
|
if len(copyCmds) != 12 {
|
||||||
t.Fatalf("Expected 5 commands, got %d in:\n%s", len(copyCmds), s)
|
t.Fatalf("Expected 12 commands, got %d in:\n%s", len(copyCmds), s)
|
||||||
}
|
}
|
||||||
|
|
||||||
ensureMatches(t, copyCmds[4], "^cp -f .*/aconfig_flags.pb .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/aconfig_flags.pb .*/image.apex/etc/aconfig_flags.pb")
|
||||||
ensureMatches(t, copyCmds[5], "^cp -f .*/package.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/package.map .*/image.apex/etc/package.map")
|
||||||
ensureMatches(t, copyCmds[6], "^cp -f .*/flag.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.map .*/image.apex/etc/flag.map")
|
||||||
ensureMatches(t, copyCmds[7], "^cp -f .*/flag.val .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.val .*/image.apex/etc/flag.val")
|
||||||
|
|
||||||
inputs := []string{
|
inputs := []string{
|
||||||
"my_aconfig_declarations_foo/intermediate.pb",
|
"my_aconfig_declarations_foo/intermediate.pb",
|
||||||
@@ -10926,14 +10935,14 @@ func TestAconfigFilesJavaAndCcDeps(t *testing.T) {
|
|||||||
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
||||||
s := mod.Rule("apexRule").Args["copy_commands"]
|
s := mod.Rule("apexRule").Args["copy_commands"]
|
||||||
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
||||||
if len(copyCmds) != 12 {
|
if len(copyCmds) != 16 {
|
||||||
t.Fatalf("Expected 12 commands, got %d in:\n%s", len(copyCmds), s)
|
t.Fatalf("Expected 16 commands, got %d in:\n%s", len(copyCmds), s)
|
||||||
}
|
}
|
||||||
|
|
||||||
ensureMatches(t, copyCmds[8], "^cp -f .*/aconfig_flags.pb .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/aconfig_flags.pb .*/image.apex/etc/aconfig_flags.pb")
|
||||||
ensureMatches(t, copyCmds[9], "^cp -f .*/package.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/package.map .*/image.apex/etc/package.map")
|
||||||
ensureMatches(t, copyCmds[10], "^cp -f .*/flag.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.map .*/image.apex/etc/flag.map")
|
||||||
ensureMatches(t, copyCmds[11], "^cp -f .*/flag.val .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.val .*/image.apex/etc/flag.val")
|
||||||
|
|
||||||
inputs := []string{
|
inputs := []string{
|
||||||
"my_aconfig_declarations_foo/intermediate.pb",
|
"my_aconfig_declarations_foo/intermediate.pb",
|
||||||
@@ -11094,14 +11103,14 @@ func TestAconfigFilesRustDeps(t *testing.T) {
|
|||||||
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
mod := ctx.ModuleForTests("myapex", "android_common_myapex")
|
||||||
s := mod.Rule("apexRule").Args["copy_commands"]
|
s := mod.Rule("apexRule").Args["copy_commands"]
|
||||||
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
copyCmds := regexp.MustCompile(" *&& *").Split(s, -1)
|
||||||
if len(copyCmds) != 32 {
|
if len(copyCmds) != 36 {
|
||||||
t.Fatalf("Expected 28 commands, got %d in:\n%s", len(copyCmds), s)
|
t.Fatalf("Expected 36 commands, got %d in:\n%s", len(copyCmds), s)
|
||||||
}
|
}
|
||||||
|
|
||||||
ensureMatches(t, copyCmds[28], "^cp -f .*/aconfig_flags.pb .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/aconfig_flags.pb .*/image.apex/etc/aconfig_flags.pb")
|
||||||
ensureMatches(t, copyCmds[29], "^cp -f .*/package.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/package.map .*/image.apex/etc/package.map")
|
||||||
ensureMatches(t, copyCmds[30], "^cp -f .*/flag.map .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.map .*/image.apex/etc/flag.map")
|
||||||
ensureMatches(t, copyCmds[31], "^cp -f .*/flag.val .*/image.apex/etc$")
|
ensureListContainsMatch(t, copyCmds, "^cp -f .*/flag.val .*/image.apex/etc/flag.val")
|
||||||
|
|
||||||
inputs := []string{
|
inputs := []string{
|
||||||
"my_aconfig_declarations_foo/intermediate.pb",
|
"my_aconfig_declarations_foo/intermediate.pb",
|
||||||
|
@@ -262,6 +262,58 @@ var (
|
|||||||
}, "tool_path", "unwanted")
|
}, "tool_path", "unwanted")
|
||||||
)
|
)
|
||||||
|
|
||||||
|
func (a *apexBundle) buildAconfigFiles(ctx android.ModuleContext) []apexFile {
|
||||||
|
var aconfigFiles android.Paths
|
||||||
|
for _, file := range a.filesInfo {
|
||||||
|
if file.module == nil {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if dep, ok := android.OtherModuleProvider(ctx, file.module, android.AconfigPropagatingProviderKey); ok {
|
||||||
|
if len(dep.AconfigFiles) > 0 && dep.AconfigFiles[ctx.ModuleName()] != nil {
|
||||||
|
aconfigFiles = append(aconfigFiles, dep.AconfigFiles[ctx.ModuleName()]...)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
validationFlag := ctx.DeviceConfig().AconfigContainerValidation()
|
||||||
|
if validationFlag == "error" || validationFlag == "warning" {
|
||||||
|
android.VerifyAconfigBuildMode(ctx, ctx.ModuleName(), file.module, validationFlag == "error")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
aconfigFiles = android.FirstUniquePaths(aconfigFiles)
|
||||||
|
|
||||||
|
var files []apexFile
|
||||||
|
if len(aconfigFiles) > 0 {
|
||||||
|
apexAconfigFile := android.PathForModuleOut(ctx, "aconfig_flags.pb")
|
||||||
|
ctx.Build(pctx, android.BuildParams{
|
||||||
|
Rule: aconfig.AllDeclarationsRule,
|
||||||
|
Inputs: aconfigFiles,
|
||||||
|
Output: apexAconfigFile,
|
||||||
|
Description: "combine_aconfig_declarations",
|
||||||
|
Args: map[string]string{
|
||||||
|
"cache_files": android.JoinPathsWithPrefix(aconfigFiles, "--cache "),
|
||||||
|
},
|
||||||
|
})
|
||||||
|
files = append(files, newApexFile(ctx, apexAconfigFile, "aconfig_flags", "etc", etc, nil))
|
||||||
|
|
||||||
|
for _, info := range createStorageInfo {
|
||||||
|
outputFile := android.PathForModuleOut(ctx, info.Output_file)
|
||||||
|
ctx.Build(pctx, android.BuildParams{
|
||||||
|
Rule: aconfig.CreateStorageRule,
|
||||||
|
Inputs: aconfigFiles,
|
||||||
|
Output: outputFile,
|
||||||
|
Description: info.Desc,
|
||||||
|
Args: map[string]string{
|
||||||
|
"container": ctx.ModuleName(),
|
||||||
|
"file_type": info.File_type,
|
||||||
|
"cache_files": android.JoinPathsWithPrefix(aconfigFiles, "--cache "),
|
||||||
|
},
|
||||||
|
})
|
||||||
|
files = append(files, newApexFile(ctx, outputFile, info.File_type, "etc", etc, nil))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return files
|
||||||
|
}
|
||||||
|
|
||||||
// buildManifest creates buile rules to modify the input apex_manifest.json to add information
|
// buildManifest creates buile rules to modify the input apex_manifest.json to add information
|
||||||
// gathered by the build system such as provided/required native libraries. Two output files having
|
// gathered by the build system such as provided/required native libraries. Two output files having
|
||||||
// different formats are generated. a.manifestJsonOut is JSON format for Q devices, and
|
// different formats are generated. a.manifestJsonOut is JSON format for Q devices, and
|
||||||
@@ -644,48 +696,10 @@ func (a *apexBundle) buildApex(ctx android.ModuleContext) {
|
|||||||
outHostBinDir := ctx.Config().HostToolPath(ctx, "").String()
|
outHostBinDir := ctx.Config().HostToolPath(ctx, "").String()
|
||||||
prebuiltSdkToolsBinDir := filepath.Join("prebuilts", "sdk", "tools", runtime.GOOS, "bin")
|
prebuiltSdkToolsBinDir := filepath.Join("prebuilts", "sdk", "tools", runtime.GOOS, "bin")
|
||||||
|
|
||||||
defaultReadOnlyFiles := []string{"apex_manifest.json", "apex_manifest.pb"}
|
|
||||||
aconfigDest := imageDir.Join(ctx, "etc").String()
|
|
||||||
if len(a.aconfigFiles) > 0 {
|
|
||||||
apexAconfigFile := android.PathForModuleOut(ctx, "aconfig_flags.pb")
|
|
||||||
ctx.Build(pctx, android.BuildParams{
|
|
||||||
Rule: aconfig.AllDeclarationsRule,
|
|
||||||
Inputs: a.aconfigFiles,
|
|
||||||
Output: apexAconfigFile,
|
|
||||||
Description: "combine_aconfig_declarations",
|
|
||||||
Args: map[string]string{
|
|
||||||
"cache_files": android.JoinPathsWithPrefix(a.aconfigFiles, "--cache "),
|
|
||||||
},
|
|
||||||
})
|
|
||||||
|
|
||||||
copyCommands = append(copyCommands, "cp -f "+apexAconfigFile.String()+" "+aconfigDest)
|
|
||||||
implicitInputs = append(implicitInputs, apexAconfigFile)
|
|
||||||
defaultReadOnlyFiles = append(defaultReadOnlyFiles, "etc/"+apexAconfigFile.Base())
|
|
||||||
|
|
||||||
for _, info := range createStorageInfo {
|
|
||||||
outputFile := android.PathForModuleOut(ctx, info.Output_file)
|
|
||||||
ctx.Build(pctx, android.BuildParams{
|
|
||||||
Rule: aconfig.CreateStorageRule,
|
|
||||||
Inputs: a.aconfigFiles,
|
|
||||||
Output: outputFile,
|
|
||||||
Description: info.Desc,
|
|
||||||
Args: map[string]string{
|
|
||||||
"container": ctx.ModuleName(),
|
|
||||||
"file_type": info.File_type,
|
|
||||||
"cache_files": android.JoinPathsWithPrefix(a.aconfigFiles, "--cache "),
|
|
||||||
},
|
|
||||||
})
|
|
||||||
|
|
||||||
copyCommands = append(copyCommands, "cp -f "+outputFile.String()+" "+aconfigDest)
|
|
||||||
implicitInputs = append(implicitInputs, outputFile)
|
|
||||||
defaultReadOnlyFiles = append(defaultReadOnlyFiles, "etc/"+outputFile.Base())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////
|
||||||
// Step 2: create canned_fs_config which encodes filemode,uid,gid of each files
|
// Step 2: create canned_fs_config which encodes filemode,uid,gid of each files
|
||||||
// in this APEX. The file will be used by apexer in later steps.
|
// in this APEX. The file will be used by apexer in later steps.
|
||||||
cannedFsConfig := a.buildCannedFsConfig(ctx, defaultReadOnlyFiles)
|
cannedFsConfig := a.buildCannedFsConfig(ctx)
|
||||||
implicitInputs = append(implicitInputs, cannedFsConfig)
|
implicitInputs = append(implicitInputs, cannedFsConfig)
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////
|
||||||
@@ -1139,8 +1153,8 @@ func (a *apexBundle) buildLintReports(ctx android.ModuleContext) {
|
|||||||
a.lintReports = java.BuildModuleLintReportZips(ctx, depSetsBuilder.Build())
|
a.lintReports = java.BuildModuleLintReportZips(ctx, depSetsBuilder.Build())
|
||||||
}
|
}
|
||||||
|
|
||||||
func (a *apexBundle) buildCannedFsConfig(ctx android.ModuleContext, defaultReadOnlyFiles []string) android.OutputPath {
|
func (a *apexBundle) buildCannedFsConfig(ctx android.ModuleContext) android.OutputPath {
|
||||||
var readOnlyPaths = defaultReadOnlyFiles
|
var readOnlyPaths = []string{"apex_manifest.json", "apex_manifest.pb"}
|
||||||
var executablePaths []string // this also includes dirs
|
var executablePaths []string // this also includes dirs
|
||||||
var appSetDirs []string
|
var appSetDirs []string
|
||||||
appSetFiles := make(map[string]android.Path)
|
appSetFiles := make(map[string]android.Path)
|
||||||
|
Reference in New Issue
Block a user