blob: 5b65c0ca06de9a323384758cfd20726ed843c899 [file] [log] [blame]
Jiyong Parkc678ad32018-04-10 13:07:10 +09001// Copyright 2018 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 java
16
17import (
18 "android/soong/android"
19 "android/soong/genrule"
20 "fmt"
Jiyong Park82484c02018-04-23 21:41:26 +090021 "io"
Jiyong Parkc678ad32018-04-10 13:07:10 +090022 "path"
Sundong Ahn054b19a2018-10-19 13:46:09 +090023 "path/filepath"
Jiyong Park82484c02018-04-23 21:41:26 +090024 "sort"
Jiyong Parkc678ad32018-04-10 13:07:10 +090025 "strings"
Jiyong Park82484c02018-04-23 21:41:26 +090026 "sync"
Jiyong Parkc678ad32018-04-10 13:07:10 +090027
28 "github.com/google/blueprint"
29 "github.com/google/blueprint/proptools"
30)
31
32var (
33 sdkStubsLibrarySuffix = ".stubs"
34 sdkSystemApiSuffix = ".system"
Jiyong Parkdf130542018-04-27 16:29:21 +090035 sdkTestApiSuffix = ".test"
Jiyong Parkc678ad32018-04-10 13:07:10 +090036 sdkDocsSuffix = ".docs"
Jiyong Parkc678ad32018-04-10 13:07:10 +090037 sdkXmlFileSuffix = ".xml"
38)
39
40type stubsLibraryDependencyTag struct {
41 blueprint.BaseDependencyTag
42 name string
43}
44
45var (
46 publicApiStubsTag = dependencyTag{name: "public"}
47 systemApiStubsTag = dependencyTag{name: "system"}
Jiyong Parkdf130542018-04-27 16:29:21 +090048 testApiStubsTag = dependencyTag{name: "test"}
Sundong Ahn20e998b2018-07-24 11:19:26 +090049 publicApiFileTag = dependencyTag{name: "publicApi"}
50 systemApiFileTag = dependencyTag{name: "systemApi"}
51 testApiFileTag = dependencyTag{name: "testApi"}
Jiyong Parkdf130542018-04-27 16:29:21 +090052)
53
54type apiScope int
55
56const (
57 apiScopePublic apiScope = iota
58 apiScopeSystem
59 apiScopeTest
Jiyong Parkc678ad32018-04-10 13:07:10 +090060)
61
Jiyong Park82484c02018-04-23 21:41:26 +090062var (
63 javaSdkLibrariesLock sync.Mutex
64)
65
Jiyong Parkc678ad32018-04-10 13:07:10 +090066// java_sdk_library is to make a Java library that implements optional platform APIs to apps.
67// It is actually a wrapper of several modules: 1) stubs library that clients are linked against
68// to, 2) droiddoc module that internally generates API stubs source files, 3) the real runtime
69// shared library that implements the APIs, and 4) XML file for adding the runtime lib to the
70// classpath at runtime if requested via <uses-library>.
71//
72// TODO: these are big features that are currently missing
Jiyong Park1be96912018-05-28 18:02:19 +090073// 1) disallowing linking to the runtime shared lib
74// 2) HTML generation
Jiyong Parkc678ad32018-04-10 13:07:10 +090075
76func init() {
Inseob Kimc0907f12019-02-08 21:00:45 +090077 android.RegisterModuleType("java_sdk_library", SdkLibraryFactory)
Colin Cross79c7c262019-04-17 11:11:46 -070078 android.RegisterModuleType("java_sdk_library_import", sdkLibraryImportFactory)
Jiyong Parkc678ad32018-04-10 13:07:10 +090079
Jiyong Park82484c02018-04-23 21:41:26 +090080 android.RegisterMakeVarsProvider(pctx, func(ctx android.MakeVarsContext) {
81 javaSdkLibraries := javaSdkLibraries(ctx.Config())
82 sort.Strings(*javaSdkLibraries)
83 ctx.Strict("JAVA_SDK_LIBRARIES", strings.Join(*javaSdkLibraries, " "))
84 })
Jiyong Parkc678ad32018-04-10 13:07:10 +090085}
86
87type sdkLibraryProperties struct {
Jiyong Parkbaaf9dd2018-05-02 01:35:27 +090088 // list of optional source files that are part of API but not part of runtime library.
89 Api_srcs []string `android:"arch_variant"`
90
Sundong Ahnf043cf62018-06-25 16:04:37 +090091 // List of Java libraries that will be in the classpath when building stubs
92 Stub_only_libs []string `android:"arch_variant"`
93
Jiyong Parkc678ad32018-04-10 13:07:10 +090094 // list of package names that will be documented and publicized as API
95 Api_packages []string
96
Jiyong Park5a2c9d72018-05-01 22:25:41 +090097 // list of package names that must be hidden from the API
98 Hidden_api_packages []string
99
Paul Duffin11512472019-02-11 15:55:17 +0000100 // local files that are used within user customized droiddoc options.
101 Droiddoc_option_files []string
102
103 // additional droiddoc options
104 // Available variables for substitution:
105 //
106 // $(location <label>): the path to the droiddoc_option_files with name <label>
Sundong Ahndd567f92018-07-31 17:19:11 +0900107 Droiddoc_options []string
108
Sundong Ahnb952ba02019-01-08 16:32:12 +0900109 // the java library (in classpath) for documentation that provides java srcs and srcjars.
110 Srcs_lib *string
111
112 // the base dirs under srcs_lib will be scanned for java srcs.
113 Srcs_lib_whitelist_dirs []string
114
Sundong Ahndd567f92018-07-31 17:19:11 +0900115 // the sub dirs under srcs_lib_whitelist_dirs will be scanned for java srcs.
116 // Defaults to "android.annotation".
117 Srcs_lib_whitelist_pkgs []string
118
Sundong Ahn054b19a2018-10-19 13:46:09 +0900119 // a list of top-level directories containing files to merge qualifier annotations
120 // (i.e. those intended to be included in the stubs written) from.
121 Merge_annotations_dirs []string
122
123 // a list of top-level directories containing Java stub files to merge show/hide annotations from.
124 Merge_inclusion_annotations_dirs []string
125
126 // If set to true, the path of dist files is apistubs/core. Defaults to false.
127 Core_lib *bool
128
Sundong Ahn80a87b32019-05-13 15:02:50 +0900129 // don't create dist rules.
130 No_dist *bool `blueprint:"mutated"`
131
Jiyong Parkc678ad32018-04-10 13:07:10 +0900132 // TODO: determines whether to create HTML doc or not
133 //Html_doc *bool
134}
135
Inseob Kimc0907f12019-02-08 21:00:45 +0900136type SdkLibrary struct {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900137 Library
Jiyong Parkc678ad32018-04-10 13:07:10 +0900138
Sundong Ahn054b19a2018-10-19 13:46:09 +0900139 sdkLibraryProperties sdkLibraryProperties
Jiyong Parkc678ad32018-04-10 13:07:10 +0900140
141 publicApiStubsPath android.Paths
142 systemApiStubsPath android.Paths
Jiyong Parkdf130542018-04-27 16:29:21 +0900143 testApiStubsPath android.Paths
Sundong Ahn241cd372018-07-13 16:16:44 +0900144
145 publicApiStubsImplPath android.Paths
146 systemApiStubsImplPath android.Paths
147 testApiStubsImplPath android.Paths
Sundong Ahn20e998b2018-07-24 11:19:26 +0900148
149 publicApiFilePath android.Path
150 systemApiFilePath android.Path
151 testApiFilePath android.Path
Jiyong Parkc678ad32018-04-10 13:07:10 +0900152}
153
Inseob Kimc0907f12019-02-08 21:00:45 +0900154var _ Dependency = (*SdkLibrary)(nil)
155var _ SdkLibraryDependency = (*SdkLibrary)(nil)
Colin Cross897d2ed2019-02-11 14:03:51 -0800156
Inseob Kimc0907f12019-02-08 21:00:45 +0900157func (module *SdkLibrary) DepsMutator(ctx android.BottomUpMutatorContext) {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900158 // Add dependencies to the stubs library
Colin Cross42d48b72018-08-29 14:10:52 -0700159 ctx.AddVariationDependencies(nil, publicApiStubsTag, module.stubsName(apiScopePublic))
Colin Cross42d48b72018-08-29 14:10:52 -0700160 ctx.AddVariationDependencies(nil, publicApiFileTag, module.docsName(apiScopePublic))
Sundong Ahn054b19a2018-10-19 13:46:09 +0900161
162 if !Bool(module.properties.No_standard_libs) {
163 ctx.AddVariationDependencies(nil, systemApiStubsTag, module.stubsName(apiScopeSystem))
164 ctx.AddVariationDependencies(nil, systemApiFileTag, module.docsName(apiScopeSystem))
165 ctx.AddVariationDependencies(nil, testApiFileTag, module.docsName(apiScopeTest))
166 ctx.AddVariationDependencies(nil, testApiStubsTag, module.stubsName(apiScopeTest))
167 }
168
169 module.Library.deps(ctx)
Jiyong Parkc678ad32018-04-10 13:07:10 +0900170}
171
Inseob Kimc0907f12019-02-08 21:00:45 +0900172func (module *SdkLibrary) GenerateAndroidBuildActions(ctx android.ModuleContext) {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900173 module.Library.GenerateAndroidBuildActions(ctx)
174
Sundong Ahn57368eb2018-07-06 11:20:23 +0900175 // Record the paths to the header jars of the library (stubs and impl).
Jiyong Parkc678ad32018-04-10 13:07:10 +0900176 // When this java_sdk_library is dependened from others via "libs" property,
177 // the recorded paths will be returned depending on the link type of the caller.
178 ctx.VisitDirectDeps(func(to android.Module) {
179 otherName := ctx.OtherModuleName(to)
180 tag := ctx.OtherModuleDependencyTag(to)
181
Sundong Ahn57368eb2018-07-06 11:20:23 +0900182 if lib, ok := to.(Dependency); ok {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900183 switch tag {
184 case publicApiStubsTag:
Sundong Ahn57368eb2018-07-06 11:20:23 +0900185 module.publicApiStubsPath = lib.HeaderJars()
Sundong Ahn241cd372018-07-13 16:16:44 +0900186 module.publicApiStubsImplPath = lib.ImplementationJars()
Jiyong Parkc678ad32018-04-10 13:07:10 +0900187 case systemApiStubsTag:
Sundong Ahn57368eb2018-07-06 11:20:23 +0900188 module.systemApiStubsPath = lib.HeaderJars()
Sundong Ahn241cd372018-07-13 16:16:44 +0900189 module.systemApiStubsImplPath = lib.ImplementationJars()
Jiyong Parkdf130542018-04-27 16:29:21 +0900190 case testApiStubsTag:
Sundong Ahn57368eb2018-07-06 11:20:23 +0900191 module.testApiStubsPath = lib.HeaderJars()
Sundong Ahn241cd372018-07-13 16:16:44 +0900192 module.testApiStubsImplPath = lib.ImplementationJars()
Jiyong Parkc678ad32018-04-10 13:07:10 +0900193 }
194 }
Sundong Ahn20e998b2018-07-24 11:19:26 +0900195 if doc, ok := to.(ApiFilePath); ok {
196 switch tag {
197 case publicApiFileTag:
198 module.publicApiFilePath = doc.ApiFilePath()
199 case systemApiFileTag:
200 module.systemApiFilePath = doc.ApiFilePath()
201 case testApiFileTag:
202 module.testApiFilePath = doc.ApiFilePath()
203 default:
204 ctx.ModuleErrorf("depends on module %q of unknown tag %q", otherName, tag)
205 }
206 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900207 })
208}
209
Inseob Kimc0907f12019-02-08 21:00:45 +0900210func (module *SdkLibrary) AndroidMk() android.AndroidMkData {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900211 data := module.Library.AndroidMk()
212 data.Required = append(data.Required, module.xmlFileName())
213
214 data.Custom = func(w io.Writer, name, prefix, moduleDir string, data android.AndroidMkData) {
215 android.WriteAndroidMkData(w, data)
216
217 module.Library.AndroidMkHostDex(w, name, data)
Sundong Ahn80a87b32019-05-13 15:02:50 +0900218 if !Bool(module.sdkLibraryProperties.No_dist) {
219 // Create a phony module that installs the impl library, for the case when this lib is
220 // in PRODUCT_PACKAGES.
221 owner := module.ModuleBase.Owner()
222 if owner == "" {
223 if Bool(module.sdkLibraryProperties.Core_lib) {
224 owner = "core"
225 } else {
226 owner = "android"
227 }
Sundong Ahn4fd04bb2018-08-31 18:01:37 +0900228 }
Sundong Ahn80a87b32019-05-13 15:02:50 +0900229 // Create dist rules to install the stubs libs to the dist dir
230 if len(module.publicApiStubsPath) == 1 {
231 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
232 module.publicApiStubsImplPath.Strings()[0]+
233 ":"+path.Join("apistubs", owner, "public",
234 module.BaseModuleName()+".jar")+")")
235 }
236 if len(module.systemApiStubsPath) == 1 {
237 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
238 module.systemApiStubsImplPath.Strings()[0]+
239 ":"+path.Join("apistubs", owner, "system",
240 module.BaseModuleName()+".jar")+")")
241 }
242 if len(module.testApiStubsPath) == 1 {
243 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
244 module.testApiStubsImplPath.Strings()[0]+
245 ":"+path.Join("apistubs", owner, "test",
246 module.BaseModuleName()+".jar")+")")
247 }
248 if module.publicApiFilePath != nil {
249 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
250 module.publicApiFilePath.String()+
251 ":"+path.Join("apistubs", owner, "public", "api",
252 module.BaseModuleName()+".txt")+")")
253 }
254 if module.systemApiFilePath != nil {
255 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
256 module.systemApiFilePath.String()+
257 ":"+path.Join("apistubs", owner, "system", "api",
258 module.BaseModuleName()+".txt")+")")
259 }
260 if module.testApiFilePath != nil {
261 fmt.Fprintln(w, "$(call dist-for-goals,sdk win_sdk,"+
262 module.testApiFilePath.String()+
263 ":"+path.Join("apistubs", owner, "test", "api",
264 module.BaseModuleName()+".txt")+")")
265 }
Sundong Ahn054b19a2018-10-19 13:46:09 +0900266 }
Jiyong Park82484c02018-04-23 21:41:26 +0900267 }
Sundong Ahn054b19a2018-10-19 13:46:09 +0900268 return data
Jiyong Park82484c02018-04-23 21:41:26 +0900269}
270
Jiyong Parkc678ad32018-04-10 13:07:10 +0900271// Module name of the stubs library
Inseob Kimc0907f12019-02-08 21:00:45 +0900272func (module *SdkLibrary) stubsName(apiScope apiScope) string {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900273 stubsName := module.BaseModuleName() + sdkStubsLibrarySuffix
Jiyong Parkdf130542018-04-27 16:29:21 +0900274 switch apiScope {
275 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900276 stubsName = stubsName + sdkSystemApiSuffix
Jiyong Parkdf130542018-04-27 16:29:21 +0900277 case apiScopeTest:
278 stubsName = stubsName + sdkTestApiSuffix
Jiyong Parkc678ad32018-04-10 13:07:10 +0900279 }
280 return stubsName
281}
282
283// Module name of the docs
Inseob Kimc0907f12019-02-08 21:00:45 +0900284func (module *SdkLibrary) docsName(apiScope apiScope) string {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900285 docsName := module.BaseModuleName() + sdkDocsSuffix
Jiyong Parkdf130542018-04-27 16:29:21 +0900286 switch apiScope {
287 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900288 docsName = docsName + sdkSystemApiSuffix
Jiyong Parkdf130542018-04-27 16:29:21 +0900289 case apiScopeTest:
290 docsName = docsName + sdkTestApiSuffix
Jiyong Parkc678ad32018-04-10 13:07:10 +0900291 }
292 return docsName
293}
294
295// Module name of the runtime implementation library
Inseob Kimc0907f12019-02-08 21:00:45 +0900296func (module *SdkLibrary) implName() string {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900297 return module.BaseModuleName()
Jiyong Parkc678ad32018-04-10 13:07:10 +0900298}
299
300// File path to the runtime implementation library
Inseob Kimc0907f12019-02-08 21:00:45 +0900301func (module *SdkLibrary) implPath() string {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900302 partition := "system"
303 if module.SocSpecific() {
304 partition = "vendor"
305 } else if module.DeviceSpecific() {
306 partition = "odm"
307 } else if module.ProductSpecific() {
308 partition = "product"
309 }
310 return "/" + partition + "/framework/" + module.implName() + ".jar"
311}
312
313// Module name of the XML file for the lib
Inseob Kimc0907f12019-02-08 21:00:45 +0900314func (module *SdkLibrary) xmlFileName() string {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900315 return module.BaseModuleName() + sdkXmlFileSuffix
316}
317
318// SDK version that the stubs library is built against. Note that this is always
319// *current. Older stubs library built with a numberd SDK version is created from
320// the prebuilt jar.
Inseob Kimc0907f12019-02-08 21:00:45 +0900321func (module *SdkLibrary) sdkVersion(apiScope apiScope) string {
Jiyong Parkdf130542018-04-27 16:29:21 +0900322 switch apiScope {
323 case apiScopePublic:
324 return "current"
325 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900326 return "system_current"
Jiyong Parkdf130542018-04-27 16:29:21 +0900327 case apiScopeTest:
328 return "test_current"
329 default:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900330 return "current"
331 }
332}
333
334// $(INTERNAL_PLATFORM_<apiTagName>_API_FILE) points to the generated
335// api file for the current source
336// TODO: remove this when apicheck is done in soong
Inseob Kimc0907f12019-02-08 21:00:45 +0900337func (module *SdkLibrary) apiTagName(apiScope apiScope) string {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900338 apiTagName := strings.Replace(strings.ToUpper(module.BaseModuleName()), ".", "_", -1)
Jiyong Parkdf130542018-04-27 16:29:21 +0900339 switch apiScope {
340 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900341 apiTagName = apiTagName + "_SYSTEM"
Jiyong Parkdf130542018-04-27 16:29:21 +0900342 case apiScopeTest:
343 apiTagName = apiTagName + "_TEST"
Jiyong Parkc678ad32018-04-10 13:07:10 +0900344 }
345 return apiTagName
346}
347
Inseob Kimc0907f12019-02-08 21:00:45 +0900348func (module *SdkLibrary) latestApiFilegroupName(apiScope apiScope) string {
Jiyong Park58c518b2018-05-12 22:29:12 +0900349 name := ":" + module.BaseModuleName() + ".api."
Jiyong Parkdf130542018-04-27 16:29:21 +0900350 switch apiScope {
Jiyong Park58c518b2018-05-12 22:29:12 +0900351 case apiScopePublic:
352 name = name + "public"
Jiyong Parkdf130542018-04-27 16:29:21 +0900353 case apiScopeSystem:
Jiyong Park58c518b2018-05-12 22:29:12 +0900354 name = name + "system"
Jiyong Parkdf130542018-04-27 16:29:21 +0900355 case apiScopeTest:
Jiyong Park58c518b2018-05-12 22:29:12 +0900356 name = name + "test"
Jiyong Parkc678ad32018-04-10 13:07:10 +0900357 }
Jiyong Park58c518b2018-05-12 22:29:12 +0900358 name = name + ".latest"
359 return name
360}
Jiyong Parkc678ad32018-04-10 13:07:10 +0900361
Inseob Kimc0907f12019-02-08 21:00:45 +0900362func (module *SdkLibrary) latestRemovedApiFilegroupName(apiScope apiScope) string {
Jiyong Park58c518b2018-05-12 22:29:12 +0900363 name := ":" + module.BaseModuleName() + "-removed.api."
364 switch apiScope {
365 case apiScopePublic:
366 name = name + "public"
367 case apiScopeSystem:
368 name = name + "system"
369 case apiScopeTest:
370 name = name + "test"
371 }
372 name = name + ".latest"
373 return name
Jiyong Parkc678ad32018-04-10 13:07:10 +0900374}
375
376// Creates a static java library that has API stubs
Colin Crossf8b860a2019-04-16 14:43:28 -0700377func (module *SdkLibrary) createStubsLibrary(mctx android.LoadHookContext, apiScope apiScope) {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900378 props := struct {
379 Name *string
380 Srcs []string
381 Sdk_version *string
Sundong Ahnf043cf62018-06-25 16:04:37 +0900382 Libs []string
Jiyong Parkc678ad32018-04-10 13:07:10 +0900383 Soc_specific *bool
384 Device_specific *bool
385 Product_specific *bool
Sundong Ahndd567f92018-07-31 17:19:11 +0900386 Compile_dex *bool
Sundong Ahn054b19a2018-10-19 13:46:09 +0900387 No_standard_libs *bool
388 System_modules *string
389 Java_version *string
Jiyong Parkc678ad32018-04-10 13:07:10 +0900390 Product_variables struct {
391 Unbundled_build struct {
392 Enabled *bool
393 }
Jiyong Park82484c02018-04-23 21:41:26 +0900394 Pdk struct {
395 Enabled *bool
396 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900397 }
Sundong Ahn054b19a2018-10-19 13:46:09 +0900398 Openjdk9 struct {
399 Srcs []string
400 Javacflags []string
401 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900402 }{}
403
Jiyong Parkdf130542018-04-27 16:29:21 +0900404 props.Name = proptools.StringPtr(module.stubsName(apiScope))
Jiyong Parkc678ad32018-04-10 13:07:10 +0900405 // sources are generated from the droiddoc
Jiyong Parkdf130542018-04-27 16:29:21 +0900406 props.Srcs = []string{":" + module.docsName(apiScope)}
407 props.Sdk_version = proptools.StringPtr(module.sdkVersion(apiScope))
Sundong Ahn054b19a2018-10-19 13:46:09 +0900408 props.Libs = module.sdkLibraryProperties.Stub_only_libs
Jiyong Parkc678ad32018-04-10 13:07:10 +0900409 // Unbundled apps will use the prebult one from /prebuilts/sdk
Colin Cross10932872019-04-18 14:27:12 -0700410 if mctx.Config().UnbundledBuildUsePrebuiltSdks() {
Colin Cross2c77ceb2019-01-21 11:56:21 -0800411 props.Product_variables.Unbundled_build.Enabled = proptools.BoolPtr(false)
412 }
Jiyong Park82484c02018-04-23 21:41:26 +0900413 props.Product_variables.Pdk.Enabled = proptools.BoolPtr(false)
Sundong Ahn054b19a2018-10-19 13:46:09 +0900414 props.No_standard_libs = module.Library.Module.properties.No_standard_libs
415 props.System_modules = module.Library.Module.deviceProperties.System_modules
416 props.Openjdk9.Srcs = module.Library.Module.properties.Openjdk9.Srcs
417 props.Openjdk9.Javacflags = module.Library.Module.properties.Openjdk9.Javacflags
418 props.Java_version = module.Library.Module.properties.Java_version
419 if module.Library.Module.deviceProperties.Compile_dex != nil {
420 props.Compile_dex = module.Library.Module.deviceProperties.Compile_dex
Sundong Ahndd567f92018-07-31 17:19:11 +0900421 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900422
423 if module.SocSpecific() {
424 props.Soc_specific = proptools.BoolPtr(true)
425 } else if module.DeviceSpecific() {
426 props.Device_specific = proptools.BoolPtr(true)
427 } else if module.ProductSpecific() {
428 props.Product_specific = proptools.BoolPtr(true)
429 }
430
Colin Cross9ae1b922018-06-26 17:59:05 -0700431 mctx.CreateModule(android.ModuleFactoryAdaptor(LibraryFactory), &props)
Jiyong Parkc678ad32018-04-10 13:07:10 +0900432}
433
434// Creates a droiddoc module that creates stubs source files from the given full source
435// files
Colin Crossf8b860a2019-04-16 14:43:28 -0700436func (module *SdkLibrary) createDocs(mctx android.LoadHookContext, apiScope apiScope) {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900437 props := struct {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900438 Name *string
439 Srcs []string
440 Installable *bool
441 Srcs_lib *string
442 Srcs_lib_whitelist_dirs []string
443 Srcs_lib_whitelist_pkgs []string
444 Libs []string
Paul Duffin11512472019-02-11 15:55:17 +0000445 Arg_files []string
Sundong Ahn054b19a2018-10-19 13:46:09 +0900446 Args *string
447 Api_tag_name *string
448 Api_filename *string
449 Removed_api_filename *string
450 No_standard_libs *bool
451 Java_version *string
452 Merge_annotations_dirs []string
453 Merge_inclusion_annotations_dirs []string
454 Check_api struct {
Inseob Kim38449af2019-02-28 14:24:05 +0900455 Current ApiToCheck
456 Last_released ApiToCheck
457 Ignore_missing_latest_api *bool
Jiyong Park58c518b2018-05-12 22:29:12 +0900458 }
Sundong Ahn1b92c822018-05-29 11:35:17 +0900459 Aidl struct {
460 Include_dirs []string
461 Local_include_dirs []string
462 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900463 }{}
464
Jiyong Parkdf130542018-04-27 16:29:21 +0900465 props.Name = proptools.StringPtr(module.docsName(apiScope))
Sundong Ahn054b19a2018-10-19 13:46:09 +0900466 props.Srcs = append(props.Srcs, module.Library.Module.properties.Srcs...)
467 props.Srcs = append(props.Srcs, module.sdkLibraryProperties.Api_srcs...)
Jiyong Parkc678ad32018-04-10 13:07:10 +0900468 props.Installable = proptools.BoolPtr(false)
Sundong Ahne6f0b052018-06-05 16:46:14 +0900469 // A droiddoc module has only one Libs property and doesn't distinguish between
470 // shared libs and static libs. So we need to add both of these libs to Libs property.
Sundong Ahn054b19a2018-10-19 13:46:09 +0900471 props.Libs = module.Library.Module.properties.Libs
472 props.Libs = append(props.Libs, module.Library.Module.properties.Static_libs...)
473 props.Aidl.Include_dirs = module.Library.Module.deviceProperties.Aidl.Include_dirs
474 props.Aidl.Local_include_dirs = module.Library.Module.deviceProperties.Aidl.Local_include_dirs
475 props.No_standard_libs = module.Library.Module.properties.No_standard_libs
476 props.Java_version = module.Library.Module.properties.Java_version
Jiyong Parkc678ad32018-04-10 13:07:10 +0900477
Sundong Ahn054b19a2018-10-19 13:46:09 +0900478 props.Merge_annotations_dirs = module.sdkLibraryProperties.Merge_annotations_dirs
479 props.Merge_inclusion_annotations_dirs = module.sdkLibraryProperties.Merge_inclusion_annotations_dirs
480
481 droiddocArgs := " --stub-packages " + strings.Join(module.sdkLibraryProperties.Api_packages, ":") +
482 " " + android.JoinWithPrefix(module.sdkLibraryProperties.Hidden_api_packages, " --hide-package ") +
483 " " + android.JoinWithPrefix(module.sdkLibraryProperties.Droiddoc_options, " ") +
Sundong Ahn04ef8a32019-01-14 11:36:50 +0900484 " --hide MissingPermission --hide BroadcastBehavior " +
485 "--hide HiddenSuperclass --hide DeprecationMismatch --hide UnavailableSymbol " +
486 "--hide SdkConstant --hide HiddenTypeParameter --hide Todo --hide Typo"
Sundong Ahnfb2721f2018-09-17 13:23:09 +0900487
Jiyong Parkdf130542018-04-27 16:29:21 +0900488 switch apiScope {
489 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900490 droiddocArgs = droiddocArgs + " -showAnnotation android.annotation.SystemApi"
Jiyong Parkdf130542018-04-27 16:29:21 +0900491 case apiScopeTest:
492 droiddocArgs = droiddocArgs + " -showAnnotation android.annotation.TestApi"
Jiyong Parkc678ad32018-04-10 13:07:10 +0900493 }
Paul Duffin11512472019-02-11 15:55:17 +0000494 props.Arg_files = module.sdkLibraryProperties.Droiddoc_option_files
Jiyong Parkc678ad32018-04-10 13:07:10 +0900495 props.Args = proptools.StringPtr(droiddocArgs)
496
497 // List of APIs identified from the provided source files are created. They are later
498 // compared against to the not-yet-released (a.k.a current) list of APIs and to the
499 // last-released (a.k.a numbered) list of API.
Jiyong Parkc678ad32018-04-10 13:07:10 +0900500 currentApiFileName := "current.txt"
501 removedApiFileName := "removed.txt"
Jiyong Parkdf130542018-04-27 16:29:21 +0900502 switch apiScope {
503 case apiScopeSystem:
Jiyong Parkc678ad32018-04-10 13:07:10 +0900504 currentApiFileName = "system-" + currentApiFileName
505 removedApiFileName = "system-" + removedApiFileName
Jiyong Parkdf130542018-04-27 16:29:21 +0900506 case apiScopeTest:
507 currentApiFileName = "test-" + currentApiFileName
508 removedApiFileName = "test-" + removedApiFileName
Jiyong Parkc678ad32018-04-10 13:07:10 +0900509 }
510 currentApiFileName = path.Join("api", currentApiFileName)
511 removedApiFileName = path.Join("api", removedApiFileName)
Jiyong Park58c518b2018-05-12 22:29:12 +0900512 // TODO(jiyong): remove these three props
Jiyong Parkdf130542018-04-27 16:29:21 +0900513 props.Api_tag_name = proptools.StringPtr(module.apiTagName(apiScope))
Jiyong Parkc678ad32018-04-10 13:07:10 +0900514 props.Api_filename = proptools.StringPtr(currentApiFileName)
515 props.Removed_api_filename = proptools.StringPtr(removedApiFileName)
516
Jiyong Park58c518b2018-05-12 22:29:12 +0900517 // check against the not-yet-release API
518 props.Check_api.Current.Api_file = proptools.StringPtr(currentApiFileName)
519 props.Check_api.Current.Removed_api_file = proptools.StringPtr(removedApiFileName)
Jiyong Park58c518b2018-05-12 22:29:12 +0900520
521 // check against the latest released API
522 props.Check_api.Last_released.Api_file = proptools.StringPtr(
523 module.latestApiFilegroupName(apiScope))
524 props.Check_api.Last_released.Removed_api_file = proptools.StringPtr(
525 module.latestRemovedApiFilegroupName(apiScope))
Inseob Kim38449af2019-02-28 14:24:05 +0900526 props.Check_api.Ignore_missing_latest_api = proptools.BoolPtr(true)
Sundong Ahn054b19a2018-10-19 13:46:09 +0900527 props.Srcs_lib = module.sdkLibraryProperties.Srcs_lib
528 props.Srcs_lib_whitelist_dirs = module.sdkLibraryProperties.Srcs_lib_whitelist_dirs
529 props.Srcs_lib_whitelist_pkgs = module.sdkLibraryProperties.Srcs_lib_whitelist_pkgs
Jiyong Park58c518b2018-05-12 22:29:12 +0900530
Sundong Ahn04ef8a32019-01-14 11:36:50 +0900531 mctx.CreateModule(android.ModuleFactoryAdaptor(DroidstubsFactory), &props)
Jiyong Parkc678ad32018-04-10 13:07:10 +0900532}
533
Jiyong Parkc678ad32018-04-10 13:07:10 +0900534// Creates the xml file that publicizes the runtime library
Colin Crossf8b860a2019-04-16 14:43:28 -0700535func (module *SdkLibrary) createXmlFile(mctx android.LoadHookContext) {
Jiyong Parkc678ad32018-04-10 13:07:10 +0900536 template := `
537<?xml version="1.0" encoding="utf-8"?>
538<!-- Copyright (C) 2018 The Android Open Source Project
539
540 Licensed under the Apache License, Version 2.0 (the "License");
541 you may not use this file except in compliance with the License.
542 You may obtain a copy of the License at
543
544 http://www.apache.org/licenses/LICENSE-2.0
545
546 Unless required by applicable law or agreed to in writing, software
547 distributed under the License is distributed on an "AS IS" BASIS,
548 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
549 See the License for the specific language governing permissions and
550 limitations under the License.
551-->
552
553<permissions>
554 <library name="%s" file="%s"/>
555</permissions>
556`
557 // genrule to generate the xml file content from the template above
558 // TODO: preserve newlines in the generate xml file. Newlines are being squashed
559 // in the ninja file. Do we need to have an external tool for this?
560 xmlContent := fmt.Sprintf(template, module.BaseModuleName(), module.implPath())
561 genruleProps := struct {
562 Name *string
563 Cmd *string
564 Out []string
565 }{}
566 genruleProps.Name = proptools.StringPtr(module.xmlFileName() + "-gen")
567 genruleProps.Cmd = proptools.StringPtr("echo '" + xmlContent + "' > $(out)")
568 genruleProps.Out = []string{module.xmlFileName()}
569 mctx.CreateModule(android.ModuleFactoryAdaptor(genrule.GenRuleFactory), &genruleProps)
570
571 // creates a prebuilt_etc module to actually place the xml file under
572 // <partition>/etc/permissions
573 etcProps := struct {
574 Name *string
Jiyong Park5a8d1be2018-04-25 22:57:34 +0900575 Src *string
Jiyong Parkc678ad32018-04-10 13:07:10 +0900576 Sub_dir *string
577 Soc_specific *bool
578 Device_specific *bool
579 Product_specific *bool
580 }{}
581 etcProps.Name = proptools.StringPtr(module.xmlFileName())
Jiyong Park5a8d1be2018-04-25 22:57:34 +0900582 etcProps.Src = proptools.StringPtr(":" + module.xmlFileName() + "-gen")
Jiyong Parkc678ad32018-04-10 13:07:10 +0900583 etcProps.Sub_dir = proptools.StringPtr("permissions")
584 if module.SocSpecific() {
585 etcProps.Soc_specific = proptools.BoolPtr(true)
586 } else if module.DeviceSpecific() {
587 etcProps.Device_specific = proptools.BoolPtr(true)
588 } else if module.ProductSpecific() {
589 etcProps.Product_specific = proptools.BoolPtr(true)
590 }
591 mctx.CreateModule(android.ModuleFactoryAdaptor(android.PrebuiltEtcFactory), &etcProps)
592}
593
Inseob Kimc0907f12019-02-08 21:00:45 +0900594func (module *SdkLibrary) PrebuiltJars(ctx android.BaseContext, sdkVersion string) android.Paths {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900595 var api, v string
596 if sdkVersion == "" {
597 api = "system"
598 v = "current"
599 } else if strings.Contains(sdkVersion, "_") {
600 t := strings.Split(sdkVersion, "_")
601 api = t[0]
602 v = t[1]
Jiyong Parkc678ad32018-04-10 13:07:10 +0900603 } else {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900604 api = "public"
605 v = sdkVersion
606 }
607 dir := filepath.Join("prebuilts", "sdk", v, api)
608 jar := filepath.Join(dir, module.BaseModuleName()+".jar")
609 jarPath := android.ExistentPathForSource(ctx, jar)
Sundong Ahnae418ac2019-02-28 15:01:28 +0900610 if !jarPath.Valid() {
611 ctx.PropertyErrorf("sdk_library", "invalid sdk version %q, %q does not exist", v, jar)
612 return nil
613 }
Sundong Ahn054b19a2018-10-19 13:46:09 +0900614 return android.Paths{jarPath.Path()}
615}
616
617// to satisfy SdkLibraryDependency interface
Inseob Kimc0907f12019-02-08 21:00:45 +0900618func (module *SdkLibrary) SdkHeaderJars(ctx android.BaseContext, sdkVersion string) android.Paths {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900619 // This module is just a wrapper for the stubs.
Colin Cross10932872019-04-18 14:27:12 -0700620 if ctx.Config().UnbundledBuildUsePrebuiltSdks() {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900621 return module.PrebuiltJars(ctx, sdkVersion)
622 } else {
623 if strings.HasPrefix(sdkVersion, "system_") {
624 return module.systemApiStubsPath
625 } else if sdkVersion == "" {
626 return module.Library.HeaderJars()
627 } else {
628 return module.publicApiStubsPath
629 }
Jiyong Parkc678ad32018-04-10 13:07:10 +0900630 }
631}
632
Sundong Ahn241cd372018-07-13 16:16:44 +0900633// to satisfy SdkLibraryDependency interface
Inseob Kimc0907f12019-02-08 21:00:45 +0900634func (module *SdkLibrary) SdkImplementationJars(ctx android.BaseContext, sdkVersion string) android.Paths {
Sundong Ahn241cd372018-07-13 16:16:44 +0900635 // This module is just a wrapper for the stubs.
Colin Cross10932872019-04-18 14:27:12 -0700636 if ctx.Config().UnbundledBuildUsePrebuiltSdks() {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900637 return module.PrebuiltJars(ctx, sdkVersion)
Sundong Ahn241cd372018-07-13 16:16:44 +0900638 } else {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900639 if strings.HasPrefix(sdkVersion, "system_") {
640 return module.systemApiStubsImplPath
641 } else if sdkVersion == "" {
642 return module.Library.ImplementationJars()
643 } else {
644 return module.publicApiStubsImplPath
645 }
Sundong Ahn241cd372018-07-13 16:16:44 +0900646 }
647}
648
Sundong Ahn80a87b32019-05-13 15:02:50 +0900649func (module *SdkLibrary) SetNoDist() {
650 module.sdkLibraryProperties.No_dist = proptools.BoolPtr(true)
651}
652
Colin Cross571cccf2019-02-04 11:22:08 -0800653var javaSdkLibrariesKey = android.NewOnceKey("javaSdkLibraries")
654
Jiyong Park82484c02018-04-23 21:41:26 +0900655func javaSdkLibraries(config android.Config) *[]string {
Colin Cross571cccf2019-02-04 11:22:08 -0800656 return config.Once(javaSdkLibrariesKey, func() interface{} {
Jiyong Park82484c02018-04-23 21:41:26 +0900657 return &[]string{}
658 }).(*[]string)
659}
660
Jiyong Parkc678ad32018-04-10 13:07:10 +0900661// For a java_sdk_library module, create internal modules for stubs, docs,
662// runtime libs and xml file. If requested, the stubs and docs are created twice
663// once for public API level and once for system API level
Colin Crossf8b860a2019-04-16 14:43:28 -0700664func (module *SdkLibrary) CreateInternalModules(mctx android.LoadHookContext) {
Inseob Kim6e93ac92019-03-21 17:43:49 +0900665 if len(module.Library.Module.properties.Srcs) == 0 {
Inseob Kimc0907f12019-02-08 21:00:45 +0900666 mctx.PropertyErrorf("srcs", "java_sdk_library must specify srcs")
667 }
668
Inseob Kim6e93ac92019-03-21 17:43:49 +0900669 if len(module.sdkLibraryProperties.Api_packages) == 0 {
Inseob Kimc0907f12019-02-08 21:00:45 +0900670 mctx.PropertyErrorf("api_packages", "java_sdk_library must specify api_packages")
671 }
Inseob Kim8098faa2019-03-18 10:19:51 +0900672
673 missing_current_api := false
674
675 for _, scope := range []string{"", "system-", "test-"} {
676 for _, api := range []string{"current.txt", "removed.txt"} {
677 path := path.Join(mctx.ModuleDir(), "api", scope+api)
678 p := android.ExistentPathForSource(mctx, path)
679 if !p.Valid() {
680 mctx.ModuleErrorf("Current api file %#v doesn't exist", path)
681 missing_current_api = true
682 }
683 }
684 }
685
686 if missing_current_api {
687 script := "build/soong/scripts/gen-java-current-api-files.sh"
688 p := android.ExistentPathForSource(mctx, script)
689
690 if !p.Valid() {
691 panic(fmt.Sprintf("script file %s doesn't exist", script))
692 }
693
694 mctx.ModuleErrorf("One or more current api files are missing. "+
695 "You can update them by:\n"+
696 "%s %q && m update-api", script, mctx.ModuleDir())
697 return
698 }
699
Inseob Kimc0907f12019-02-08 21:00:45 +0900700 // for public API stubs
701 module.createStubsLibrary(mctx, apiScopePublic)
702 module.createDocs(mctx, apiScopePublic)
703
704 if !Bool(module.properties.No_standard_libs) {
705 // for system API stubs
706 module.createStubsLibrary(mctx, apiScopeSystem)
707 module.createDocs(mctx, apiScopeSystem)
708
709 // for test API stubs
710 module.createStubsLibrary(mctx, apiScopeTest)
711 module.createDocs(mctx, apiScopeTest)
712
713 // for runtime
714 module.createXmlFile(mctx)
715 }
716
717 // record java_sdk_library modules so that they are exported to make
718 javaSdkLibraries := javaSdkLibraries(mctx.Config())
719 javaSdkLibrariesLock.Lock()
720 defer javaSdkLibrariesLock.Unlock()
721 *javaSdkLibraries = append(*javaSdkLibraries, module.BaseModuleName())
722}
723
724func (module *SdkLibrary) InitSdkLibraryProperties() {
Sundong Ahn054b19a2018-10-19 13:46:09 +0900725 module.AddProperties(
726 &module.sdkLibraryProperties,
727 &module.Library.Module.properties,
728 &module.Library.Module.dexpreoptProperties,
729 &module.Library.Module.deviceProperties,
730 &module.Library.Module.protoProperties,
731 )
732
733 module.Library.Module.properties.Installable = proptools.BoolPtr(true)
734 module.Library.Module.deviceProperties.IsSDKLibrary = true
Inseob Kimc0907f12019-02-08 21:00:45 +0900735}
Sundong Ahn054b19a2018-10-19 13:46:09 +0900736
Inseob Kimc0907f12019-02-08 21:00:45 +0900737func SdkLibraryFactory() android.Module {
738 module := &SdkLibrary{}
739 module.InitSdkLibraryProperties()
Sundong Ahn054b19a2018-10-19 13:46:09 +0900740 InitJavaModule(module, android.HostAndDeviceSupported)
Colin Crossf8b860a2019-04-16 14:43:28 -0700741 android.AddLoadHook(module, func(ctx android.LoadHookContext) { module.CreateInternalModules(ctx) })
Jiyong Parkc678ad32018-04-10 13:07:10 +0900742 return module
743}
Colin Cross79c7c262019-04-17 11:11:46 -0700744
745//
746// SDK library prebuilts
747//
748
749type sdkLibraryImportProperties struct {
750 Jars []string `android:"path"`
751
752 Sdk_version *string
753
754 Installable *bool
755
756 // List of shared java libs that this module has dependencies to
757 Libs []string
758
759 // List of files to remove from the jar file(s)
760 Exclude_files []string
761
762 // List of directories to remove from the jar file(s)
763 Exclude_dirs []string
764}
765
766type sdkLibraryImport struct {
767 android.ModuleBase
768 android.DefaultableModuleBase
769 prebuilt android.Prebuilt
770
771 properties sdkLibraryImportProperties
772
773 stubsPath android.Paths
774}
775
776var _ SdkLibraryDependency = (*sdkLibraryImport)(nil)
777
778func sdkLibraryImportFactory() android.Module {
779 module := &sdkLibraryImport{}
780
781 module.AddProperties(&module.properties)
782
783 android.InitPrebuiltModule(module, &module.properties.Jars)
784 InitJavaModule(module, android.HostAndDeviceSupported)
785
786 android.AddLoadHook(module, func(mctx android.LoadHookContext) { module.createInternalModules(mctx) })
787 return module
788}
789
790func (module *sdkLibraryImport) Prebuilt() *android.Prebuilt {
791 return &module.prebuilt
792}
793
794func (module *sdkLibraryImport) Name() string {
795 return module.prebuilt.Name(module.ModuleBase.Name())
796}
797
798func (module *sdkLibraryImport) createInternalModules(mctx android.LoadHookContext) {
799 // Creates a java import for the jar with ".stubs" suffix
800 props := struct {
801 Name *string
802 Soc_specific *bool
803 Device_specific *bool
804 Product_specific *bool
805 }{}
806
807 props.Name = proptools.StringPtr(module.BaseModuleName() + sdkStubsLibrarySuffix)
808
809 if module.SocSpecific() {
810 props.Soc_specific = proptools.BoolPtr(true)
811 } else if module.DeviceSpecific() {
812 props.Device_specific = proptools.BoolPtr(true)
813 } else if module.ProductSpecific() {
814 props.Product_specific = proptools.BoolPtr(true)
815 }
816
817 mctx.CreateModule(android.ModuleFactoryAdaptor(ImportFactory), &props, &module.properties)
818
819 javaSdkLibraries := javaSdkLibraries(mctx.Config())
820 javaSdkLibrariesLock.Lock()
821 defer javaSdkLibrariesLock.Unlock()
822 *javaSdkLibraries = append(*javaSdkLibraries, module.BaseModuleName())
823}
824
825func (module *sdkLibraryImport) DepsMutator(ctx android.BottomUpMutatorContext) {
826 // Add dependencies to the prebuilt stubs library
827 ctx.AddVariationDependencies(nil, publicApiStubsTag, module.BaseModuleName()+sdkStubsLibrarySuffix)
828}
829
830func (module *sdkLibraryImport) GenerateAndroidBuildActions(ctx android.ModuleContext) {
831 // Record the paths to the prebuilt stubs library.
832 ctx.VisitDirectDeps(func(to android.Module) {
833 tag := ctx.OtherModuleDependencyTag(to)
834
835 switch tag {
836 case publicApiStubsTag:
837 module.stubsPath = to.(Dependency).HeaderJars()
838 }
839 })
840}
841
842// to satisfy SdkLibraryDependency interface
843func (module *sdkLibraryImport) SdkHeaderJars(ctx android.BaseContext, sdkVersion string) android.Paths {
844 // This module is just a wrapper for the prebuilt stubs.
845 return module.stubsPath
846}
847
848// to satisfy SdkLibraryDependency interface
849func (module *sdkLibraryImport) SdkImplementationJars(ctx android.BaseContext, sdkVersion string) android.Paths {
850 // This module is just a wrapper for the stubs.
851 return module.stubsPath
852}