blob: 698fab52702fc53286213250f2f29bf7ee4e33d6 [file] [log] [blame]
Justin Yun8effde42017-06-23 19:24:43 +09001// Copyright 2017 Google Inc. All rights reserved.
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.
14
15package cc
16
17import (
Inseob Kimae553032019-05-14 18:52:49 +090018 "encoding/json"
Martin Stjernholm257eb0c2018-10-15 13:05:27 +010019 "errors"
Inseob Kim1f086e22019-05-09 13:29:15 +090020 "path/filepath"
Colin Cross766efbc2017-08-17 14:55:15 -070021 "sort"
Jiyong Parkd5b18a52017-08-03 21:22:50 +090022 "strings"
23 "sync"
24
Justin Yun8effde42017-06-23 19:24:43 +090025 "android/soong/android"
Vic Yangefd249e2018-11-12 20:19:56 -080026 "android/soong/cc/config"
Justin Yun8effde42017-06-23 19:24:43 +090027)
28
29type VndkProperties struct {
30 Vndk struct {
31 // declared as a VNDK or VNDK-SP module. The vendor variant
32 // will be installed in /system instead of /vendor partition.
33 //
Roland Levillaindfe75b32019-07-23 16:53:32 +010034 // `vendor_available` must be explicitly set to either true or
Jiyong Park82e2bf32017-08-16 14:05:54 +090035 // false together with `vndk: {enabled: true}`.
Justin Yun8effde42017-06-23 19:24:43 +090036 Enabled *bool
37
38 // declared as a VNDK-SP module, which is a subset of VNDK.
39 //
40 // `vndk: { enabled: true }` must set together.
41 //
42 // All these modules are allowed to link to VNDK-SP or LL-NDK
43 // modules only. Other dependency will cause link-type errors.
44 //
45 // If `support_system_process` is not set or set to false,
46 // the module is VNDK-core and can link to other VNDK-core,
47 // VNDK-SP or LL-NDK modules only.
48 Support_system_process *bool
Logan Chienf3511742017-10-31 18:04:35 +080049
50 // Extending another module
51 Extends *string
Jooyung Han76106d92019-05-20 18:49:10 +090052
53 // for vndk_prebuilt_shared, this is set by "version" property.
54 // Otherwise, this is set as PLATFORM_VNDK_VERSION.
55 Version string `blueprint:"mutated"`
Justin Yun8effde42017-06-23 19:24:43 +090056 }
57}
58
59type vndkdep struct {
60 Properties VndkProperties
61}
62
63func (vndk *vndkdep) props() []interface{} {
64 return []interface{}{&vndk.Properties}
65}
66
67func (vndk *vndkdep) begin(ctx BaseModuleContext) {}
68
69func (vndk *vndkdep) deps(ctx BaseModuleContext, deps Deps) Deps {
70 return deps
71}
72
73func (vndk *vndkdep) isVndk() bool {
74 return Bool(vndk.Properties.Vndk.Enabled)
75}
76
77func (vndk *vndkdep) isVndkSp() bool {
78 return Bool(vndk.Properties.Vndk.Support_system_process)
79}
80
Logan Chienf3511742017-10-31 18:04:35 +080081func (vndk *vndkdep) isVndkExt() bool {
82 return vndk.Properties.Vndk.Extends != nil
83}
84
85func (vndk *vndkdep) getVndkExtendsModuleName() string {
86 return String(vndk.Properties.Vndk.Extends)
87}
88
Justin Yun8effde42017-06-23 19:24:43 +090089func (vndk *vndkdep) typeName() string {
90 if !vndk.isVndk() {
91 return "native:vendor"
92 }
Logan Chienf3511742017-10-31 18:04:35 +080093 if !vndk.isVndkExt() {
94 if !vndk.isVndkSp() {
95 return "native:vendor:vndk"
96 }
97 return "native:vendor:vndksp"
Justin Yun8effde42017-06-23 19:24:43 +090098 }
Logan Chienf3511742017-10-31 18:04:35 +080099 if !vndk.isVndkSp() {
100 return "native:vendor:vndkext"
101 }
102 return "native:vendor:vndkspext"
Justin Yun8effde42017-06-23 19:24:43 +0900103}
104
Logan Chienf3511742017-10-31 18:04:35 +0800105func (vndk *vndkdep) vndkCheckLinkType(ctx android.ModuleContext, to *Module, tag dependencyTag) {
Justin Yun8effde42017-06-23 19:24:43 +0900106 if to.linker == nil {
107 return
108 }
Jiyong Park82e2bf32017-08-16 14:05:54 +0900109 if !vndk.isVndk() {
110 // Non-VNDK modules (those installed to /vendor) can't depend on modules marked with
111 // vendor_available: false.
112 violation := false
Nan Zhang0007d812017-11-07 10:57:05 -0800113 if lib, ok := to.linker.(*llndkStubDecorator); ok && !Bool(lib.Properties.Vendor_available) {
Jiyong Park82e2bf32017-08-16 14:05:54 +0900114 violation = true
115 } else {
116 if _, ok := to.linker.(libraryInterface); ok && to.VendorProperties.Vendor_available != nil && !Bool(to.VendorProperties.Vendor_available) {
117 // Vendor_available == nil && !Bool(Vendor_available) should be okay since
118 // it means a vendor-only library which is a valid dependency for non-VNDK
119 // modules.
120 violation = true
121 }
122 }
123 if violation {
124 ctx.ModuleErrorf("Vendor module that is not VNDK should not link to %q which is marked as `vendor_available: false`", to.Name())
125 }
126 }
Justin Yun8effde42017-06-23 19:24:43 +0900127 if lib, ok := to.linker.(*libraryDecorator); !ok || !lib.shared() {
128 // Check only shared libraries.
129 // Other (static and LL-NDK) libraries are allowed to link.
130 return
131 }
132 if !to.Properties.UseVndk {
133 ctx.ModuleErrorf("(%s) should not link to %q which is not a vendor-available library",
134 vndk.typeName(), to.Name())
135 return
136 }
Logan Chienf3511742017-10-31 18:04:35 +0800137 if tag == vndkExtDepTag {
138 // Ensure `extends: "name"` property refers a vndk module that has vendor_available
139 // and has identical vndk properties.
140 if to.vndkdep == nil || !to.vndkdep.isVndk() {
141 ctx.ModuleErrorf("`extends` refers a non-vndk module %q", to.Name())
142 return
143 }
144 if vndk.isVndkSp() != to.vndkdep.isVndkSp() {
145 ctx.ModuleErrorf(
146 "`extends` refers a module %q with mismatched support_system_process",
147 to.Name())
148 return
149 }
150 if !Bool(to.VendorProperties.Vendor_available) {
151 ctx.ModuleErrorf(
152 "`extends` refers module %q which does not have `vendor_available: true`",
153 to.Name())
154 return
155 }
156 }
Justin Yun8effde42017-06-23 19:24:43 +0900157 if to.vndkdep == nil {
158 return
159 }
Logan Chienf3511742017-10-31 18:04:35 +0800160
Logan Chiend3c59a22018-03-29 14:08:15 +0800161 // Check the dependencies of VNDK shared libraries.
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100162 if err := vndkIsVndkDepAllowed(vndk, to.vndkdep); err != nil {
163 ctx.ModuleErrorf("(%s) should not link to %q (%s): %v",
164 vndk.typeName(), to.Name(), to.vndkdep.typeName(), err)
Logan Chienf3511742017-10-31 18:04:35 +0800165 return
166 }
Logan Chiend3c59a22018-03-29 14:08:15 +0800167}
Logan Chienf3511742017-10-31 18:04:35 +0800168
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100169func vndkIsVndkDepAllowed(from *vndkdep, to *vndkdep) error {
Logan Chiend3c59a22018-03-29 14:08:15 +0800170 // Check the dependencies of VNDK, VNDK-Ext, VNDK-SP, VNDK-SP-Ext and vendor modules.
171 if from.isVndkExt() {
172 if from.isVndkSp() {
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100173 if to.isVndk() && !to.isVndkSp() {
174 return errors.New("VNDK-SP extensions must not depend on VNDK or VNDK extensions")
175 }
176 return nil
Logan Chiend3c59a22018-03-29 14:08:15 +0800177 }
178 // VNDK-Ext may depend on VNDK, VNDK-Ext, VNDK-SP, VNDK-SP-Ext, or vendor libs.
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100179 return nil
Justin Yun8effde42017-06-23 19:24:43 +0900180 }
Logan Chiend3c59a22018-03-29 14:08:15 +0800181 if from.isVndk() {
182 if to.isVndkExt() {
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100183 return errors.New("VNDK-core and VNDK-SP must not depend on VNDK extensions")
Logan Chiend3c59a22018-03-29 14:08:15 +0800184 }
185 if from.isVndkSp() {
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100186 if !to.isVndkSp() {
187 return errors.New("VNDK-SP must only depend on VNDK-SP")
188 }
189 return nil
Logan Chiend3c59a22018-03-29 14:08:15 +0800190 }
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100191 if !to.isVndk() {
192 return errors.New("VNDK-core must only depend on VNDK-core or VNDK-SP")
193 }
194 return nil
Logan Chiend3c59a22018-03-29 14:08:15 +0800195 }
196 // Vendor modules may depend on VNDK, VNDK-Ext, VNDK-SP, VNDK-SP-Ext, or vendor libs.
Martin Stjernholm257eb0c2018-10-15 13:05:27 +0100197 return nil
Justin Yun8effde42017-06-23 19:24:43 +0900198}
Jiyong Parkd5b18a52017-08-03 21:22:50 +0900199
200var (
Inseob Kim9516ee92019-05-09 10:56:13 +0900201 vndkCoreLibrariesKey = android.NewOnceKey("vndkCoreLibrarires")
202 vndkSpLibrariesKey = android.NewOnceKey("vndkSpLibrarires")
203 llndkLibrariesKey = android.NewOnceKey("llndkLibrarires")
204 vndkPrivateLibrariesKey = android.NewOnceKey("vndkPrivateLibrarires")
205 vndkUsingCoreVariantLibrariesKey = android.NewOnceKey("vndkUsingCoreVariantLibrarires")
Inseob Kim1f086e22019-05-09 13:29:15 +0900206 modulePathsKey = android.NewOnceKey("modulePaths")
207 vndkSnapshotOutputsKey = android.NewOnceKey("vndkSnapshotOutputs")
Inseob Kim9516ee92019-05-09 10:56:13 +0900208 vndkLibrariesLock sync.Mutex
Jiyong Parkd5b18a52017-08-03 21:22:50 +0900209
Inseob Kimae553032019-05-14 18:52:49 +0900210 headerExts = []string{".h", ".hh", ".hpp", ".hxx", ".h++", ".inl", ".inc", ".ipp", ".h.generic"}
211)
Inseob Kim1f086e22019-05-09 13:29:15 +0900212
Inseob Kim9516ee92019-05-09 10:56:13 +0900213func vndkCoreLibraries(config android.Config) *[]string {
214 return config.Once(vndkCoreLibrariesKey, func() interface{} {
215 return &[]string{}
216 }).(*[]string)
217}
218
219func vndkSpLibraries(config android.Config) *[]string {
220 return config.Once(vndkSpLibrariesKey, func() interface{} {
221 return &[]string{}
222 }).(*[]string)
223}
224
225func llndkLibraries(config android.Config) *[]string {
226 return config.Once(llndkLibrariesKey, func() interface{} {
227 return &[]string{}
228 }).(*[]string)
229}
230
231func vndkPrivateLibraries(config android.Config) *[]string {
232 return config.Once(vndkPrivateLibrariesKey, func() interface{} {
233 return &[]string{}
234 }).(*[]string)
235}
236
237func vndkUsingCoreVariantLibraries(config android.Config) *[]string {
238 return config.Once(vndkUsingCoreVariantLibrariesKey, func() interface{} {
239 return &[]string{}
240 }).(*[]string)
241}
242
Inseob Kim1f086e22019-05-09 13:29:15 +0900243func modulePaths(config android.Config) map[string]string {
244 return config.Once(modulePathsKey, func() interface{} {
245 return make(map[string]string)
246 }).(map[string]string)
247}
Inseob Kim9516ee92019-05-09 10:56:13 +0900248
Inseob Kimae553032019-05-14 18:52:49 +0900249func vndkSnapshotOutputs(config android.Config) *android.RuleBuilderInstalls {
Inseob Kim1f086e22019-05-09 13:29:15 +0900250 return config.Once(vndkSnapshotOutputsKey, func() interface{} {
Inseob Kimae553032019-05-14 18:52:49 +0900251 return &android.RuleBuilderInstalls{}
252 }).(*android.RuleBuilderInstalls)
Inseob Kim1f086e22019-05-09 13:29:15 +0900253}
Inseob Kim9516ee92019-05-09 10:56:13 +0900254
Inseob Kim1f086e22019-05-09 13:29:15 +0900255func processLlndkLibrary(mctx android.BottomUpMutatorContext, m *Module) {
256 lib := m.linker.(*llndkStubDecorator)
257 name := strings.TrimSuffix(m.Name(), llndkLibrarySuffix)
Inseob Kim9516ee92019-05-09 10:56:13 +0900258
Inseob Kim1f086e22019-05-09 13:29:15 +0900259 vndkLibrariesLock.Lock()
260 defer vndkLibrariesLock.Unlock()
Inseob Kim9516ee92019-05-09 10:56:13 +0900261
Inseob Kim1f086e22019-05-09 13:29:15 +0900262 llndkLibraries := llndkLibraries(mctx.Config())
263 if !inList(name, *llndkLibraries) {
264 *llndkLibraries = append(*llndkLibraries, name)
265 sort.Strings(*llndkLibraries)
266 }
267 if !Bool(lib.Properties.Vendor_available) {
268 vndkPrivateLibraries := vndkPrivateLibraries(mctx.Config())
269 if !inList(name, *vndkPrivateLibraries) {
270 *vndkPrivateLibraries = append(*vndkPrivateLibraries, name)
271 sort.Strings(*vndkPrivateLibraries)
Jiyong Parkd5b18a52017-08-03 21:22:50 +0900272 }
273 }
274}
Inseob Kim1f086e22019-05-09 13:29:15 +0900275
276func processVndkLibrary(mctx android.BottomUpMutatorContext, m *Module) {
277 name := strings.TrimPrefix(m.Name(), "prebuilt_")
278
279 vndkLibrariesLock.Lock()
280 defer vndkLibrariesLock.Unlock()
281
282 modulePaths := modulePaths(mctx.Config())
283 if mctx.DeviceConfig().VndkUseCoreVariant() && !inList(name, config.VndkMustUseVendorVariantList) {
284 vndkUsingCoreVariantLibraries := vndkUsingCoreVariantLibraries(mctx.Config())
285 if !inList(name, *vndkUsingCoreVariantLibraries) {
286 *vndkUsingCoreVariantLibraries = append(*vndkUsingCoreVariantLibraries, name)
287 sort.Strings(*vndkUsingCoreVariantLibraries)
288 }
289 }
290 if m.vndkdep.isVndkSp() {
291 vndkSpLibraries := vndkSpLibraries(mctx.Config())
292 if !inList(name, *vndkSpLibraries) {
293 *vndkSpLibraries = append(*vndkSpLibraries, name)
294 sort.Strings(*vndkSpLibraries)
295 modulePaths[name] = mctx.ModuleDir()
296 }
297 } else {
298 vndkCoreLibraries := vndkCoreLibraries(mctx.Config())
299 if !inList(name, *vndkCoreLibraries) {
300 *vndkCoreLibraries = append(*vndkCoreLibraries, name)
301 sort.Strings(*vndkCoreLibraries)
302 modulePaths[name] = mctx.ModuleDir()
303 }
304 }
305 if !Bool(m.VendorProperties.Vendor_available) {
306 vndkPrivateLibraries := vndkPrivateLibraries(mctx.Config())
307 if !inList(name, *vndkPrivateLibraries) {
308 *vndkPrivateLibraries = append(*vndkPrivateLibraries, name)
309 sort.Strings(*vndkPrivateLibraries)
310 }
311 }
312}
313
314// gather list of vndk-core, vndk-sp, and ll-ndk libs
315func VndkMutator(mctx android.BottomUpMutatorContext) {
316 m, ok := mctx.Module().(*Module)
317 if !ok {
318 return
319 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900320 if !m.Enabled() {
321 return
322 }
Justin Yun7390ea32019-09-08 11:34:06 +0900323 if m.Target().NativeBridge == android.NativeBridgeEnabled {
324 // Skip native_bridge modules
325 return
326 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900327
Jooyung Han76106d92019-05-20 18:49:10 +0900328 if m.isVndk() {
329 if lib, ok := m.linker.(*vndkPrebuiltLibraryDecorator); ok {
330 m.vndkdep.Properties.Vndk.Version = lib.version()
331 } else {
332 m.vndkdep.Properties.Vndk.Version = mctx.DeviceConfig().PlatformVndkVersion()
333 }
334 }
335
Inseob Kim1f086e22019-05-09 13:29:15 +0900336 if _, ok := m.linker.(*llndkStubDecorator); ok {
337 processLlndkLibrary(mctx, m)
338 return
339 }
340
341 lib, is_lib := m.linker.(*libraryDecorator)
342 prebuilt_lib, is_prebuilt_lib := m.linker.(*prebuiltLibraryLinker)
343
344 if (is_lib && lib.shared()) || (is_prebuilt_lib && prebuilt_lib.shared()) {
345 if m.vndkdep.isVndk() && !m.vndkdep.isVndkExt() {
346 processVndkLibrary(mctx, m)
347 return
348 }
349 }
350}
351
352func init() {
353 android.RegisterSingletonType("vndk-snapshot", VndkSnapshotSingleton)
354 android.RegisterMakeVarsProvider(pctx, func(ctx android.MakeVarsContext) {
355 outputs := vndkSnapshotOutputs(ctx.Config())
Inseob Kimae553032019-05-14 18:52:49 +0900356 ctx.Strict("SOONG_VNDK_SNAPSHOT_FILES", outputs.String())
Inseob Kim1f086e22019-05-09 13:29:15 +0900357 })
358}
359
360func VndkSnapshotSingleton() android.Singleton {
361 return &vndkSnapshotSingleton{}
362}
363
364type vndkSnapshotSingleton struct{}
365
Inseob Kim1f086e22019-05-09 13:29:15 +0900366func (c *vndkSnapshotSingleton) GenerateBuildActions(ctx android.SingletonContext) {
367 // BOARD_VNDK_VERSION must be set to 'current' in order to generate a VNDK snapshot.
368 if ctx.DeviceConfig().VndkVersion() != "current" {
369 return
370 }
371
372 if ctx.DeviceConfig().PlatformVndkVersion() == "" {
373 return
374 }
375
376 if ctx.DeviceConfig().BoardVndkRuntimeDisable() {
377 return
378 }
379
380 outputs := vndkSnapshotOutputs(ctx.Config())
381
382 snapshotDir := "vndk-snapshot"
383
Inseob Kimae553032019-05-14 18:52:49 +0900384 vndkLibDir := make(map[android.ArchType]string)
Inseob Kim1f086e22019-05-09 13:29:15 +0900385
Inseob Kimae553032019-05-14 18:52:49 +0900386 snapshotVariantDir := ctx.DeviceConfig().DeviceArch()
387 for _, target := range ctx.Config().Targets[android.Android] {
388 dir := snapshotVariantDir
389 if ctx.DeviceConfig().BinderBitness() == "32" {
390 dir = filepath.Join(dir, "binder32")
391 }
392 arch := "arch-" + target.Arch.ArchType.String()
393 if target.Arch.ArchVariant != "" {
394 arch += "-" + target.Arch.ArchVariant
395 }
396 dir = filepath.Join(dir, arch)
397 vndkLibDir[target.Arch.ArchType] = dir
Inseob Kim1f086e22019-05-09 13:29:15 +0900398 }
Inseob Kimae553032019-05-14 18:52:49 +0900399 configsDir := filepath.Join(snapshotVariantDir, "configs")
400 noticeDir := filepath.Join(snapshotVariantDir, "NOTICE_FILES")
401 includeDir := filepath.Join(snapshotVariantDir, "include")
Inseob Kim1f086e22019-05-09 13:29:15 +0900402 noticeBuilt := make(map[string]bool)
403
Inseob Kimae553032019-05-14 18:52:49 +0900404 installSnapshotFileFromPath := func(path android.Path, out string) {
405 ctx.Build(pctx, android.BuildParams{
406 Rule: android.Cp,
407 Input: path,
408 Output: android.PathForOutput(ctx, snapshotDir, out),
409 Description: "vndk snapshot " + out,
410 Args: map[string]string{
411 "cpFlags": "-f -L",
412 },
413 })
414 *outputs = append(*outputs, android.RuleBuilderInstall{
415 From: android.PathForOutput(ctx, snapshotDir, out),
416 To: out,
417 })
418 }
419 installSnapshotFileFromContent := func(content, out string) {
420 ctx.Build(pctx, android.BuildParams{
421 Rule: android.WriteFile,
422 Output: android.PathForOutput(ctx, snapshotDir, out),
423 Description: "vndk snapshot " + out,
424 Args: map[string]string{
425 "content": content,
426 },
427 })
428 *outputs = append(*outputs, android.RuleBuilderInstall{
429 From: android.PathForOutput(ctx, snapshotDir, out),
430 To: out,
431 })
432 }
433
Inseob Kim1f086e22019-05-09 13:29:15 +0900434 tryBuildNotice := func(m *Module) {
Inseob Kimae553032019-05-14 18:52:49 +0900435 name := ctx.ModuleName(m) + ".so.txt"
Inseob Kim1f086e22019-05-09 13:29:15 +0900436
437 if _, ok := noticeBuilt[name]; ok {
438 return
439 }
440
441 noticeBuilt[name] = true
442
443 if m.NoticeFile().Valid() {
Inseob Kimae553032019-05-14 18:52:49 +0900444 installSnapshotFileFromPath(m.NoticeFile().Path(), filepath.Join(noticeDir, name))
Inseob Kim1f086e22019-05-09 13:29:15 +0900445 }
446 }
447
448 vndkCoreLibraries := vndkCoreLibraries(ctx.Config())
449 vndkSpLibraries := vndkSpLibraries(ctx.Config())
450 vndkPrivateLibraries := vndkPrivateLibraries(ctx.Config())
451
Inseob Kimae553032019-05-14 18:52:49 +0900452 var generatedHeaders android.Paths
453 includeDirs := make(map[string]bool)
454
455 type vndkSnapshotLibraryInterface interface {
456 exportedFlagsProducer
457 libraryInterface
458 }
459
460 var _ vndkSnapshotLibraryInterface = (*prebuiltLibraryLinker)(nil)
461 var _ vndkSnapshotLibraryInterface = (*libraryDecorator)(nil)
462
463 installVndkSnapshotLib := func(m *Module, l vndkSnapshotLibraryInterface, dir string) bool {
464 name := ctx.ModuleName(m)
465 libOut := filepath.Join(dir, name+".so")
466
467 installSnapshotFileFromPath(m.outputFile.Path(), libOut)
468 tryBuildNotice(m)
469
470 if ctx.Config().VndkSnapshotBuildArtifacts() {
471 prop := struct {
472 ExportedDirs []string `json:",omitempty"`
473 ExportedSystemDirs []string `json:",omitempty"`
474 ExportedFlags []string `json:",omitempty"`
475 RelativeInstallPath string `json:",omitempty"`
476 }{}
477 prop.ExportedFlags = l.exportedFlags()
478 prop.ExportedDirs = l.exportedDirs()
479 prop.ExportedSystemDirs = l.exportedSystemDirs()
480 prop.RelativeInstallPath = m.RelativeInstallPath()
481
482 propOut := libOut + ".json"
483
484 j, err := json.Marshal(prop)
485 if err != nil {
486 ctx.Errorf("json marshal to %q failed: %#v", propOut, err)
487 return false
488 }
489
490 installSnapshotFileFromContent(string(j), propOut)
491 }
492 return true
493 }
494
495 isVndkSnapshotLibrary := func(m *Module) (i vndkSnapshotLibraryInterface, libDir string, isVndkSnapshotLib bool) {
496 if m.Target().NativeBridge == android.NativeBridgeEnabled {
497 return nil, "", false
498 }
499 if !m.useVndk() || !m.IsForPlatform() || !m.installable() {
500 return nil, "", false
501 }
502 l, ok := m.linker.(vndkSnapshotLibraryInterface)
503 if !ok || !l.shared() {
504 return nil, "", false
505 }
506 name := ctx.ModuleName(m)
507 if inList(name, *vndkCoreLibraries) {
508 return l, filepath.Join("shared", "vndk-core"), true
509 } else if inList(name, *vndkSpLibraries) {
510 return l, filepath.Join("shared", "vndk-sp"), true
511 } else {
512 return nil, "", false
513 }
514 }
515
Inseob Kim1f086e22019-05-09 13:29:15 +0900516 ctx.VisitAllModules(func(module android.Module) {
517 m, ok := module.(*Module)
Inseob Kimae553032019-05-14 18:52:49 +0900518 if !ok || !m.Enabled() {
Inseob Kim1f086e22019-05-09 13:29:15 +0900519 return
520 }
521
Inseob Kimae553032019-05-14 18:52:49 +0900522 baseDir, ok := vndkLibDir[m.Target().Arch.ArchType]
523 if !ok {
dimitry51ea18a2019-05-20 10:39:52 +0200524 return
525 }
526
Inseob Kimae553032019-05-14 18:52:49 +0900527 l, libDir, ok := isVndkSnapshotLibrary(m)
528 if !ok {
Inseob Kim1f086e22019-05-09 13:29:15 +0900529 return
530 }
531
Inseob Kimae553032019-05-14 18:52:49 +0900532 if !installVndkSnapshotLib(m, l, filepath.Join(baseDir, libDir)) {
533 return
534 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900535
Inseob Kimae553032019-05-14 18:52:49 +0900536 generatedHeaders = append(generatedHeaders, l.exportedDeps()...)
537 for _, dir := range append(l.exportedDirs(), l.exportedSystemDirs()...) {
538 includeDirs[dir] = true
539 }
540 })
Inseob Kim1f086e22019-05-09 13:29:15 +0900541
Inseob Kimae553032019-05-14 18:52:49 +0900542 if ctx.Config().VndkSnapshotBuildArtifacts() {
543 headers := make(map[string]bool)
544
545 for _, dir := range android.SortedStringKeys(includeDirs) {
546 // workaround to determine if dir is under output directory
547 if strings.HasPrefix(dir, android.PathForOutput(ctx).String()) {
548 continue
Inseob Kim1f086e22019-05-09 13:29:15 +0900549 }
Inseob Kimae553032019-05-14 18:52:49 +0900550 exts := headerExts
551 // Glob all files under this special directory, because of C++ headers.
552 if strings.HasPrefix(dir, "external/libcxx/include") {
553 exts = []string{""}
Inseob Kim1f086e22019-05-09 13:29:15 +0900554 }
Inseob Kimae553032019-05-14 18:52:49 +0900555 for _, ext := range exts {
556 glob, err := ctx.GlobWithDeps(dir+"/**/*"+ext, nil)
557 if err != nil {
558 ctx.Errorf("%#v\n", err)
559 return
560 }
561 for _, header := range glob {
562 if strings.HasSuffix(header, "/") {
563 continue
564 }
565 headers[header] = true
566 }
567 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900568 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900569
Inseob Kimae553032019-05-14 18:52:49 +0900570 for _, header := range android.SortedStringKeys(headers) {
571 installSnapshotFileFromPath(android.PathForSource(ctx, header),
572 filepath.Join(includeDir, header))
573 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900574
Inseob Kimae553032019-05-14 18:52:49 +0900575 isHeader := func(path string) bool {
576 for _, ext := range headerExts {
577 if strings.HasSuffix(path, ext) {
578 return true
579 }
580 }
581 return false
582 }
Inseob Kim1f086e22019-05-09 13:29:15 +0900583
Inseob Kimae553032019-05-14 18:52:49 +0900584 for _, path := range android.PathsToDirectorySortedPaths(android.FirstUniquePaths(generatedHeaders)) {
585 header := path.String()
586
587 if !isHeader(header) {
588 continue
589 }
590
591 installSnapshotFileFromPath(path, filepath.Join(includeDir, header))
592 }
593 }
594
595 installSnapshotFileFromContent(android.JoinWithSuffix(*vndkCoreLibraries, ".so", "\\n"),
596 filepath.Join(configsDir, "vndkcore.libraries.txt"))
597 installSnapshotFileFromContent(android.JoinWithSuffix(*vndkPrivateLibraries, ".so", "\\n"),
598 filepath.Join(configsDir, "vndkprivate.libraries.txt"))
Inseob Kim1f086e22019-05-09 13:29:15 +0900599
600 var modulePathTxtBuilder strings.Builder
601
Colin Cross4c2c46f2019-06-03 15:26:05 -0700602 modulePaths := modulePaths(ctx.Config())
Colin Cross4c2c46f2019-06-03 15:26:05 -0700603
Inseob Kim1f086e22019-05-09 13:29:15 +0900604 first := true
Inseob Kimae553032019-05-14 18:52:49 +0900605 for _, lib := range android.SortedStringKeys(modulePaths) {
Inseob Kim1f086e22019-05-09 13:29:15 +0900606 if first {
607 first = false
608 } else {
609 modulePathTxtBuilder.WriteString("\\n")
610 }
611 modulePathTxtBuilder.WriteString(lib)
612 modulePathTxtBuilder.WriteString(".so ")
Colin Cross4c2c46f2019-06-03 15:26:05 -0700613 modulePathTxtBuilder.WriteString(modulePaths[lib])
Inseob Kim1f086e22019-05-09 13:29:15 +0900614 }
615
Inseob Kimae553032019-05-14 18:52:49 +0900616 installSnapshotFileFromContent(modulePathTxtBuilder.String(),
617 filepath.Join(configsDir, "module_paths.txt"))
Inseob Kim1f086e22019-05-09 13:29:15 +0900618}