blob: c0b8d5d0661f02a4544ee9614b04b7ccc9192f00 [file] [log] [blame]
Inseob Kimde5744a2020-12-02 13:14:28 +09001// Copyright 2020 The Android Open Source Project
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14package cc
15
16// This file defines snapshot prebuilt modules, e.g. vendor snapshot and recovery snapshot. Such
17// snapshot modules will override original source modules with setting BOARD_VNDK_VERSION, with
18// snapshot mutators and snapshot information maps which are also defined in this file.
19
20import (
21 "strings"
22 "sync"
23
24 "android/soong/android"
Jose Galmes6f843bc2020-12-11 13:36:29 -080025
Colin Crosse0edaf92021-01-11 17:31:17 -080026 "github.com/google/blueprint"
Jose Galmes6f843bc2020-12-11 13:36:29 -080027 "github.com/google/blueprint/proptools"
Inseob Kimde5744a2020-12-02 13:14:28 +090028)
29
30// Defines the specifics of different images to which the snapshot process is applicable, e.g.,
31// vendor, recovery, ramdisk.
32type snapshotImage interface {
Jose Galmes6f843bc2020-12-11 13:36:29 -080033 // Returns true if a snapshot should be generated for this image.
34 shouldGenerateSnapshot(ctx android.SingletonContext) bool
35
Inseob Kimde5744a2020-12-02 13:14:28 +090036 // Function that returns true if the module is included in this image.
37 // Using a function return instead of a value to prevent early
38 // evalution of a function that may be not be defined.
39 inImage(m *Module) func() bool
40
Justin Yune09ac172021-01-20 19:49:01 +090041 // Returns true if the module is private and must not be included in the
42 // snapshot. For example VNDK-private modules must return true for the
43 // vendor snapshots. But false for the recovery snapshots.
44 private(m *Module) bool
Inseob Kimde5744a2020-12-02 13:14:28 +090045
46 // Returns true if a dir under source tree is an SoC-owned proprietary
47 // directory, such as device/, vendor/, etc.
48 //
49 // For a given snapshot (e.g., vendor, recovery, etc.) if
50 // isProprietaryPath(dir) returns true, then the module in dir will be
51 // built from sources.
52 isProprietaryPath(dir string) bool
53
54 // Whether to include VNDK in the snapshot for this image.
55 includeVndk() bool
56
57 // Whether a given module has been explicitly excluded from the
58 // snapshot, e.g., using the exclude_from_vendor_snapshot or
59 // exclude_from_recovery_snapshot properties.
60 excludeFromSnapshot(m *Module) bool
Jose Galmes6f843bc2020-12-11 13:36:29 -080061
Jose Galmes6f843bc2020-12-11 13:36:29 -080062 // Returns mutex used for mutual exclusion when updating the snapshot maps.
63 getMutex() *sync.Mutex
64
65 // For a given arch, a maps of which modules are included in this image.
66 suffixModules(config android.Config) map[string]bool
67
68 // Whether to add a given module to the suffix map.
69 shouldBeAddedToSuffixModules(m *Module) bool
70
71 // Returns true if the build is using a snapshot for this image.
72 isUsingSnapshot(cfg android.DeviceConfig) bool
73
Colin Crosse0edaf92021-01-11 17:31:17 -080074 // Returns a version of which the snapshot should be used in this target.
75 // This will only be meaningful when isUsingSnapshot is true.
76 targetSnapshotVersion(cfg android.DeviceConfig) string
Inseob Kim7cf14652021-01-06 23:06:52 +090077
78 // Whether to exclude a given module from the directed snapshot or not.
79 // If the makefile variable DIRECTED_{IMAGE}_SNAPSHOT is true, directed snapshot is turned on,
80 // and only modules listed in {IMAGE}_SNAPSHOT_MODULES will be captured.
81 excludeFromDirectedSnapshot(cfg android.DeviceConfig, name string) bool
Colin Crosse0edaf92021-01-11 17:31:17 -080082
83 // The image variant name for this snapshot image.
84 // For example, recovery snapshot image will return "recovery", and vendor snapshot image will
85 // return "vendor." + version.
86 imageVariantName(cfg android.DeviceConfig) string
87
88 // The variant suffix for snapshot modules. For example, vendor snapshot modules will have
89 // ".vendor" as their suffix.
90 moduleNameSuffix() string
Inseob Kimde5744a2020-12-02 13:14:28 +090091}
92
93type vendorSnapshotImage struct{}
94type recoverySnapshotImage struct{}
95
Colin Crosse0edaf92021-01-11 17:31:17 -080096func (vendorSnapshotImage) init(ctx android.RegistrationContext) {
97 ctx.RegisterSingletonType("vendor-snapshot", VendorSnapshotSingleton)
98 ctx.RegisterModuleType("vendor_snapshot", vendorSnapshotFactory)
99 ctx.RegisterModuleType("vendor_snapshot_shared", VendorSnapshotSharedFactory)
100 ctx.RegisterModuleType("vendor_snapshot_static", VendorSnapshotStaticFactory)
101 ctx.RegisterModuleType("vendor_snapshot_header", VendorSnapshotHeaderFactory)
102 ctx.RegisterModuleType("vendor_snapshot_binary", VendorSnapshotBinaryFactory)
103 ctx.RegisterModuleType("vendor_snapshot_object", VendorSnapshotObjectFactory)
Inseob Kime9aec6a2021-01-05 20:03:22 +0900104
Colin Crosse0edaf92021-01-11 17:31:17 -0800105 ctx.RegisterSingletonType("vendor-fake-snapshot", VendorFakeSnapshotSingleton)
Inseob Kimde5744a2020-12-02 13:14:28 +0900106}
107
Jose Galmes6f843bc2020-12-11 13:36:29 -0800108func (vendorSnapshotImage) shouldGenerateSnapshot(ctx android.SingletonContext) bool {
109 // BOARD_VNDK_VERSION must be set to 'current' in order to generate a snapshot.
110 return ctx.DeviceConfig().VndkVersion() == "current"
111}
112
Inseob Kimde5744a2020-12-02 13:14:28 +0900113func (vendorSnapshotImage) inImage(m *Module) func() bool {
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500114 return m.InVendor
Inseob Kimde5744a2020-12-02 13:14:28 +0900115}
116
Justin Yune09ac172021-01-20 19:49:01 +0900117func (vendorSnapshotImage) private(m *Module) bool {
118 return m.IsVndkPrivate()
Inseob Kimde5744a2020-12-02 13:14:28 +0900119}
120
121func (vendorSnapshotImage) isProprietaryPath(dir string) bool {
122 return isVendorProprietaryPath(dir)
123}
124
125// vendor snapshot includes static/header libraries with vndk: {enabled: true}.
126func (vendorSnapshotImage) includeVndk() bool {
127 return true
128}
129
130func (vendorSnapshotImage) excludeFromSnapshot(m *Module) bool {
131 return m.ExcludeFromVendorSnapshot()
132}
133
Jose Galmes6f843bc2020-12-11 13:36:29 -0800134func (vendorSnapshotImage) getMutex() *sync.Mutex {
135 return &vendorSnapshotsLock
136}
137
138func (vendorSnapshotImage) suffixModules(config android.Config) map[string]bool {
139 return vendorSuffixModules(config)
140}
141
142func (vendorSnapshotImage) shouldBeAddedToSuffixModules(module *Module) bool {
143 // vendor suffix should be added to snapshots if the source module isn't vendor: true.
144 if module.SocSpecific() {
145 return false
146 }
147
148 // But we can't just check SocSpecific() since we already passed the image mutator.
149 // Check ramdisk and recovery to see if we are real "vendor: true" module.
150 ramdiskAvailable := module.InRamdisk() && !module.OnlyInRamdisk()
151 vendorRamdiskAvailable := module.InVendorRamdisk() && !module.OnlyInVendorRamdisk()
152 recoveryAvailable := module.InRecovery() && !module.OnlyInRecovery()
153
154 return !ramdiskAvailable && !recoveryAvailable && !vendorRamdiskAvailable
155}
156
157func (vendorSnapshotImage) isUsingSnapshot(cfg android.DeviceConfig) bool {
158 vndkVersion := cfg.VndkVersion()
159 return vndkVersion != "current" && vndkVersion != ""
160}
161
Colin Crosse0edaf92021-01-11 17:31:17 -0800162func (vendorSnapshotImage) targetSnapshotVersion(cfg android.DeviceConfig) string {
163 return cfg.VndkVersion()
Jose Galmes6f843bc2020-12-11 13:36:29 -0800164}
165
Inseob Kim7cf14652021-01-06 23:06:52 +0900166// returns true iff a given module SHOULD BE EXCLUDED, false if included
167func (vendorSnapshotImage) excludeFromDirectedSnapshot(cfg android.DeviceConfig, name string) bool {
168 // If we're using full snapshot, not directed snapshot, capture every module
169 if !cfg.DirectedVendorSnapshot() {
170 return false
171 }
172 // Else, checks if name is in VENDOR_SNAPSHOT_MODULES.
173 return !cfg.VendorSnapshotModules()[name]
174}
175
Colin Crosse0edaf92021-01-11 17:31:17 -0800176func (vendorSnapshotImage) imageVariantName(cfg android.DeviceConfig) string {
177 return VendorVariationPrefix + cfg.VndkVersion()
178}
179
180func (vendorSnapshotImage) moduleNameSuffix() string {
181 return vendorSuffix
182}
183
184func (recoverySnapshotImage) init(ctx android.RegistrationContext) {
185 ctx.RegisterSingletonType("recovery-snapshot", RecoverySnapshotSingleton)
186 ctx.RegisterModuleType("recovery_snapshot", recoverySnapshotFactory)
187 ctx.RegisterModuleType("recovery_snapshot_shared", RecoverySnapshotSharedFactory)
188 ctx.RegisterModuleType("recovery_snapshot_static", RecoverySnapshotStaticFactory)
189 ctx.RegisterModuleType("recovery_snapshot_header", RecoverySnapshotHeaderFactory)
190 ctx.RegisterModuleType("recovery_snapshot_binary", RecoverySnapshotBinaryFactory)
191 ctx.RegisterModuleType("recovery_snapshot_object", RecoverySnapshotObjectFactory)
Inseob Kimde5744a2020-12-02 13:14:28 +0900192}
193
Jose Galmes6f843bc2020-12-11 13:36:29 -0800194func (recoverySnapshotImage) shouldGenerateSnapshot(ctx android.SingletonContext) bool {
195 // RECOVERY_SNAPSHOT_VERSION must be set to 'current' in order to generate a
196 // snapshot.
197 return ctx.DeviceConfig().RecoverySnapshotVersion() == "current"
198}
199
Inseob Kimde5744a2020-12-02 13:14:28 +0900200func (recoverySnapshotImage) inImage(m *Module) func() bool {
201 return m.InRecovery
202}
203
Justin Yune09ac172021-01-20 19:49:01 +0900204// recovery snapshot does not have private libraries.
205func (recoverySnapshotImage) private(m *Module) bool {
206 return false
Inseob Kimde5744a2020-12-02 13:14:28 +0900207}
208
209func (recoverySnapshotImage) isProprietaryPath(dir string) bool {
210 return isRecoveryProprietaryPath(dir)
211}
212
213// recovery snapshot does NOT treat vndk specially.
214func (recoverySnapshotImage) includeVndk() bool {
215 return false
216}
217
218func (recoverySnapshotImage) excludeFromSnapshot(m *Module) bool {
219 return m.ExcludeFromRecoverySnapshot()
220}
221
Jose Galmes6f843bc2020-12-11 13:36:29 -0800222func (recoverySnapshotImage) getMutex() *sync.Mutex {
223 return &recoverySnapshotsLock
224}
225
226func (recoverySnapshotImage) suffixModules(config android.Config) map[string]bool {
227 return recoverySuffixModules(config)
228}
229
230func (recoverySnapshotImage) shouldBeAddedToSuffixModules(module *Module) bool {
231 return proptools.BoolDefault(module.Properties.Recovery_available, false)
232}
233
234func (recoverySnapshotImage) isUsingSnapshot(cfg android.DeviceConfig) bool {
235 recoverySnapshotVersion := cfg.RecoverySnapshotVersion()
236 return recoverySnapshotVersion != "current" && recoverySnapshotVersion != ""
237}
238
Colin Crosse0edaf92021-01-11 17:31:17 -0800239func (recoverySnapshotImage) targetSnapshotVersion(cfg android.DeviceConfig) string {
240 return cfg.RecoverySnapshotVersion()
Jose Galmes6f843bc2020-12-11 13:36:29 -0800241}
242
Inseob Kim7cf14652021-01-06 23:06:52 +0900243func (recoverySnapshotImage) excludeFromDirectedSnapshot(cfg android.DeviceConfig, name string) bool {
244 // directed recovery snapshot is not implemented yet
245 return false
246}
247
Colin Crosse0edaf92021-01-11 17:31:17 -0800248func (recoverySnapshotImage) imageVariantName(cfg android.DeviceConfig) string {
249 return android.RecoveryVariation
250}
251
252func (recoverySnapshotImage) moduleNameSuffix() string {
253 return recoverySuffix
254}
255
Inseob Kimde5744a2020-12-02 13:14:28 +0900256var vendorSnapshotImageSingleton vendorSnapshotImage
257var recoverySnapshotImageSingleton recoverySnapshotImage
258
259func init() {
Colin Crosse0edaf92021-01-11 17:31:17 -0800260 vendorSnapshotImageSingleton.init(android.InitRegistrationContext)
261 recoverySnapshotImageSingleton.init(android.InitRegistrationContext)
Inseob Kimde5744a2020-12-02 13:14:28 +0900262}
263
264const (
Colin Crosse0edaf92021-01-11 17:31:17 -0800265 snapshotHeaderSuffix = "_header."
266 snapshotSharedSuffix = "_shared."
267 snapshotStaticSuffix = "_static."
268 snapshotBinarySuffix = "_binary."
269 snapshotObjectSuffix = "_object."
Inseob Kimde5744a2020-12-02 13:14:28 +0900270)
271
272var (
Colin Crosse0edaf92021-01-11 17:31:17 -0800273 vendorSnapshotsLock sync.Mutex
274 vendorSuffixModulesKey = android.NewOnceKey("vendorSuffixModules")
Inseob Kimde5744a2020-12-02 13:14:28 +0900275)
276
Jose Galmes6f843bc2020-12-11 13:36:29 -0800277var (
Colin Crosse0edaf92021-01-11 17:31:17 -0800278 recoverySnapshotsLock sync.Mutex
279 recoverySuffixModulesKey = android.NewOnceKey("recoverySuffixModules")
Jose Galmes6f843bc2020-12-11 13:36:29 -0800280)
281
Colin Crosse0edaf92021-01-11 17:31:17 -0800282type SnapshotProperties struct {
283 Header_libs []string `android:"arch_variant"`
284 Static_libs []string `android:"arch_variant"`
285 Shared_libs []string `android:"arch_variant"`
286 Vndk_libs []string `android:"arch_variant"`
287 Binaries []string `android:"arch_variant"`
288 Objects []string `android:"arch_variant"`
289}
290
291type snapshot struct {
292 android.ModuleBase
293
294 properties SnapshotProperties
295
296 baseSnapshot baseSnapshotDecorator
297
298 image snapshotImage
299}
300
301func (s *snapshot) ImageMutatorBegin(ctx android.BaseModuleContext) {
302 cfg := ctx.DeviceConfig()
303 if !s.image.isUsingSnapshot(cfg) || s.image.targetSnapshotVersion(cfg) != s.baseSnapshot.version() {
304 s.Disable()
305 }
306}
307
308func (s *snapshot) CoreVariantNeeded(ctx android.BaseModuleContext) bool {
309 return false
310}
311
312func (s *snapshot) RamdiskVariantNeeded(ctx android.BaseModuleContext) bool {
313 return false
314}
315
316func (s *snapshot) VendorRamdiskVariantNeeded(ctx android.BaseModuleContext) bool {
317 return false
318}
319
320func (s *snapshot) RecoveryVariantNeeded(ctx android.BaseModuleContext) bool {
321 return false
322}
323
324func (s *snapshot) ExtraImageVariations(ctx android.BaseModuleContext) []string {
325 return []string{s.image.imageVariantName(ctx.DeviceConfig())}
326}
327
328func (s *snapshot) SetImageVariation(ctx android.BaseModuleContext, variation string, module android.Module) {
329}
330
331func (s *snapshot) GenerateAndroidBuildActions(ctx android.ModuleContext) {
332 // Nothing, the snapshot module is only used to forward dependency information in DepsMutator.
333}
334
335func (s *snapshot) DepsMutator(ctx android.BottomUpMutatorContext) {
336 collectSnapshotMap := func(variations []blueprint.Variation, depTag blueprint.DependencyTag,
337 names []string, snapshotSuffix, moduleSuffix string) map[string]string {
338
339 decoratedNames := make([]string, 0, len(names))
340 for _, name := range names {
341 decoratedNames = append(decoratedNames, name+
342 snapshotSuffix+moduleSuffix+
343 s.baseSnapshot.version()+
344 "."+ctx.Arch().ArchType.Name)
345 }
346
347 deps := ctx.AddVariationDependencies(variations, depTag, decoratedNames...)
348 snapshotMap := make(map[string]string)
349 for _, dep := range deps {
350 if dep == nil {
351 continue
352 }
353
354 snapshotMap[dep.(*Module).BaseModuleName()] = ctx.OtherModuleName(dep)
355 }
356 return snapshotMap
357 }
358
359 snapshotSuffix := s.image.moduleNameSuffix()
360 headers := collectSnapshotMap(nil, HeaderDepTag(), s.properties.Header_libs, snapshotSuffix, snapshotHeaderSuffix)
361 binaries := collectSnapshotMap(nil, nil, s.properties.Binaries, snapshotSuffix, snapshotBinarySuffix)
362 objects := collectSnapshotMap(nil, nil, s.properties.Objects, snapshotSuffix, snapshotObjectSuffix)
363
364 staticLibs := collectSnapshotMap([]blueprint.Variation{
365 {Mutator: "link", Variation: "static"},
366 }, StaticDepTag(), s.properties.Static_libs, snapshotSuffix, snapshotStaticSuffix)
367
368 sharedLibs := collectSnapshotMap([]blueprint.Variation{
369 {Mutator: "link", Variation: "shared"},
370 }, SharedDepTag(), s.properties.Shared_libs, snapshotSuffix, snapshotSharedSuffix)
371
372 vndkLibs := collectSnapshotMap([]blueprint.Variation{
373 {Mutator: "link", Variation: "shared"},
374 }, SharedDepTag(), s.properties.Vndk_libs, "", vndkSuffix)
375
376 for k, v := range vndkLibs {
377 sharedLibs[k] = v
378 }
379 ctx.SetProvider(SnapshotInfoProvider, SnapshotInfo{
380 HeaderLibs: headers,
381 Binaries: binaries,
382 Objects: objects,
383 StaticLibs: staticLibs,
384 SharedLibs: sharedLibs,
385 })
386}
387
388type SnapshotInfo struct {
389 HeaderLibs, Binaries, Objects, StaticLibs, SharedLibs map[string]string
390}
391
392var SnapshotInfoProvider = blueprint.NewMutatorProvider(SnapshotInfo{}, "deps")
393
394var _ android.ImageInterface = (*snapshot)(nil)
395
396func vendorSnapshotFactory() android.Module {
397 return snapshotFactory(vendorSnapshotImageSingleton)
398}
399
400func recoverySnapshotFactory() android.Module {
401 return snapshotFactory(recoverySnapshotImageSingleton)
402}
403
404func snapshotFactory(image snapshotImage) android.Module {
405 snapshot := &snapshot{}
406 snapshot.image = image
407 snapshot.AddProperties(
408 &snapshot.properties,
409 &snapshot.baseSnapshot.baseProperties)
410 android.InitAndroidArchModule(snapshot, android.DeviceSupported, android.MultilibBoth)
411 return snapshot
412}
413
Inseob Kimde5744a2020-12-02 13:14:28 +0900414// vendorSuffixModules holds names of modules whose vendor variants should have the vendor suffix.
415// This is determined by source modules, and then this will be used when exporting snapshot modules
416// to Makefile.
417//
418// For example, if libbase has "vendor_available: true", the name of core variant will be "libbase"
419// while the name of vendor variant will be "libbase.vendor". In such cases, the vendor snapshot of
420// "libbase" should be exported with the name "libbase.vendor".
421//
422// Refer to VendorSnapshotSourceMutator and makeLibName which use this.
423func vendorSuffixModules(config android.Config) map[string]bool {
424 return config.Once(vendorSuffixModulesKey, func() interface{} {
425 return make(map[string]bool)
426 }).(map[string]bool)
427}
428
Jose Galmes6f843bc2020-12-11 13:36:29 -0800429func recoverySuffixModules(config android.Config) map[string]bool {
430 return config.Once(recoverySuffixModulesKey, func() interface{} {
431 return make(map[string]bool)
432 }).(map[string]bool)
433}
434
Inseob Kimde5744a2020-12-02 13:14:28 +0900435type baseSnapshotDecoratorProperties struct {
436 // snapshot version.
437 Version string
438
439 // Target arch name of the snapshot (e.g. 'arm64' for variant 'aosp_arm64')
440 Target_arch string
Jose Galmes6f843bc2020-12-11 13:36:29 -0800441
442 // Suffix to be added to the module name, e.g., vendor_shared,
443 // recovery_shared, etc.
Colin Crosse0edaf92021-01-11 17:31:17 -0800444 ModuleSuffix string `blueprint:"mutated"`
Inseob Kimde5744a2020-12-02 13:14:28 +0900445}
446
447// baseSnapshotDecorator provides common basic functions for all snapshot modules, such as snapshot
448// version, snapshot arch, etc. It also adds a special suffix to Soong module name, so it doesn't
449// collide with source modules. e.g. the following example module,
450//
451// vendor_snapshot_static {
452// name: "libbase",
453// arch: "arm64",
454// version: 30,
455// ...
456// }
457//
458// will be seen as "libbase.vendor_static.30.arm64" by Soong.
459type baseSnapshotDecorator struct {
460 baseProperties baseSnapshotDecoratorProperties
Inseob Kimde5744a2020-12-02 13:14:28 +0900461}
462
463func (p *baseSnapshotDecorator) Name(name string) string {
464 return name + p.NameSuffix()
465}
466
467func (p *baseSnapshotDecorator) NameSuffix() string {
468 versionSuffix := p.version()
469 if p.arch() != "" {
470 versionSuffix += "." + p.arch()
471 }
472
Colin Crosse0edaf92021-01-11 17:31:17 -0800473 return p.baseProperties.ModuleSuffix + versionSuffix
Inseob Kimde5744a2020-12-02 13:14:28 +0900474}
475
476func (p *baseSnapshotDecorator) version() string {
477 return p.baseProperties.Version
478}
479
480func (p *baseSnapshotDecorator) arch() string {
481 return p.baseProperties.Target_arch
482}
483
Colin Crosse0edaf92021-01-11 17:31:17 -0800484func (p *baseSnapshotDecorator) moduleSuffix() string {
485 return p.baseProperties.ModuleSuffix
Jose Galmes6f843bc2020-12-11 13:36:29 -0800486}
487
Inseob Kimde5744a2020-12-02 13:14:28 +0900488func (p *baseSnapshotDecorator) isSnapshotPrebuilt() bool {
489 return true
490}
491
492// Call this with a module suffix after creating a snapshot module, such as
493// vendorSnapshotSharedSuffix, recoverySnapshotBinarySuffix, etc.
Colin Crosse0edaf92021-01-11 17:31:17 -0800494func (p *baseSnapshotDecorator) init(m *Module, snapshotSuffix, moduleSuffix string) {
495 p.baseProperties.ModuleSuffix = snapshotSuffix + moduleSuffix
Inseob Kimde5744a2020-12-02 13:14:28 +0900496 m.AddProperties(&p.baseProperties)
497 android.AddLoadHook(m, func(ctx android.LoadHookContext) {
498 vendorSnapshotLoadHook(ctx, p)
499 })
500}
501
502// vendorSnapshotLoadHook disables snapshots if it's not BOARD_VNDK_VERSION.
503// As vendor snapshot is only for vendor, such modules won't be used at all.
504func vendorSnapshotLoadHook(ctx android.LoadHookContext, p *baseSnapshotDecorator) {
505 if p.version() != ctx.DeviceConfig().VndkVersion() {
506 ctx.Module().Disable()
507 return
508 }
509}
510
511//
512// Module definitions for snapshots of libraries (shared, static, header).
513//
514// Modules (vendor|recovery)_snapshot_(shared|static|header) are defined here. Shared libraries and
515// static libraries have their prebuilt library files (.so for shared, .a for static) as their src,
516// which can be installed or linked against. Also they export flags needed when linked, such as
517// include directories, c flags, sanitize dependency information, etc.
518//
519// These modules are auto-generated by development/vendor_snapshot/update.py.
520type snapshotLibraryProperties struct {
521 // Prebuilt file for each arch.
522 Src *string `android:"arch_variant"`
523
524 // list of directories that will be added to the include path (using -I).
525 Export_include_dirs []string `android:"arch_variant"`
526
527 // list of directories that will be added to the system path (using -isystem).
528 Export_system_include_dirs []string `android:"arch_variant"`
529
530 // list of flags that will be used for any module that links against this module.
531 Export_flags []string `android:"arch_variant"`
532
533 // Whether this prebuilt needs to depend on sanitize ubsan runtime or not.
534 Sanitize_ubsan_dep *bool `android:"arch_variant"`
535
536 // Whether this prebuilt needs to depend on sanitize minimal runtime or not.
537 Sanitize_minimal_dep *bool `android:"arch_variant"`
538}
539
540type snapshotSanitizer interface {
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500541 isSanitizerEnabled(t SanitizerType) bool
542 setSanitizerVariation(t SanitizerType, enabled bool)
Inseob Kimde5744a2020-12-02 13:14:28 +0900543}
544
545type snapshotLibraryDecorator struct {
546 baseSnapshotDecorator
547 *libraryDecorator
548 properties snapshotLibraryProperties
549 sanitizerProperties struct {
550 CfiEnabled bool `blueprint:"mutated"`
551
552 // Library flags for cfi variant.
553 Cfi snapshotLibraryProperties `android:"arch_variant"`
554 }
Jose Galmes6f843bc2020-12-11 13:36:29 -0800555 androidMkSuffix string
Inseob Kimde5744a2020-12-02 13:14:28 +0900556}
557
558func (p *snapshotLibraryDecorator) linkerFlags(ctx ModuleContext, flags Flags) Flags {
559 p.libraryDecorator.libName = strings.TrimSuffix(ctx.ModuleName(), p.NameSuffix())
560 return p.libraryDecorator.linkerFlags(ctx, flags)
561}
562
563func (p *snapshotLibraryDecorator) matchesWithDevice(config android.DeviceConfig) bool {
564 arches := config.Arches()
565 if len(arches) == 0 || arches[0].ArchType.String() != p.arch() {
566 return false
567 }
568 if !p.header() && p.properties.Src == nil {
569 return false
570 }
571 return true
572}
573
574// cc modules' link functions are to link compiled objects into final binaries.
575// As snapshots are prebuilts, this just returns the prebuilt binary after doing things which are
576// done by normal library decorator, e.g. exporting flags.
577func (p *snapshotLibraryDecorator) link(ctx ModuleContext, flags Flags, deps PathDeps, objs Objects) android.Path {
578 m := ctx.Module().(*Module)
Jose Galmes6f843bc2020-12-11 13:36:29 -0800579
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500580 if m.InVendor() && vendorSuffixModules(ctx.Config())[m.BaseModuleName()] {
Jose Galmes6f843bc2020-12-11 13:36:29 -0800581 p.androidMkSuffix = vendorSuffix
582 } else if m.InRecovery() && recoverySuffixModules(ctx.Config())[m.BaseModuleName()] {
583 p.androidMkSuffix = recoverySuffix
584 }
Inseob Kimde5744a2020-12-02 13:14:28 +0900585
586 if p.header() {
587 return p.libraryDecorator.link(ctx, flags, deps, objs)
588 }
589
590 if p.sanitizerProperties.CfiEnabled {
591 p.properties = p.sanitizerProperties.Cfi
592 }
593
594 if !p.matchesWithDevice(ctx.DeviceConfig()) {
595 return nil
596 }
597
598 p.libraryDecorator.reexportDirs(android.PathsForModuleSrc(ctx, p.properties.Export_include_dirs)...)
599 p.libraryDecorator.reexportSystemDirs(android.PathsForModuleSrc(ctx, p.properties.Export_system_include_dirs)...)
600 p.libraryDecorator.reexportFlags(p.properties.Export_flags...)
601
602 in := android.PathForModuleSrc(ctx, *p.properties.Src)
603 p.unstrippedOutputFile = in
604
605 if p.shared() {
606 libName := in.Base()
607 builderFlags := flagsToBuilderFlags(flags)
608
609 // Optimize out relinking against shared libraries whose interface hasn't changed by
610 // depending on a table of contents file instead of the library itself.
611 tocFile := android.PathForModuleOut(ctx, libName+".toc")
612 p.tocFile = android.OptionalPathForPath(tocFile)
613 transformSharedObjectToToc(ctx, in, tocFile, builderFlags)
614
615 ctx.SetProvider(SharedLibraryInfoProvider, SharedLibraryInfo{
616 SharedLibrary: in,
617 UnstrippedSharedLibrary: p.unstrippedOutputFile,
618
619 TableOfContents: p.tocFile,
620 })
621 }
622
623 if p.static() {
624 depSet := android.NewDepSetBuilder(android.TOPOLOGICAL).Direct(in).Build()
625 ctx.SetProvider(StaticLibraryInfoProvider, StaticLibraryInfo{
626 StaticLibrary: in,
627
628 TransitiveStaticLibrariesForOrdering: depSet,
629 })
630 }
631
632 p.libraryDecorator.flagExporter.setProvider(ctx)
633
634 return in
635}
636
637func (p *snapshotLibraryDecorator) install(ctx ModuleContext, file android.Path) {
638 if p.matchesWithDevice(ctx.DeviceConfig()) && (p.shared() || p.static()) {
639 p.baseInstaller.install(ctx, file)
640 }
641}
642
643func (p *snapshotLibraryDecorator) nativeCoverage() bool {
644 return false
645}
646
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500647func (p *snapshotLibraryDecorator) isSanitizerEnabled(t SanitizerType) bool {
Inseob Kimde5744a2020-12-02 13:14:28 +0900648 switch t {
649 case cfi:
650 return p.sanitizerProperties.Cfi.Src != nil
651 default:
652 return false
653 }
654}
655
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500656func (p *snapshotLibraryDecorator) setSanitizerVariation(t SanitizerType, enabled bool) {
Inseob Kimde5744a2020-12-02 13:14:28 +0900657 if !enabled {
658 return
659 }
660 switch t {
661 case cfi:
662 p.sanitizerProperties.CfiEnabled = true
663 default:
664 return
665 }
666}
667
Colin Crosse0edaf92021-01-11 17:31:17 -0800668func snapshotLibraryFactory(snapshotSuffix, moduleSuffix string) (*Module, *snapshotLibraryDecorator) {
Inseob Kimde5744a2020-12-02 13:14:28 +0900669 module, library := NewLibrary(android.DeviceSupported)
670
671 module.stl = nil
672 module.sanitize = nil
673 library.disableStripping()
674
675 prebuilt := &snapshotLibraryDecorator{
676 libraryDecorator: library,
677 }
678
679 prebuilt.baseLinker.Properties.No_libcrt = BoolPtr(true)
680 prebuilt.baseLinker.Properties.Nocrt = BoolPtr(true)
681
682 // Prevent default system libs (libc, libm, and libdl) from being linked
683 if prebuilt.baseLinker.Properties.System_shared_libs == nil {
684 prebuilt.baseLinker.Properties.System_shared_libs = []string{}
685 }
686
687 module.compiler = nil
688 module.linker = prebuilt
689 module.installer = prebuilt
690
Colin Crosse0edaf92021-01-11 17:31:17 -0800691 prebuilt.init(module, snapshotSuffix, moduleSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900692 module.AddProperties(
693 &prebuilt.properties,
694 &prebuilt.sanitizerProperties,
695 )
696
697 return module, prebuilt
698}
699
700// vendor_snapshot_shared is a special prebuilt shared library which is auto-generated by
701// development/vendor_snapshot/update.py. As a part of vendor snapshot, vendor_snapshot_shared
702// overrides the vendor variant of the cc shared library with the same name, if BOARD_VNDK_VERSION
703// is set.
704func VendorSnapshotSharedFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800705 module, prebuilt := snapshotLibraryFactory(vendorSnapshotImageSingleton.moduleNameSuffix(), snapshotSharedSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900706 prebuilt.libraryDecorator.BuildOnlyShared()
707 return module.Init()
708}
709
710// recovery_snapshot_shared is a special prebuilt shared library which is auto-generated by
711// development/vendor_snapshot/update.py. As a part of recovery snapshot, recovery_snapshot_shared
712// overrides the recovery variant of the cc shared library with the same name, if BOARD_VNDK_VERSION
713// is set.
714func RecoverySnapshotSharedFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800715 module, prebuilt := snapshotLibraryFactory(recoverySnapshotImageSingleton.moduleNameSuffix(), snapshotSharedSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900716 prebuilt.libraryDecorator.BuildOnlyShared()
717 return module.Init()
718}
719
720// vendor_snapshot_static is a special prebuilt static library which is auto-generated by
721// development/vendor_snapshot/update.py. As a part of vendor snapshot, vendor_snapshot_static
722// overrides the vendor variant of the cc static library with the same name, if BOARD_VNDK_VERSION
723// is set.
724func VendorSnapshotStaticFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800725 module, prebuilt := snapshotLibraryFactory(vendorSnapshotImageSingleton.moduleNameSuffix(), snapshotStaticSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900726 prebuilt.libraryDecorator.BuildOnlyStatic()
727 return module.Init()
728}
729
730// recovery_snapshot_static is a special prebuilt static library which is auto-generated by
731// development/vendor_snapshot/update.py. As a part of recovery snapshot, recovery_snapshot_static
732// overrides the recovery variant of the cc static library with the same name, if BOARD_VNDK_VERSION
733// is set.
734func RecoverySnapshotStaticFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800735 module, prebuilt := snapshotLibraryFactory(recoverySnapshotImageSingleton.moduleNameSuffix(), snapshotStaticSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900736 prebuilt.libraryDecorator.BuildOnlyStatic()
737 return module.Init()
738}
739
740// vendor_snapshot_header is a special header library which is auto-generated by
741// development/vendor_snapshot/update.py. As a part of vendor snapshot, vendor_snapshot_header
742// overrides the vendor variant of the cc header library with the same name, if BOARD_VNDK_VERSION
743// is set.
744func VendorSnapshotHeaderFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800745 module, prebuilt := snapshotLibraryFactory(vendorSnapshotImageSingleton.moduleNameSuffix(), snapshotHeaderSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900746 prebuilt.libraryDecorator.HeaderOnly()
747 return module.Init()
748}
749
750// recovery_snapshot_header is a special header library which is auto-generated by
751// development/vendor_snapshot/update.py. As a part of recovery snapshot, recovery_snapshot_header
752// overrides the recovery variant of the cc header library with the same name, if BOARD_VNDK_VERSION
753// is set.
754func RecoverySnapshotHeaderFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800755 module, prebuilt := snapshotLibraryFactory(recoverySnapshotImageSingleton.moduleNameSuffix(), snapshotHeaderSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900756 prebuilt.libraryDecorator.HeaderOnly()
757 return module.Init()
758}
759
760var _ snapshotSanitizer = (*snapshotLibraryDecorator)(nil)
761
762//
763// Module definitions for snapshots of executable binaries.
764//
765// Modules (vendor|recovery)_snapshot_binary are defined here. They have their prebuilt executable
766// binaries (e.g. toybox, sh) as their src, which can be installed.
767//
768// These modules are auto-generated by development/vendor_snapshot/update.py.
769type snapshotBinaryProperties struct {
770 // Prebuilt file for each arch.
771 Src *string `android:"arch_variant"`
772}
773
774type snapshotBinaryDecorator struct {
775 baseSnapshotDecorator
776 *binaryDecorator
Jose Galmes6f843bc2020-12-11 13:36:29 -0800777 properties snapshotBinaryProperties
778 androidMkSuffix string
Inseob Kimde5744a2020-12-02 13:14:28 +0900779}
780
781func (p *snapshotBinaryDecorator) matchesWithDevice(config android.DeviceConfig) bool {
782 if config.DeviceArch() != p.arch() {
783 return false
784 }
785 if p.properties.Src == nil {
786 return false
787 }
788 return true
789}
790
791// cc modules' link functions are to link compiled objects into final binaries.
792// As snapshots are prebuilts, this just returns the prebuilt binary
793func (p *snapshotBinaryDecorator) link(ctx ModuleContext, flags Flags, deps PathDeps, objs Objects) android.Path {
794 if !p.matchesWithDevice(ctx.DeviceConfig()) {
795 return nil
796 }
797
798 in := android.PathForModuleSrc(ctx, *p.properties.Src)
799 p.unstrippedOutputFile = in
800 binName := in.Base()
801
802 m := ctx.Module().(*Module)
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500803 if m.InVendor() && vendorSuffixModules(ctx.Config())[m.BaseModuleName()] {
Jose Galmes6f843bc2020-12-11 13:36:29 -0800804 p.androidMkSuffix = vendorSuffix
805 } else if m.InRecovery() && recoverySuffixModules(ctx.Config())[m.BaseModuleName()] {
806 p.androidMkSuffix = recoverySuffix
807
808 }
Inseob Kimde5744a2020-12-02 13:14:28 +0900809
810 // use cpExecutable to make it executable
811 outputFile := android.PathForModuleOut(ctx, binName)
812 ctx.Build(pctx, android.BuildParams{
813 Rule: android.CpExecutable,
814 Description: "prebuilt",
815 Output: outputFile,
816 Input: in,
817 })
818
819 return outputFile
820}
821
822func (p *snapshotBinaryDecorator) nativeCoverage() bool {
823 return false
824}
825
826// vendor_snapshot_binary is a special prebuilt executable binary which is auto-generated by
827// development/vendor_snapshot/update.py. As a part of vendor snapshot, vendor_snapshot_binary
828// overrides the vendor variant of the cc binary with the same name, if BOARD_VNDK_VERSION is set.
829func VendorSnapshotBinaryFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800830 return snapshotBinaryFactory(vendorSnapshotImageSingleton.moduleNameSuffix(), snapshotBinarySuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900831}
832
833// recovery_snapshot_binary is a special prebuilt executable binary which is auto-generated by
834// development/vendor_snapshot/update.py. As a part of recovery snapshot, recovery_snapshot_binary
835// overrides the recovery variant of the cc binary with the same name, if BOARD_VNDK_VERSION is set.
836func RecoverySnapshotBinaryFactory() android.Module {
Colin Crosse0edaf92021-01-11 17:31:17 -0800837 return snapshotBinaryFactory(recoverySnapshotImageSingleton.moduleNameSuffix(), snapshotBinarySuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900838}
839
Colin Crosse0edaf92021-01-11 17:31:17 -0800840func snapshotBinaryFactory(snapshotSuffix, moduleSuffix string) android.Module {
Inseob Kimde5744a2020-12-02 13:14:28 +0900841 module, binary := NewBinary(android.DeviceSupported)
842 binary.baseLinker.Properties.No_libcrt = BoolPtr(true)
843 binary.baseLinker.Properties.Nocrt = BoolPtr(true)
844
845 // Prevent default system libs (libc, libm, and libdl) from being linked
846 if binary.baseLinker.Properties.System_shared_libs == nil {
847 binary.baseLinker.Properties.System_shared_libs = []string{}
848 }
849
850 prebuilt := &snapshotBinaryDecorator{
851 binaryDecorator: binary,
852 }
853
854 module.compiler = nil
855 module.sanitize = nil
856 module.stl = nil
857 module.linker = prebuilt
858
Colin Crosse0edaf92021-01-11 17:31:17 -0800859 prebuilt.init(module, snapshotSuffix, moduleSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900860 module.AddProperties(&prebuilt.properties)
861 return module.Init()
862}
863
864//
865// Module definitions for snapshots of object files (*.o).
866//
867// Modules (vendor|recovery)_snapshot_object are defined here. They have their prebuilt object
868// files (*.o) as their src.
869//
870// These modules are auto-generated by development/vendor_snapshot/update.py.
871type vendorSnapshotObjectProperties struct {
872 // Prebuilt file for each arch.
873 Src *string `android:"arch_variant"`
874}
875
876type snapshotObjectLinker struct {
877 baseSnapshotDecorator
878 objectLinker
Jose Galmes6f843bc2020-12-11 13:36:29 -0800879 properties vendorSnapshotObjectProperties
880 androidMkSuffix string
Inseob Kimde5744a2020-12-02 13:14:28 +0900881}
882
883func (p *snapshotObjectLinker) matchesWithDevice(config android.DeviceConfig) bool {
884 if config.DeviceArch() != p.arch() {
885 return false
886 }
887 if p.properties.Src == nil {
888 return false
889 }
890 return true
891}
892
893// cc modules' link functions are to link compiled objects into final binaries.
894// As snapshots are prebuilts, this just returns the prebuilt binary
895func (p *snapshotObjectLinker) link(ctx ModuleContext, flags Flags, deps PathDeps, objs Objects) android.Path {
896 if !p.matchesWithDevice(ctx.DeviceConfig()) {
897 return nil
898 }
899
900 m := ctx.Module().(*Module)
Jose Galmes6f843bc2020-12-11 13:36:29 -0800901
Ivan Lozano3968d8f2020-12-14 11:27:52 -0500902 if m.InVendor() && vendorSuffixModules(ctx.Config())[m.BaseModuleName()] {
Jose Galmes6f843bc2020-12-11 13:36:29 -0800903 p.androidMkSuffix = vendorSuffix
904 } else if m.InRecovery() && recoverySuffixModules(ctx.Config())[m.BaseModuleName()] {
905 p.androidMkSuffix = recoverySuffix
906 }
Inseob Kimde5744a2020-12-02 13:14:28 +0900907
908 return android.PathForModuleSrc(ctx, *p.properties.Src)
909}
910
911func (p *snapshotObjectLinker) nativeCoverage() bool {
912 return false
913}
914
915// vendor_snapshot_object is a special prebuilt compiled object file which is auto-generated by
916// development/vendor_snapshot/update.py. As a part of vendor snapshot, vendor_snapshot_object
917// overrides the vendor variant of the cc object with the same name, if BOARD_VNDK_VERSION is set.
918func VendorSnapshotObjectFactory() android.Module {
919 module := newObject()
920
921 prebuilt := &snapshotObjectLinker{
922 objectLinker: objectLinker{
923 baseLinker: NewBaseLinker(nil),
924 },
925 }
926 module.linker = prebuilt
927
Colin Crosse0edaf92021-01-11 17:31:17 -0800928 prebuilt.init(module, vendorSnapshotImageSingleton.moduleNameSuffix(), snapshotObjectSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900929 module.AddProperties(&prebuilt.properties)
930 return module.Init()
931}
932
933// recovery_snapshot_object is a special prebuilt compiled object file which is auto-generated by
934// development/vendor_snapshot/update.py. As a part of recovery snapshot, recovery_snapshot_object
935// overrides the recovery variant of the cc object with the same name, if BOARD_VNDK_VERSION is set.
936func RecoverySnapshotObjectFactory() android.Module {
937 module := newObject()
938
939 prebuilt := &snapshotObjectLinker{
940 objectLinker: objectLinker{
941 baseLinker: NewBaseLinker(nil),
942 },
943 }
944 module.linker = prebuilt
945
Colin Crosse0edaf92021-01-11 17:31:17 -0800946 prebuilt.init(module, recoverySnapshotImageSingleton.moduleNameSuffix(), snapshotObjectSuffix)
Inseob Kimde5744a2020-12-02 13:14:28 +0900947 module.AddProperties(&prebuilt.properties)
948 return module.Init()
949}
950
951type snapshotInterface interface {
952 matchesWithDevice(config android.DeviceConfig) bool
953}
954
955var _ snapshotInterface = (*vndkPrebuiltLibraryDecorator)(nil)
956var _ snapshotInterface = (*snapshotLibraryDecorator)(nil)
957var _ snapshotInterface = (*snapshotBinaryDecorator)(nil)
958var _ snapshotInterface = (*snapshotObjectLinker)(nil)
959
960//
961// Mutators that helps vendor snapshot modules override source modules.
962//
963
Inseob Kimde5744a2020-12-02 13:14:28 +0900964// VendorSnapshotSourceMutator disables source modules which have corresponding snapshots.
965func VendorSnapshotSourceMutator(ctx android.BottomUpMutatorContext) {
Jose Galmes6f843bc2020-12-11 13:36:29 -0800966 snapshotSourceMutator(ctx, vendorSnapshotImageSingleton)
967}
968
969func RecoverySnapshotSourceMutator(ctx android.BottomUpMutatorContext) {
970 snapshotSourceMutator(ctx, recoverySnapshotImageSingleton)
971}
972
973func snapshotSourceMutator(ctx android.BottomUpMutatorContext, image snapshotImage) {
Inseob Kimde5744a2020-12-02 13:14:28 +0900974 if !ctx.Device() {
975 return
976 }
Jose Galmes6f843bc2020-12-11 13:36:29 -0800977 if !image.isUsingSnapshot(ctx.DeviceConfig()) {
Inseob Kimde5744a2020-12-02 13:14:28 +0900978 return
979 }
980
981 module, ok := ctx.Module().(*Module)
982 if !ok {
983 return
984 }
985
Jose Galmes6f843bc2020-12-11 13:36:29 -0800986 if image.shouldBeAddedToSuffixModules(module) {
987 mutex := image.getMutex()
988 mutex.Lock()
989 defer mutex.Unlock()
Inseob Kimde5744a2020-12-02 13:14:28 +0900990
Jose Galmes6f843bc2020-12-11 13:36:29 -0800991 image.suffixModules(ctx.Config())[ctx.ModuleName()] = true
Inseob Kimde5744a2020-12-02 13:14:28 +0900992 }
Inseob Kimde5744a2020-12-02 13:14:28 +0900993}