blob: 7cc587f5c0706b55e18a95ce9479e252dcfd6ab4 [file] [log] [blame]
Colin Cross4d9c2d12016-07-29 12:48:20 -07001// Copyright 2016 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 (
18 "strings"
19
20 "github.com/google/blueprint"
21
22 "android/soong"
23 "android/soong/android"
24)
25
Colin Crossb916a382016-07-29 17:28:03 -070026type LibraryProperties struct {
Colin Cross4d9c2d12016-07-29 12:48:20 -070027 Static struct {
28 Srcs []string `android:"arch_variant"`
29 Exclude_srcs []string `android:"arch_variant"`
30 Cflags []string `android:"arch_variant"`
Colin Cross4d9c2d12016-07-29 12:48:20 -070031
Colin Cross4d9c2d12016-07-29 12:48:20 -070032 Enabled *bool `android:"arch_variant"`
33 Whole_static_libs []string `android:"arch_variant"`
34 Static_libs []string `android:"arch_variant"`
35 Shared_libs []string `android:"arch_variant"`
36 } `android:"arch_variant"`
37 Shared struct {
Colin Crossb916a382016-07-29 17:28:03 -070038 Srcs []string `android:"arch_variant"`
39 Exclude_srcs []string `android:"arch_variant"`
40 Cflags []string `android:"arch_variant"`
41
Colin Cross4d9c2d12016-07-29 12:48:20 -070042 Enabled *bool `android:"arch_variant"`
43 Whole_static_libs []string `android:"arch_variant"`
44 Static_libs []string `android:"arch_variant"`
45 Shared_libs []string `android:"arch_variant"`
46 } `android:"arch_variant"`
47
48 // local file name to pass to the linker as --version_script
49 Version_script *string `android:"arch_variant"`
50 // local file name to pass to the linker as -unexported_symbols_list
51 Unexported_symbols_list *string `android:"arch_variant"`
52 // local file name to pass to the linker as -force_symbols_not_weak_list
53 Force_symbols_not_weak_list *string `android:"arch_variant"`
54 // local file name to pass to the linker as -force_symbols_weak_list
55 Force_symbols_weak_list *string `android:"arch_variant"`
56
57 // rename host libraries to prevent overlap with system installed libraries
58 Unique_host_soname *bool
59
60 VariantName string `blueprint:"mutated"`
Colin Crossb916a382016-07-29 17:28:03 -070061
62 // Build a static variant
63 BuildStatic bool `blueprint:"mutated"`
64 // Build a shared variant
65 BuildShared bool `blueprint:"mutated"`
66 // This variant is shared
67 VariantIsShared bool `blueprint:"mutated"`
68 // This variant is static
69 VariantIsStatic bool `blueprint:"mutated"`
70}
71
72type FlagExporterProperties struct {
73 // list of directories relative to the Blueprints file that will
74 // be added to the include path using -I for any module that links against this module
75 Export_include_dirs []string `android:"arch_variant"`
Colin Cross4d9c2d12016-07-29 12:48:20 -070076}
77
78func init() {
79 soong.RegisterModuleType("cc_library_static", libraryStaticFactory)
80 soong.RegisterModuleType("cc_library_shared", librarySharedFactory)
81 soong.RegisterModuleType("cc_library", libraryFactory)
82 soong.RegisterModuleType("cc_library_host_static", libraryHostStaticFactory)
83 soong.RegisterModuleType("cc_library_host_shared", libraryHostSharedFactory)
84}
85
86// Module factory for combined static + shared libraries, device by default but with possible host
87// support
88func libraryFactory() (blueprint.Module, []interface{}) {
Colin Crossb916a382016-07-29 17:28:03 -070089 module, _ := NewLibrary(android.HostAndDeviceSupported, true, true)
Colin Cross4d9c2d12016-07-29 12:48:20 -070090 return module.Init()
91}
92
93// Module factory for static libraries
94func libraryStaticFactory() (blueprint.Module, []interface{}) {
Colin Crossb916a382016-07-29 17:28:03 -070095 module, _ := NewLibrary(android.HostAndDeviceSupported, false, true)
Colin Cross4d9c2d12016-07-29 12:48:20 -070096 return module.Init()
97}
98
99// Module factory for shared libraries
100func librarySharedFactory() (blueprint.Module, []interface{}) {
Colin Crossb916a382016-07-29 17:28:03 -0700101 module, _ := NewLibrary(android.HostAndDeviceSupported, true, false)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700102 return module.Init()
103}
104
105// Module factory for host static libraries
106func libraryHostStaticFactory() (blueprint.Module, []interface{}) {
Colin Crossb916a382016-07-29 17:28:03 -0700107 module, _ := NewLibrary(android.HostSupported, false, true)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700108 return module.Init()
109}
110
111// Module factory for host shared libraries
112func libraryHostSharedFactory() (blueprint.Module, []interface{}) {
Colin Crossb916a382016-07-29 17:28:03 -0700113 module, _ := NewLibrary(android.HostSupported, true, false)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700114 return module.Init()
115}
116
117type flagExporter struct {
118 Properties FlagExporterProperties
119
Dan Willemsen847dcc72016-09-29 12:13:36 -0700120 flags []string
121 flagsDeps android.Paths
Colin Cross4d9c2d12016-07-29 12:48:20 -0700122}
123
124func (f *flagExporter) exportIncludes(ctx ModuleContext, inc string) {
125 includeDirs := android.PathsForModuleSrc(ctx, f.Properties.Export_include_dirs)
126 for _, dir := range includeDirs.Strings() {
127 f.flags = append(f.flags, inc+dir)
128 }
129}
130
131func (f *flagExporter) reexportFlags(flags []string) {
132 f.flags = append(f.flags, flags...)
133}
134
Dan Willemsen847dcc72016-09-29 12:13:36 -0700135func (f *flagExporter) reexportDeps(deps android.Paths) {
136 f.flagsDeps = append(f.flagsDeps, deps...)
137}
138
Colin Cross4d9c2d12016-07-29 12:48:20 -0700139func (f *flagExporter) exportedFlags() []string {
140 return f.flags
141}
142
Dan Willemsen847dcc72016-09-29 12:13:36 -0700143func (f *flagExporter) exportedFlagsDeps() android.Paths {
144 return f.flagsDeps
145}
146
Colin Cross4d9c2d12016-07-29 12:48:20 -0700147type exportedFlagsProducer interface {
148 exportedFlags() []string
Dan Willemsen847dcc72016-09-29 12:13:36 -0700149 exportedFlagsDeps() android.Paths
Colin Cross4d9c2d12016-07-29 12:48:20 -0700150}
151
152var _ exportedFlagsProducer = (*flagExporter)(nil)
153
Colin Crossb916a382016-07-29 17:28:03 -0700154// libraryDecorator wraps baseCompiler, baseLinker and baseInstaller to provide library-specific
155// functionality: static vs. shared linkage, reusing object files for shared libraries
156type libraryDecorator struct {
157 Properties LibraryProperties
Colin Cross4d9c2d12016-07-29 12:48:20 -0700158
159 // For reusing static library objects for shared library
160 reuseObjFiles android.Paths
Colin Cross4d9c2d12016-07-29 12:48:20 -0700161
Colin Cross4d9c2d12016-07-29 12:48:20 -0700162 flagExporter
163 stripper
Dan Willemsen394e9dc2016-09-14 15:04:48 -0700164 relocationPacker
Colin Cross4d9c2d12016-07-29 12:48:20 -0700165
Colin Cross4d9c2d12016-07-29 12:48:20 -0700166 // If we're used as a whole_static_lib, our missing dependencies need
167 // to be given
168 wholeStaticMissingDeps []string
169
170 // For whole_static_libs
171 objFiles android.Paths
172
173 // Uses the module's name if empty, but can be overridden. Does not include
174 // shlib suffix.
175 libName string
Colin Crossb916a382016-07-29 17:28:03 -0700176
177 sanitize *sanitize
178
179 // Decorated interafaces
180 *baseCompiler
181 *baseLinker
182 *baseInstaller
Colin Cross4d9c2d12016-07-29 12:48:20 -0700183}
184
Colin Crossb916a382016-07-29 17:28:03 -0700185func (library *libraryDecorator) linkerProps() []interface{} {
186 var props []interface{}
187 props = append(props, library.baseLinker.linkerProps()...)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700188 return append(props,
189 &library.Properties,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700190 &library.flagExporter.Properties,
Dan Willemsen394e9dc2016-09-14 15:04:48 -0700191 &library.stripper.StripProperties,
192 &library.relocationPacker.Properties)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700193}
194
Colin Crossb916a382016-07-29 17:28:03 -0700195func (library *libraryDecorator) linkerFlags(ctx ModuleContext, flags Flags) Flags {
Colin Cross42742b82016-08-01 13:20:05 -0700196 flags = library.baseLinker.linkerFlags(ctx, flags)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700197
Colin Crossb916a382016-07-29 17:28:03 -0700198 // MinGW spits out warnings about -fPIC even for -fpie?!) being ignored because
199 // all code is position independent, and then those warnings get promoted to
200 // errors.
201 if ctx.Os() != android.Windows {
202 flags.CFlags = append(flags.CFlags, "-fPIC")
203 }
204
205 if library.static() {
206 flags.CFlags = append(flags.CFlags, library.Properties.Static.Cflags...)
207 } else {
208 flags.CFlags = append(flags.CFlags, library.Properties.Shared.Cflags...)
209 }
210
Colin Cross4d9c2d12016-07-29 12:48:20 -0700211 if !library.static() {
212 libName := library.getLibName(ctx)
213 // GCC for Android assumes that -shared means -Bsymbolic, use -Wl,-shared instead
214 sharedFlag := "-Wl,-shared"
215 if flags.Clang || ctx.Host() {
216 sharedFlag = "-shared"
217 }
218 var f []string
219 if ctx.Device() {
220 f = append(f,
221 "-nostdlib",
222 "-Wl,--gc-sections",
223 )
224 }
225
226 if ctx.Darwin() {
227 f = append(f,
228 "-dynamiclib",
229 "-single_module",
Colin Cross7d82ab72016-08-25 16:54:53 -0700230 "-read_only_relocs suppress",
Colin Cross4d9c2d12016-07-29 12:48:20 -0700231 "-install_name @rpath/"+libName+flags.Toolchain.ShlibSuffix(),
232 )
233 } else {
234 f = append(f,
235 sharedFlag,
236 "-Wl,-soname,"+libName+flags.Toolchain.ShlibSuffix())
237 }
238
239 flags.LdFlags = append(f, flags.LdFlags...)
240 }
241
242 return flags
243}
244
Colin Crossb916a382016-07-29 17:28:03 -0700245func (library *libraryDecorator) compile(ctx ModuleContext, flags Flags, deps PathDeps) android.Paths {
246 var objFiles android.Paths
247
248 objFiles = library.baseCompiler.compile(ctx, flags, deps)
249 library.reuseObjFiles = objFiles
250
251 pathDeps := deps.GeneratedHeaders
252 pathDeps = append(pathDeps, ndkPathDeps(ctx)...)
253
Colin Cross4d9c2d12016-07-29 12:48:20 -0700254 if library.static() {
Colin Crossb916a382016-07-29 17:28:03 -0700255 objFiles = append(objFiles, compileObjs(ctx, flags, android.DeviceStaticLibrary,
256 library.Properties.Static.Srcs, library.Properties.Static.Exclude_srcs,
257 nil, pathDeps)...)
258 } else {
259 objFiles = append(objFiles, compileObjs(ctx, flags, android.DeviceSharedLibrary,
260 library.Properties.Shared.Srcs, library.Properties.Shared.Exclude_srcs,
261 nil, pathDeps)...)
262 }
263
264 return objFiles
265}
266
267type libraryInterface interface {
268 getWholeStaticMissingDeps() []string
269 static() bool
270 objs() android.Paths
271 reuseObjs() android.Paths
272
273 // Returns true if the build options for the module have selected a static or shared build
274 buildStatic() bool
275 buildShared() bool
276
277 // Sets whether a specific variant is static or shared
278 setStatic(bool)
279}
280
281func (library *libraryDecorator) getLibName(ctx ModuleContext) string {
282 name := library.libName
283 if name == "" {
284 name = ctx.ModuleName()
285 }
286
287 if ctx.Host() && Bool(library.Properties.Unique_host_soname) {
288 if !strings.HasSuffix(name, "-host") {
289 name = name + "-host"
290 }
291 }
292
293 return name + library.Properties.VariantName
294}
295
296func (library *libraryDecorator) linkerInit(ctx BaseModuleContext) {
297 location := InstallInSystem
298 if library.sanitize.inData() {
299 location = InstallInData
300 }
301 library.baseInstaller.location = location
302
303 library.baseLinker.linkerInit(ctx)
Dan Willemsen394e9dc2016-09-14 15:04:48 -0700304
305 library.relocationPacker.packingInit(ctx)
Colin Crossb916a382016-07-29 17:28:03 -0700306}
307
308func (library *libraryDecorator) linkerDeps(ctx BaseModuleContext, deps Deps) Deps {
309 deps = library.baseLinker.linkerDeps(ctx, deps)
310
311 if library.static() {
312 deps.WholeStaticLibs = append(deps.WholeStaticLibs,
313 library.Properties.Static.Whole_static_libs...)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700314 deps.StaticLibs = append(deps.StaticLibs, library.Properties.Static.Static_libs...)
315 deps.SharedLibs = append(deps.SharedLibs, library.Properties.Static.Shared_libs...)
316 } else {
317 if ctx.Device() && !Bool(library.baseLinker.Properties.Nocrt) {
318 if !ctx.sdk() {
319 deps.CrtBegin = "crtbegin_so"
320 deps.CrtEnd = "crtend_so"
321 } else {
322 deps.CrtBegin = "ndk_crtbegin_so." + ctx.sdkVersion()
323 deps.CrtEnd = "ndk_crtend_so." + ctx.sdkVersion()
324 }
325 }
326 deps.WholeStaticLibs = append(deps.WholeStaticLibs, library.Properties.Shared.Whole_static_libs...)
327 deps.StaticLibs = append(deps.StaticLibs, library.Properties.Shared.Static_libs...)
328 deps.SharedLibs = append(deps.SharedLibs, library.Properties.Shared.Shared_libs...)
329 }
330
331 return deps
332}
333
Colin Crossb916a382016-07-29 17:28:03 -0700334func (library *libraryDecorator) linkStatic(ctx ModuleContext,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700335 flags Flags, deps PathDeps, objFiles android.Paths) android.Path {
336
337 library.objFiles = append(android.Paths{}, deps.WholeStaticLibObjFiles...)
338 library.objFiles = append(library.objFiles, objFiles...)
339
340 outputFile := android.PathForModuleOut(ctx,
341 ctx.ModuleName()+library.Properties.VariantName+staticLibraryExtension)
342
343 if ctx.Darwin() {
344 TransformDarwinObjToStaticLib(ctx, library.objFiles, flagsToBuilderFlags(flags), outputFile)
345 } else {
346 TransformObjToStaticLib(ctx, library.objFiles, flagsToBuilderFlags(flags), outputFile)
347 }
348
349 library.wholeStaticMissingDeps = ctx.GetMissingDependencies()
350
351 ctx.CheckbuildFile(outputFile)
352
353 return outputFile
354}
355
Colin Crossb916a382016-07-29 17:28:03 -0700356func (library *libraryDecorator) linkShared(ctx ModuleContext,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700357 flags Flags, deps PathDeps, objFiles android.Paths) android.Path {
358
359 var linkerDeps android.Paths
360
361 versionScript := android.OptionalPathForModuleSrc(ctx, library.Properties.Version_script)
362 unexportedSymbols := android.OptionalPathForModuleSrc(ctx, library.Properties.Unexported_symbols_list)
363 forceNotWeakSymbols := android.OptionalPathForModuleSrc(ctx, library.Properties.Force_symbols_not_weak_list)
364 forceWeakSymbols := android.OptionalPathForModuleSrc(ctx, library.Properties.Force_symbols_weak_list)
365 if !ctx.Darwin() {
366 if versionScript.Valid() {
367 flags.LdFlags = append(flags.LdFlags, "-Wl,--version-script,"+versionScript.String())
368 linkerDeps = append(linkerDeps, versionScript.Path())
369 }
370 if unexportedSymbols.Valid() {
371 ctx.PropertyErrorf("unexported_symbols_list", "Only supported on Darwin")
372 }
373 if forceNotWeakSymbols.Valid() {
374 ctx.PropertyErrorf("force_symbols_not_weak_list", "Only supported on Darwin")
375 }
376 if forceWeakSymbols.Valid() {
377 ctx.PropertyErrorf("force_symbols_weak_list", "Only supported on Darwin")
378 }
379 } else {
380 if versionScript.Valid() {
381 ctx.PropertyErrorf("version_script", "Not supported on Darwin")
382 }
383 if unexportedSymbols.Valid() {
384 flags.LdFlags = append(flags.LdFlags, "-Wl,-unexported_symbols_list,"+unexportedSymbols.String())
385 linkerDeps = append(linkerDeps, unexportedSymbols.Path())
386 }
387 if forceNotWeakSymbols.Valid() {
388 flags.LdFlags = append(flags.LdFlags, "-Wl,-force_symbols_not_weak_list,"+forceNotWeakSymbols.String())
389 linkerDeps = append(linkerDeps, forceNotWeakSymbols.Path())
390 }
391 if forceWeakSymbols.Valid() {
392 flags.LdFlags = append(flags.LdFlags, "-Wl,-force_symbols_weak_list,"+forceWeakSymbols.String())
393 linkerDeps = append(linkerDeps, forceWeakSymbols.Path())
394 }
395 }
396
397 fileName := library.getLibName(ctx) + flags.Toolchain.ShlibSuffix()
398 outputFile := android.PathForModuleOut(ctx, fileName)
399 ret := outputFile
400
401 builderFlags := flagsToBuilderFlags(flags)
402
Dan Willemsen394e9dc2016-09-14 15:04:48 -0700403 if library.relocationPacker.needsPacking(ctx) {
404 packedOutputFile := outputFile
405 outputFile = android.PathForModuleOut(ctx, "unpacked", fileName)
406 library.relocationPacker.pack(ctx, outputFile, packedOutputFile, builderFlags)
407 }
408
Colin Cross4d9c2d12016-07-29 12:48:20 -0700409 if library.stripper.needsStrip(ctx) {
410 strippedOutputFile := outputFile
411 outputFile = android.PathForModuleOut(ctx, "unstripped", fileName)
412 library.stripper.strip(ctx, outputFile, strippedOutputFile, builderFlags)
413 }
414
415 sharedLibs := deps.SharedLibs
416 sharedLibs = append(sharedLibs, deps.LateSharedLibs...)
417
Dan Albertd015c4a2016-08-10 14:34:08 -0700418 // TODO(danalbert): Clean this up when soong supports prebuilts.
419 if strings.HasPrefix(ctx.selectedStl(), "ndk_libc++") {
420 libDir := getNdkStlLibDir(ctx, flags.Toolchain, "libc++")
421
422 if strings.HasSuffix(ctx.selectedStl(), "_shared") {
423 deps.StaticLibs = append(deps.StaticLibs,
424 libDir.Join(ctx, "libandroid_support.a"))
425 } else {
426 deps.StaticLibs = append(deps.StaticLibs,
427 libDir.Join(ctx, "libc++abi.a"),
428 libDir.Join(ctx, "libandroid_support.a"))
429 }
430
431 if ctx.Arch().ArchType == android.Arm {
432 deps.StaticLibs = append(deps.StaticLibs,
433 libDir.Join(ctx, "libunwind.a"))
434 }
435 }
436
Colin Cross4d9c2d12016-07-29 12:48:20 -0700437 TransformObjToDynamicBinary(ctx, objFiles, sharedLibs,
438 deps.StaticLibs, deps.LateStaticLibs, deps.WholeStaticLibs,
439 linkerDeps, deps.CrtBegin, deps.CrtEnd, false, builderFlags, outputFile)
440
441 return ret
442}
443
Colin Crossb916a382016-07-29 17:28:03 -0700444func (library *libraryDecorator) link(ctx ModuleContext,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700445 flags Flags, deps PathDeps, objFiles android.Paths) android.Path {
446
447 objFiles = append(objFiles, deps.ObjFiles...)
448
449 var out android.Path
450 if library.static() {
451 out = library.linkStatic(ctx, flags, deps, objFiles)
452 } else {
453 out = library.linkShared(ctx, flags, deps, objFiles)
454 }
455
456 library.exportIncludes(ctx, "-I")
457 library.reexportFlags(deps.ReexportedFlags)
Dan Willemsen847dcc72016-09-29 12:13:36 -0700458 library.reexportDeps(deps.ReexportedFlagsDeps)
Colin Cross4d9c2d12016-07-29 12:48:20 -0700459
460 return out
461}
462
Colin Crossb916a382016-07-29 17:28:03 -0700463func (library *libraryDecorator) buildStatic() bool {
464 return library.Properties.BuildStatic &&
Colin Cross4d9c2d12016-07-29 12:48:20 -0700465 (library.Properties.Static.Enabled == nil || *library.Properties.Static.Enabled)
466}
467
Colin Crossb916a382016-07-29 17:28:03 -0700468func (library *libraryDecorator) buildShared() bool {
469 return library.Properties.BuildShared &&
Colin Cross4d9c2d12016-07-29 12:48:20 -0700470 (library.Properties.Shared.Enabled == nil || *library.Properties.Shared.Enabled)
471}
472
Colin Crossb916a382016-07-29 17:28:03 -0700473func (library *libraryDecorator) getWholeStaticMissingDeps() []string {
Colin Cross4d9c2d12016-07-29 12:48:20 -0700474 return library.wholeStaticMissingDeps
475}
476
Colin Crossb916a382016-07-29 17:28:03 -0700477func (library *libraryDecorator) objs() android.Paths {
Colin Cross4d9c2d12016-07-29 12:48:20 -0700478 return library.objFiles
479}
480
Colin Crossb916a382016-07-29 17:28:03 -0700481func (library *libraryDecorator) reuseObjs() android.Paths {
482 return library.reuseObjFiles
Colin Cross4d9c2d12016-07-29 12:48:20 -0700483}
484
Colin Crossb916a382016-07-29 17:28:03 -0700485func (library *libraryDecorator) install(ctx ModuleContext, file android.Path) {
486 if !ctx.static() {
Colin Cross4d9c2d12016-07-29 12:48:20 -0700487 library.baseInstaller.install(ctx, file)
488 }
489}
490
Colin Crossb916a382016-07-29 17:28:03 -0700491func (library *libraryDecorator) static() bool {
492 return library.Properties.VariantIsStatic
Colin Cross4d9c2d12016-07-29 12:48:20 -0700493}
494
Colin Crossb916a382016-07-29 17:28:03 -0700495func (library *libraryDecorator) setStatic(static bool) {
496 library.Properties.VariantIsStatic = static
497}
498
499func NewLibrary(hod android.HostOrDeviceSupported, shared, static bool) (*Module, *libraryDecorator) {
Colin Cross4d9c2d12016-07-29 12:48:20 -0700500 module := newModule(hod, android.MultilibBoth)
501
Colin Crossb916a382016-07-29 17:28:03 -0700502 library := &libraryDecorator{
503 Properties: LibraryProperties{
504 BuildShared: shared,
505 BuildStatic: static,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700506 },
Colin Crossb916a382016-07-29 17:28:03 -0700507 baseCompiler: NewBaseCompiler(),
508 baseLinker: NewBaseLinker(),
509 baseInstaller: NewBaseInstaller("lib", "lib64", InstallInSystem),
510 sanitize: module.sanitize,
Colin Cross4d9c2d12016-07-29 12:48:20 -0700511 }
512
Colin Crossb916a382016-07-29 17:28:03 -0700513 module.compiler = library
514 module.linker = library
515 module.installer = library
516
517 return module, library
518}
519
520func linkageMutator(mctx android.BottomUpMutatorContext) {
521 if m, ok := mctx.Module().(*Module); ok && m.linker != nil {
522 if library, ok := m.linker.(libraryInterface); ok {
523 var modules []blueprint.Module
524 if library.buildStatic() && library.buildShared() {
525 modules = mctx.CreateLocalVariations("static", "shared")
526 static := modules[0].(*Module)
527 shared := modules[1].(*Module)
528
529 static.linker.(libraryInterface).setStatic(true)
530 shared.linker.(libraryInterface).setStatic(false)
531
532 if staticCompiler, ok := static.compiler.(*libraryDecorator); ok {
533 sharedCompiler := shared.compiler.(*libraryDecorator)
534 if len(staticCompiler.Properties.Static.Cflags) == 0 &&
535 len(sharedCompiler.Properties.Shared.Cflags) == 0 {
536 // Optimize out compiling common .o files twice for static+shared libraries
537 mctx.AddInterVariantDependency(reuseObjTag, shared, static)
538 sharedCompiler.baseCompiler.Properties.Srcs = nil
539 sharedCompiler.baseCompiler.Properties.Generated_sources = nil
540 }
541 }
542 } else if library.buildStatic() {
543 modules = mctx.CreateLocalVariations("static")
544 modules[0].(*Module).linker.(libraryInterface).setStatic(true)
545 } else if library.buildShared() {
546 modules = mctx.CreateLocalVariations("shared")
547 modules[0].(*Module).linker.(libraryInterface).setStatic(false)
548 }
549 }
550 }
Colin Cross4d9c2d12016-07-29 12:48:20 -0700551}