Generate fake versions of modules excluded in directed vendor snapshot.
When using the directed vendor snapshot, the build fails because soong fails to find some variants of the modules that have been excluded from VENDOR_SNAPSHOT_MODULES, even though those modules are not going to be used by the build. The solution implemented here is to generate fake versions of those modules (empty files) and include them in the generated Android.bp, so that soong finds the modules, even though trying to use them would fail. Bug: 171821997 Bug: 179275601 Test: source build/envsetup.sh Test: m -j nothing Change-Id: Ibd3e963ab3e5504c0ac817f7cabbd241bf47a5cb
This commit is contained in:
parent
23c38fa9a7
commit
0a942a0368
3 changed files with 41 additions and 33 deletions
|
@ -266,7 +266,7 @@ func checkVndkModule(t *testing.T, ctx *android.TestContext, name, subDir string
|
|||
}
|
||||
}
|
||||
|
||||
func checkSnapshotIncludeExclude(t *testing.T, ctx *android.TestContext, singleton android.TestingSingleton, moduleName, snapshotFilename, subDir, variant string, include bool) {
|
||||
func checkSnapshotIncludeExclude(t *testing.T, ctx *android.TestContext, singleton android.TestingSingleton, moduleName, snapshotFilename, subDir, variant string, include bool, fake bool) {
|
||||
t.Helper()
|
||||
mod, ok := ctx.ModuleForTests(moduleName, variant).Module().(android.OutputFileProducer)
|
||||
if !ok {
|
||||
|
@ -282,8 +282,14 @@ func checkSnapshotIncludeExclude(t *testing.T, ctx *android.TestContext, singlet
|
|||
|
||||
if include {
|
||||
out := singleton.Output(snapshotPath)
|
||||
if out.Input.String() != outputFiles[0].String() {
|
||||
t.Errorf("The input of snapshot %q must be %q, but %q", moduleName, out.Input.String(), outputFiles[0])
|
||||
if fake {
|
||||
if out.Rule == nil {
|
||||
t.Errorf("Missing rule for module %q output file %q", moduleName, outputFiles[0])
|
||||
}
|
||||
} else {
|
||||
if out.Input.String() != outputFiles[0].String() {
|
||||
t.Errorf("The input of snapshot %q must be %q, but %q", moduleName, out.Input.String(), outputFiles[0])
|
||||
}
|
||||
}
|
||||
} else {
|
||||
out := singleton.MaybeOutput(snapshotPath)
|
||||
|
@ -294,11 +300,15 @@ func checkSnapshotIncludeExclude(t *testing.T, ctx *android.TestContext, singlet
|
|||
}
|
||||
|
||||
func checkSnapshot(t *testing.T, ctx *android.TestContext, singleton android.TestingSingleton, moduleName, snapshotFilename, subDir, variant string) {
|
||||
checkSnapshotIncludeExclude(t, ctx, singleton, moduleName, snapshotFilename, subDir, variant, true)
|
||||
checkSnapshotIncludeExclude(t, ctx, singleton, moduleName, snapshotFilename, subDir, variant, true, false)
|
||||
}
|
||||
|
||||
func checkSnapshotExclude(t *testing.T, ctx *android.TestContext, singleton android.TestingSingleton, moduleName, snapshotFilename, subDir, variant string) {
|
||||
checkSnapshotIncludeExclude(t, ctx, singleton, moduleName, snapshotFilename, subDir, variant, false)
|
||||
checkSnapshotIncludeExclude(t, ctx, singleton, moduleName, snapshotFilename, subDir, variant, false, false)
|
||||
}
|
||||
|
||||
func checkSnapshotRule(t *testing.T, ctx *android.TestContext, singleton android.TestingSingleton, moduleName, snapshotFilename, subDir, variant string) {
|
||||
checkSnapshotIncludeExclude(t, ctx, singleton, moduleName, snapshotFilename, subDir, variant, true, true)
|
||||
}
|
||||
|
||||
func checkWriteFileOutput(t *testing.T, params android.TestingBuildParams, expected []string) {
|
||||
|
|
|
@ -239,10 +239,6 @@ func isSnapshotAware(cfg android.DeviceConfig, m *Module, inProprietaryPath bool
|
|||
if _, ok := m.linker.(*llndkHeadersDecorator); ok {
|
||||
return false
|
||||
}
|
||||
// If we are using directed snapshot AND we have to exclude this module, skip this
|
||||
if image.excludeFromDirectedSnapshot(cfg, m.BaseModuleName()) {
|
||||
return false
|
||||
}
|
||||
|
||||
// Libraries
|
||||
if l, ok := m.linker.(snapshotLibraryInterface); ok {
|
||||
|
@ -371,18 +367,19 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
|
||||
var headers android.Paths
|
||||
|
||||
copyFile := copyFileRule
|
||||
if c.fake {
|
||||
// All prebuilt binaries and headers are installed by copyFile function. This makes a fake
|
||||
// snapshot just touch prebuilts and headers, rather than installing real files.
|
||||
copyFile = func(ctx android.SingletonContext, path android.Path, out string) android.OutputPath {
|
||||
copyFile := func(ctx android.SingletonContext, path android.Path, out string, fake bool) android.OutputPath {
|
||||
if fake {
|
||||
// All prebuilt binaries and headers are installed by copyFile function. This makes a fake
|
||||
// snapshot just touch prebuilts and headers, rather than installing real files.
|
||||
return writeStringToFileRule(ctx, "", out)
|
||||
} else {
|
||||
return copyFileRule(ctx, path, out)
|
||||
}
|
||||
}
|
||||
|
||||
// installSnapshot function copies prebuilt file (.so, .a, or executable) and json flag file.
|
||||
// For executables, init_rc and vintf_fragments files are also copied.
|
||||
installSnapshot := func(m *Module) android.Paths {
|
||||
installSnapshot := func(m *Module, fake bool) android.Paths {
|
||||
targetArch := "arch-" + m.Target().Arch.ArchType.String()
|
||||
if m.Target().Arch.ArchVariant != "" {
|
||||
targetArch += "-" + m.Target().Arch.ArchVariant
|
||||
|
@ -419,7 +416,7 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
out := filepath.Join(configsDir, path.Base())
|
||||
if !installedConfigs[out] {
|
||||
installedConfigs[out] = true
|
||||
ret = append(ret, copyFile(ctx, path, out))
|
||||
ret = append(ret, copyFile(ctx, path, out, fake))
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -470,7 +467,7 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
prop.ModuleName += ".cfi"
|
||||
}
|
||||
snapshotLibOut := filepath.Join(snapshotArchDir, targetArch, libType, stem)
|
||||
ret = append(ret, copyFile(ctx, libPath, snapshotLibOut))
|
||||
ret = append(ret, copyFile(ctx, libPath, snapshotLibOut, fake))
|
||||
} else {
|
||||
stem = ctx.ModuleName(m)
|
||||
}
|
||||
|
@ -484,7 +481,7 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
// install bin
|
||||
binPath := m.outputFile.Path()
|
||||
snapshotBinOut := filepath.Join(snapshotArchDir, targetArch, "binary", binPath.Base())
|
||||
ret = append(ret, copyFile(ctx, binPath, snapshotBinOut))
|
||||
ret = append(ret, copyFile(ctx, binPath, snapshotBinOut, fake))
|
||||
propOut = snapshotBinOut + ".json"
|
||||
} else if m.object() {
|
||||
// object files aren't installed to the device, so their names can conflict.
|
||||
|
@ -492,7 +489,7 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
objPath := m.outputFile.Path()
|
||||
snapshotObjOut := filepath.Join(snapshotArchDir, targetArch, "object",
|
||||
ctx.ModuleName(m)+filepath.Ext(objPath.Base()))
|
||||
ret = append(ret, copyFile(ctx, objPath, snapshotObjOut))
|
||||
ret = append(ret, copyFile(ctx, objPath, snapshotObjOut, fake))
|
||||
propOut = snapshotObjOut + ".json"
|
||||
} else {
|
||||
ctx.Errorf("unknown module %q in vendor snapshot", m.String())
|
||||
|
@ -532,9 +529,17 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
return
|
||||
}
|
||||
|
||||
// installSnapshot installs prebuilts and json flag files
|
||||
snapshotOutputs = append(snapshotOutputs, installSnapshot(m)...)
|
||||
// If we are using directed snapshot and a module is not included in the
|
||||
// list, we will still include the module as if it was a fake module.
|
||||
// The reason is that soong needs all the dependencies to be present, even
|
||||
// if they are not using during the build.
|
||||
installAsFake := c.fake
|
||||
if c.image.excludeFromDirectedSnapshot(ctx.DeviceConfig(), m.BaseModuleName()) {
|
||||
installAsFake = true
|
||||
}
|
||||
|
||||
// installSnapshot installs prebuilts and json flag files
|
||||
snapshotOutputs = append(snapshotOutputs, installSnapshot(m, installAsFake)...)
|
||||
// just gather headers and notice files here, because they are to be deduplicated
|
||||
if l, ok := m.linker.(snapshotLibraryInterface); ok {
|
||||
headers = append(headers, l.snapshotHeaders()...)
|
||||
|
@ -553,7 +558,7 @@ func (c *snapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
|
|||
|
||||
// install all headers after removing duplicates
|
||||
for _, header := range android.FirstUniquePaths(headers) {
|
||||
snapshotOutputs = append(snapshotOutputs, copyFile(ctx, header, filepath.Join(includeDir, header.String())))
|
||||
snapshotOutputs = append(snapshotOutputs, copyFile(ctx, header, filepath.Join(includeDir, header.String()), c.fake))
|
||||
}
|
||||
|
||||
// All artifacts are ready. Sort them to normalize ninja and then zip.
|
||||
|
|
|
@ -228,7 +228,6 @@ func TestVendorSnapshotDirected(t *testing.T) {
|
|||
snapshotSingleton := ctx.SingletonForTests("vendor-snapshot")
|
||||
|
||||
var includeJsonFiles []string
|
||||
var excludeJsonFiles []string
|
||||
|
||||
for _, arch := range [][]string{
|
||||
[]string{"arm64", "armv8-a"},
|
||||
|
@ -248,9 +247,10 @@ func TestVendorSnapshotDirected(t *testing.T) {
|
|||
checkSnapshot(t, ctx, snapshotSingleton, "prebuilt_libfoo", "libfoo.so", sharedDir, sharedVariant)
|
||||
includeJsonFiles = append(includeJsonFiles, filepath.Join(sharedDir, "libfoo.so.json"))
|
||||
|
||||
// Excluded modules
|
||||
checkSnapshotExclude(t, ctx, snapshotSingleton, "libvendor_available", "libvendor_available.so", sharedDir, sharedVariant)
|
||||
excludeJsonFiles = append(excludeJsonFiles, filepath.Join(sharedDir, "libvendor_available.so.json"))
|
||||
// Excluded modules. Modules not included in the directed vendor snapshot
|
||||
// are still include as fake modules.
|
||||
checkSnapshotRule(t, ctx, snapshotSingleton, "libvendor_available", "libvendor_available.so", sharedDir, sharedVariant)
|
||||
includeJsonFiles = append(includeJsonFiles, filepath.Join(sharedDir, "libvendor_available.so.json"))
|
||||
}
|
||||
|
||||
// Verify that each json file for an included module has a rule.
|
||||
|
@ -259,13 +259,6 @@ func TestVendorSnapshotDirected(t *testing.T) {
|
|||
t.Errorf("include json file %q not found", jsonFile)
|
||||
}
|
||||
}
|
||||
|
||||
// Verify that each json file for an excluded module has no rule.
|
||||
for _, jsonFile := range excludeJsonFiles {
|
||||
if snapshotSingleton.MaybeOutput(jsonFile).Rule != nil {
|
||||
t.Errorf("exclude json file %q found", jsonFile)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestVendorSnapshotUse(t *testing.T) {
|
||||
|
|
Loading…
Reference in a new issue