blob: f4da31ed27953eabc89b6d57cdc8ba32df95cf90 [file] [log] [blame]
Paul Duffinb432df92021-03-22 22:09:42 +00001// Copyright (C) 2021 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.
14
15package apex
16
17import (
Paul Duffinffa83752021-06-09 14:32:53 +010018 "fmt"
19 "strings"
Paul Duffinb432df92021-03-22 22:09:42 +000020 "testing"
21
22 "android/soong/android"
Jiakai Zhangb95998b2023-05-11 16:39:27 +010023 "android/soong/dexpreopt"
Paul Duffinb432df92021-03-22 22:09:42 +000024 "android/soong/java"
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +010025
Paul Duffinb432df92021-03-22 22:09:42 +000026 "github.com/google/blueprint"
Paul Duffin7487a7a2021-05-19 09:36:09 +010027 "github.com/google/blueprint/proptools"
Paul Duffinb432df92021-03-22 22:09:42 +000028)
29
30// Contains tests for platform_bootclasspath logic from java/platform_bootclasspath.go that requires
31// apexes.
32
33var prepareForTestWithPlatformBootclasspath = android.GroupFixturePreparers(
Jiakai Zhangb95998b2023-05-11 16:39:27 +010034 java.PrepareForTestWithJavaDefaultModules,
Paul Duffinb432df92021-03-22 22:09:42 +000035 PrepareForTestWithApexBuildComponents,
36)
37
Paul Duffinffa83752021-06-09 14:32:53 +010038func TestPlatformBootclasspath_Fragments(t *testing.T) {
39 result := android.GroupFixturePreparers(
40 prepareForTestWithPlatformBootclasspath,
Paul Duffindc3f9562021-06-09 15:31:05 +010041 prepareForTestWithMyapex,
Paul Duffinffa83752021-06-09 14:32:53 +010042 java.PrepareForTestWithJavaSdkLibraryFiles,
43 java.FixtureWithLastReleaseApis("foo"),
satayevabcd5972021-08-06 17:49:46 +010044 java.FixtureConfigureApexBootJars("myapex:bar"),
Paul Duffinffa83752021-06-09 14:32:53 +010045 android.FixtureWithRootAndroidBp(`
46 platform_bootclasspath {
47 name: "platform-bootclasspath",
48 fragments: [
Paul Duffindc3f9562021-06-09 15:31:05 +010049 {
50 apex: "myapex",
51 module:"bar-fragment",
52 },
Paul Duffinffa83752021-06-09 14:32:53 +010053 ],
54 hidden_api: {
55 unsupported: [
56 "unsupported.txt",
57 ],
58 removed: [
59 "removed.txt",
60 ],
61 max_target_r_low_priority: [
62 "max-target-r-low-priority.txt",
63 ],
64 max_target_q: [
65 "max-target-q.txt",
66 ],
67 max_target_p: [
68 "max-target-p.txt",
69 ],
70 max_target_o_low_priority: [
71 "max-target-o-low-priority.txt",
72 ],
73 blocked: [
74 "blocked.txt",
75 ],
76 unsupported_packages: [
77 "unsupported-packages.txt",
78 ],
79 },
80 }
81
Paul Duffindc3f9562021-06-09 15:31:05 +010082 apex {
83 name: "myapex",
84 key: "myapex.key",
85 bootclasspath_fragments: [
86 "bar-fragment",
87 ],
88 updatable: false,
Spandan Das38c64f62024-02-12 15:00:15 +000089 min_sdk_version: "30", // R
Paul Duffindc3f9562021-06-09 15:31:05 +010090 }
91
92 apex_key {
93 name: "myapex.key",
94 public_key: "testkey.avbpubkey",
95 private_key: "testkey.pem",
96 }
97
Paul Duffinffa83752021-06-09 14:32:53 +010098 bootclasspath_fragment {
99 name: "bar-fragment",
100 contents: ["bar"],
Paul Duffindc3f9562021-06-09 15:31:05 +0100101 apex_available: ["myapex"],
Paul Duffinffa83752021-06-09 14:32:53 +0100102 api: {
103 stub_libs: ["foo"],
104 },
105 hidden_api: {
106 unsupported: [
107 "bar-unsupported.txt",
108 ],
109 removed: [
110 "bar-removed.txt",
111 ],
112 max_target_r_low_priority: [
113 "bar-max-target-r-low-priority.txt",
114 ],
115 max_target_q: [
116 "bar-max-target-q.txt",
117 ],
118 max_target_p: [
119 "bar-max-target-p.txt",
120 ],
121 max_target_o_low_priority: [
122 "bar-max-target-o-low-priority.txt",
123 ],
124 blocked: [
125 "bar-blocked.txt",
126 ],
127 unsupported_packages: [
128 "bar-unsupported-packages.txt",
129 ],
Paul Duffin9fd56472022-03-31 15:42:30 +0100130 split_packages: ["*"],
Paul Duffinffa83752021-06-09 14:32:53 +0100131 },
132 }
133
134 java_library {
135 name: "bar",
Paul Duffindc3f9562021-06-09 15:31:05 +0100136 apex_available: ["myapex"],
Paul Duffinffa83752021-06-09 14:32:53 +0100137 srcs: ["a.java"],
138 system_modules: "none",
139 sdk_version: "none",
140 compile_dex: true,
Paul Duffindc3f9562021-06-09 15:31:05 +0100141 permitted_packages: ["bar"],
Spandan Das38c64f62024-02-12 15:00:15 +0000142 min_sdk_version: "30", // R
Paul Duffinffa83752021-06-09 14:32:53 +0100143 }
144
145 java_sdk_library {
146 name: "foo",
147 srcs: ["a.java"],
148 public: {
149 enabled: true,
150 },
151 compile_dex: true,
152 }
153 `),
154 ).RunTest(t)
155
156 pbcp := result.Module("platform-bootclasspath", "android_common")
Yu Liu663e4502024-08-12 18:23:59 +0000157 info, _ := android.OtherModuleProvider(result, pbcp, java.MonolithicHiddenAPIInfoProvider)
Paul Duffinffa83752021-06-09 14:32:53 +0100158
159 for _, category := range java.HiddenAPIFlagFileCategories {
Cole Faust22e8abc2024-01-23 17:52:13 -0800160 name := category.PropertyName()
Paul Duffinffa83752021-06-09 14:32:53 +0100161 message := fmt.Sprintf("category %s", name)
162 filename := strings.ReplaceAll(name, "_", "-")
163 expected := []string{fmt.Sprintf("%s.txt", filename), fmt.Sprintf("bar-%s.txt", filename)}
164 android.AssertPathsRelativeToTopEquals(t, message, expected, info.FlagsFilesByCategory[category])
165 }
166
Spandan Das38c64f62024-02-12 15:00:15 +0000167 android.AssertPathsRelativeToTopEquals(t, "annotation flags", []string{"out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/annotation-flags.csv"}, info.AnnotationFlagsPaths)
168 android.AssertPathsRelativeToTopEquals(t, "metadata flags", []string{"out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/metadata.csv"}, info.MetadataPaths)
169 android.AssertPathsRelativeToTopEquals(t, "index flags", []string{"out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/index.csv"}, info.IndexPaths)
Paul Duffin67b9d612021-07-21 17:38:47 +0100170
Spandan Das38c64f62024-02-12 15:00:15 +0000171 android.AssertArrayString(t, "stub flags", []string{"out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/filtered-stub-flags.csv:out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/signature-patterns.csv"}, info.StubFlagSubsets.RelativeToTop())
172 android.AssertArrayString(t, "all flags", []string{"out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/filtered-flags.csv:out/soong/.intermediates/bar-fragment/android_common_apex30/modular-hiddenapi/signature-patterns.csv"}, info.FlagSubsets.RelativeToTop())
Paul Duffinffa83752021-06-09 14:32:53 +0100173}
174
Paul Duffin191be3a2021-08-10 16:14:16 +0100175// TestPlatformBootclasspath_LegacyPrebuiltFragment verifies that the
176// prebuilt_bootclasspath_fragment falls back to using the complete stub-flags/all-flags if the
177// filtered files are not provided.
178//
179// TODO: Remove once all prebuilts use the filtered_... properties.
180func TestPlatformBootclasspath_LegacyPrebuiltFragment(t *testing.T) {
181 result := android.GroupFixturePreparers(
182 prepareForTestWithPlatformBootclasspath,
183 java.FixtureConfigureApexBootJars("myapex:foo"),
184 java.PrepareForTestWithJavaSdkLibraryFiles,
185 ).RunTestWithBp(t, `
186 prebuilt_apex {
187 name: "myapex",
188 src: "myapex.apex",
189 exported_bootclasspath_fragments: ["mybootclasspath-fragment"],
190 }
191
192 // A prebuilt java_sdk_library_import that is not preferred by default but will be preferred
193 // because AlwaysUsePrebuiltSdks() is true.
194 java_sdk_library_import {
195 name: "foo",
196 prefer: false,
197 shared_library: false,
198 permitted_packages: ["foo"],
199 public: {
200 jars: ["sdk_library/public/foo-stubs.jar"],
201 stub_srcs: ["sdk_library/public/foo_stub_sources"],
202 current_api: "sdk_library/public/foo.txt",
203 removed_api: "sdk_library/public/foo-removed.txt",
204 sdk_version: "current",
205 },
206 apex_available: ["myapex"],
207 }
208
209 prebuilt_bootclasspath_fragment {
210 name: "mybootclasspath-fragment",
211 apex_available: [
212 "myapex",
213 ],
214 contents: [
215 "foo",
216 ],
217 hidden_api: {
218 stub_flags: "prebuilt-stub-flags.csv",
219 annotation_flags: "prebuilt-annotation-flags.csv",
220 metadata: "prebuilt-metadata.csv",
221 index: "prebuilt-index.csv",
222 all_flags: "prebuilt-all-flags.csv",
223 },
224 }
225
226 platform_bootclasspath {
227 name: "myplatform-bootclasspath",
228 fragments: [
229 {
230 apex: "myapex",
231 module:"mybootclasspath-fragment",
232 },
233 ],
234 }
235`,
236 )
237
238 pbcp := result.Module("myplatform-bootclasspath", "android_common")
Yu Liu663e4502024-08-12 18:23:59 +0000239 info, _ := android.OtherModuleProvider(result, pbcp, java.MonolithicHiddenAPIInfoProvider)
Paul Duffin191be3a2021-08-10 16:14:16 +0100240
241 android.AssertArrayString(t, "stub flags", []string{"prebuilt-stub-flags.csv:out/soong/.intermediates/mybootclasspath-fragment/android_common_myapex/modular-hiddenapi/signature-patterns.csv"}, info.StubFlagSubsets.RelativeToTop())
242 android.AssertArrayString(t, "all flags", []string{"prebuilt-all-flags.csv:out/soong/.intermediates/mybootclasspath-fragment/android_common_myapex/modular-hiddenapi/signature-patterns.csv"}, info.FlagSubsets.RelativeToTop())
243}
244
Paul Duffinb432df92021-03-22 22:09:42 +0000245func TestPlatformBootclasspathDependencies(t *testing.T) {
246 result := android.GroupFixturePreparers(
247 prepareForTestWithPlatformBootclasspath,
248 prepareForTestWithArtApex,
249 prepareForTestWithMyapex,
250 // Configure some libraries in the art and framework boot images.
Paul Duffin60264a02021-04-12 20:02:36 +0100251 java.FixtureConfigureBootJars("com.android.art:baz", "com.android.art:quuz", "platform:foo"),
satayevd604b212021-07-21 14:23:52 +0100252 java.FixtureConfigureApexBootJars("myapex:bar"),
Paul Duffinb432df92021-03-22 22:09:42 +0000253 java.PrepareForTestWithJavaSdkLibraryFiles,
254 java.FixtureWithLastReleaseApis("foo"),
Jiakai Zhangb95998b2023-05-11 16:39:27 +0100255 java.PrepareForTestWithDexpreopt,
256 dexpreopt.FixtureDisableDexpreoptBootImages(false),
Colin Crossa66b4632024-08-08 15:50:47 -0700257 android.PrepareForTestWithBuildFlag("RELEASE_HIDDEN_API_EXPORTABLE_STUBS", "true"),
Paul Duffinb432df92021-03-22 22:09:42 +0000258 ).RunTestWithBp(t, `
259 apex {
260 name: "com.android.art",
261 key: "com.android.art.key",
262 bootclasspath_fragments: [
263 "art-bootclasspath-fragment",
264 ],
265 updatable: false,
266 }
267
268 apex_key {
269 name: "com.android.art.key",
270 public_key: "com.android.art.avbpubkey",
271 private_key: "com.android.art.pem",
272 }
273
274 bootclasspath_fragment {
275 name: "art-bootclasspath-fragment",
satayevabcd5972021-08-06 17:49:46 +0100276 image_name: "art",
Paul Duffinb432df92021-03-22 22:09:42 +0000277 apex_available: [
278 "com.android.art",
279 ],
280 contents: [
281 "baz",
282 "quuz",
283 ],
Paul Duffin9fd56472022-03-31 15:42:30 +0100284 hidden_api: {
285 split_packages: ["*"],
286 },
Paul Duffinb432df92021-03-22 22:09:42 +0000287 }
288
289 java_library {
290 name: "baz",
291 apex_available: [
292 "com.android.art",
293 ],
294 srcs: ["b.java"],
295 installable: true,
Jihoon Kang85bc1932024-07-01 17:04:46 +0000296 sdk_version: "core_current",
Paul Duffinb432df92021-03-22 22:09:42 +0000297 }
298
299 // Add a java_import that is not preferred and so won't have an appropriate apex variant created
300 // for it to make sure that the platform_bootclasspath doesn't try and add a dependency onto it.
301 java_import {
302 name: "baz",
303 apex_available: [
304 "com.android.art",
305 ],
306 jars: ["b.jar"],
307 }
308
309 java_library {
310 name: "quuz",
311 apex_available: [
312 "com.android.art",
313 ],
314 srcs: ["b.java"],
315 installable: true,
316 }
317
318 apex {
319 name: "myapex",
320 key: "myapex.key",
Paul Duffin89f570a2021-06-16 01:42:33 +0100321 bootclasspath_fragments: [
322 "my-bootclasspath-fragment",
Paul Duffinb432df92021-03-22 22:09:42 +0000323 ],
324 updatable: false,
325 }
326
Paul Duffin89f570a2021-06-16 01:42:33 +0100327 bootclasspath_fragment {
328 name: "my-bootclasspath-fragment",
329 contents: ["bar"],
330 apex_available: ["myapex"],
Paul Duffin9fd56472022-03-31 15:42:30 +0100331 hidden_api: {
332 split_packages: ["*"],
333 },
Paul Duffin89f570a2021-06-16 01:42:33 +0100334 }
335
Paul Duffinb432df92021-03-22 22:09:42 +0000336 apex_key {
337 name: "myapex.key",
338 public_key: "testkey.avbpubkey",
339 private_key: "testkey.pem",
340 }
341
342 java_sdk_library {
343 name: "foo",
344 srcs: ["b.java"],
345 }
346
347 java_library {
348 name: "bar",
349 srcs: ["b.java"],
350 installable: true,
351 apex_available: ["myapex"],
352 permitted_packages: ["bar"],
353 }
354
355 platform_bootclasspath {
356 name: "myplatform-bootclasspath",
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100357
358 fragments: [
359 {
360 apex: "com.android.art",
361 module: "art-bootclasspath-fragment",
362 },
Paul Duffin89f570a2021-06-16 01:42:33 +0100363 {
364 apex: "myapex",
365 module: "my-bootclasspath-fragment",
366 },
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100367 ],
Paul Duffinb432df92021-03-22 22:09:42 +0000368 }
369`,
370 )
371
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100372 java.CheckPlatformBootclasspathModules(t, result, "myplatform-bootclasspath", []string{
Paul Duffin74431d52021-04-21 14:10:42 +0100373 // The configured contents of BootJars.
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100374 "com.android.art:baz",
375 "com.android.art:quuz",
376 "platform:foo",
Paul Duffin74431d52021-04-21 14:10:42 +0100377
satayevd604b212021-07-21 14:23:52 +0100378 // The configured contents of ApexBootJars.
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100379 "myapex:bar",
380 })
381
382 java.CheckPlatformBootclasspathFragments(t, result, "myplatform-bootclasspath", []string{
Paul Duffin89f570a2021-06-16 01:42:33 +0100383 "com.android.art:art-bootclasspath-fragment",
384 "myapex:my-bootclasspath-fragment",
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100385 })
386
Paul Duffinb432df92021-03-22 22:09:42 +0000387 // Make sure that the myplatform-bootclasspath has the correct dependencies.
388 CheckModuleDependencies(t, result.TestContext, "myplatform-bootclasspath", "android_common", []string{
Spandan Das64c9e0c2023-12-20 20:13:34 +0000389 // source vs prebuilt selection metadata module
390 `platform:all_apex_contributions`,
391
Paul Duffin74431d52021-04-21 14:10:42 +0100392 // The following are stubs.
Jihoon Kangbd093452023-12-26 19:08:01 +0000393 `platform:android_stubs_current_exportable`,
394 `platform:android_system_stubs_current_exportable`,
395 `platform:android_test_stubs_current_exportable`,
396 `platform:legacy.core.platform.api.stubs.exportable`,
Paul Duffin74431d52021-04-21 14:10:42 +0100397
398 // Needed for generating the boot image.
Paul Duffinb432df92021-03-22 22:09:42 +0000399 `platform:dex2oatd`,
Paul Duffin74431d52021-04-21 14:10:42 +0100400
401 // The configured contents of BootJars.
Paul Duffinb432df92021-03-22 22:09:42 +0000402 `com.android.art:baz`,
403 `com.android.art:quuz`,
404 `platform:foo`,
Paul Duffin74431d52021-04-21 14:10:42 +0100405
satayevd604b212021-07-21 14:23:52 +0100406 // The configured contents of ApexBootJars.
Paul Duffinb432df92021-03-22 22:09:42 +0000407 `myapex:bar`,
Paul Duffin74431d52021-04-21 14:10:42 +0100408
409 // The fragments.
Paul Duffin62d8c3b2021-04-07 20:35:11 +0100410 `com.android.art:art-bootclasspath-fragment`,
Paul Duffin89f570a2021-06-16 01:42:33 +0100411 `myapex:my-bootclasspath-fragment`,
Jihoon Kanga6d0aa82024-09-24 00:34:49 +0000412
413 // Impl lib of sdk_library for transitive srcjar generation
414 `platform:foo.impl`,
Paul Duffinb432df92021-03-22 22:09:42 +0000415 })
416}
417
Paul Duffin7487a7a2021-05-19 09:36:09 +0100418// TestPlatformBootclasspath_AlwaysUsePrebuiltSdks verifies that the build does not fail when
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100419// AlwaysUsePrebuiltSdk() returns true.
Paul Duffin7487a7a2021-05-19 09:36:09 +0100420func TestPlatformBootclasspath_AlwaysUsePrebuiltSdks(t *testing.T) {
421 result := android.GroupFixturePreparers(
422 prepareForTestWithPlatformBootclasspath,
423 prepareForTestWithMyapex,
424 // Configure two libraries, the first is a java_sdk_library whose prebuilt will be used because
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100425 // of AlwaysUsePrebuiltsSdk(). The second is a normal library that is unaffected. The order
426 // matters, so that the dependencies resolved by the platform_bootclasspath matches the
427 // configured list.
satayevd604b212021-07-21 14:23:52 +0100428 java.FixtureConfigureApexBootJars("myapex:foo", "myapex:bar"),
Paul Duffin7487a7a2021-05-19 09:36:09 +0100429 java.PrepareForTestWithJavaSdkLibraryFiles,
430 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
431 variables.Always_use_prebuilt_sdks = proptools.BoolPtr(true)
432 }),
Colin Crossa66b4632024-08-08 15:50:47 -0700433 android.PrepareForTestWithBuildFlag("RELEASE_HIDDEN_API_EXPORTABLE_STUBS", "true"),
434
Paul Duffin7487a7a2021-05-19 09:36:09 +0100435 java.FixtureWithPrebuiltApis(map[string][]string{
436 "current": {},
437 "30": {"foo"},
438 }),
439 ).RunTestWithBp(t, `
440 apex {
441 name: "myapex",
442 key: "myapex.key",
443 bootclasspath_fragments: [
444 "mybootclasspath-fragment",
445 ],
446 updatable: false,
447 }
448
449 apex_key {
450 name: "myapex.key",
451 public_key: "testkey.avbpubkey",
452 private_key: "testkey.pem",
453 }
454
455 java_library {
456 name: "bar",
457 srcs: ["b.java"],
458 installable: true,
459 apex_available: ["myapex"],
460 permitted_packages: ["bar"],
461 }
462
463 java_sdk_library {
464 name: "foo",
465 srcs: ["b.java"],
466 shared_library: false,
467 public: {
468 enabled: true,
469 },
470 apex_available: ["myapex"],
471 permitted_packages: ["foo"],
472 }
473
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100474 prebuilt_apex {
475 name: "myapex",
476 src: "myapex.apex",
477 exported_bootclasspath_fragments: ["mybootclasspath-fragment"],
478 }
479
Paul Duffin7487a7a2021-05-19 09:36:09 +0100480 // A prebuilt java_sdk_library_import that is not preferred by default but will be preferred
481 // because AlwaysUsePrebuiltSdks() is true.
482 java_sdk_library_import {
483 name: "foo",
484 prefer: false,
485 shared_library: false,
Paul Duffin630b11e2021-07-15 13:35:26 +0100486 permitted_packages: ["foo"],
Paul Duffin7487a7a2021-05-19 09:36:09 +0100487 public: {
488 jars: ["sdk_library/public/foo-stubs.jar"],
489 stub_srcs: ["sdk_library/public/foo_stub_sources"],
490 current_api: "sdk_library/public/foo.txt",
491 removed_api: "sdk_library/public/foo-removed.txt",
492 sdk_version: "current",
493 },
494 apex_available: ["myapex"],
495 }
496
497 // This always depends on the source foo module, its dependencies are not affected by the
498 // AlwaysUsePrebuiltSdks().
499 bootclasspath_fragment {
500 name: "mybootclasspath-fragment",
501 apex_available: [
502 "myapex",
503 ],
504 contents: [
505 "foo", "bar",
506 ],
Paul Duffin9fd56472022-03-31 15:42:30 +0100507 hidden_api: {
508 split_packages: ["*"],
509 },
Paul Duffin7487a7a2021-05-19 09:36:09 +0100510 }
511
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100512 prebuilt_bootclasspath_fragment {
513 name: "mybootclasspath-fragment",
514 apex_available: [
515 "myapex",
516 ],
517 contents: [
518 "foo",
519 ],
520 hidden_api: {
521 stub_flags: "",
522 annotation_flags: "",
523 metadata: "",
524 index: "",
525 all_flags: "",
526 },
527 }
528
Paul Duffin7487a7a2021-05-19 09:36:09 +0100529 platform_bootclasspath {
530 name: "myplatform-bootclasspath",
Paul Duffin89f570a2021-06-16 01:42:33 +0100531 fragments: [
532 {
533 apex: "myapex",
534 module:"mybootclasspath-fragment",
535 },
536 ],
Paul Duffin7487a7a2021-05-19 09:36:09 +0100537 }
538`,
539 )
540
541 java.CheckPlatformBootclasspathModules(t, result, "myplatform-bootclasspath", []string{
542 // The configured contents of BootJars.
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100543 "myapex:prebuilt_foo",
Paul Duffin7487a7a2021-05-19 09:36:09 +0100544 "myapex:bar",
545 })
546
547 // Make sure that the myplatform-bootclasspath has the correct dependencies.
548 CheckModuleDependencies(t, result.TestContext, "myplatform-bootclasspath", "android_common", []string{
Spandan Das64c9e0c2023-12-20 20:13:34 +0000549 // source vs prebuilt selection metadata module
550 `platform:all_apex_contributions`,
551
Paul Duffin7487a7a2021-05-19 09:36:09 +0100552 // The following are stubs.
553 "platform:prebuilt_sdk_public_current_android",
554 "platform:prebuilt_sdk_system_current_android",
555 "platform:prebuilt_sdk_test_current_android",
556
557 // Not a prebuilt as no prebuilt existed when it was added.
Jihoon Kangbd093452023-12-26 19:08:01 +0000558 "platform:legacy.core.platform.api.stubs.exportable",
Paul Duffin7487a7a2021-05-19 09:36:09 +0100559
Paul Duffin7487a7a2021-05-19 09:36:09 +0100560 // The platform_bootclasspath intentionally adds dependencies on both source and prebuilt
561 // modules when available as it does not know which one will be preferred.
Paul Duffin7487a7a2021-05-19 09:36:09 +0100562 "myapex:foo",
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100563 "myapex:prebuilt_foo",
Paul Duffin7487a7a2021-05-19 09:36:09 +0100564
565 // Only a source module exists.
566 "myapex:bar",
Paul Duffin89f570a2021-06-16 01:42:33 +0100567
568 // The fragments.
569 "myapex:mybootclasspath-fragment",
Martin Stjernholmb1e61cb2021-09-08 21:56:18 +0100570 "myapex:prebuilt_mybootclasspath-fragment",
Jihoon Kanga6d0aa82024-09-24 00:34:49 +0000571
572 // Impl lib of sdk_library for transitive srcjar generation
573 "platform:foo.impl",
Paul Duffin7487a7a2021-05-19 09:36:09 +0100574 })
575}
576
Paul Duffinb432df92021-03-22 22:09:42 +0000577// CheckModuleDependencies checks the dependencies of the selected module against the expected list.
578//
579// The expected list must be a list of strings of the form "<apex>:<module>", where <apex> is the
580// name of the apex, or platform is it is not part of an apex and <module> is the module name.
581func CheckModuleDependencies(t *testing.T, ctx *android.TestContext, name, variant string, expected []string) {
582 t.Helper()
583 module := ctx.ModuleForTests(name, variant).Module()
584 modules := []android.Module{}
585 ctx.VisitDirectDeps(module, func(m blueprint.Module) {
586 modules = append(modules, m.(android.Module))
587 })
588
589 pairs := java.ApexNamePairsFromModules(ctx, modules)
590 android.AssertDeepEquals(t, "module dependencies", expected, pairs)
591}
satayevb3090502021-06-15 17:49:10 +0100592
593// TestPlatformBootclasspath_IncludesRemainingApexJars verifies that any apex boot jar is present in
594// platform_bootclasspath's classpaths.proto config, if the apex does not generate its own config
595// by setting generate_classpaths_proto property to false.
596func TestPlatformBootclasspath_IncludesRemainingApexJars(t *testing.T) {
597 result := android.GroupFixturePreparers(
598 prepareForTestWithPlatformBootclasspath,
599 prepareForTestWithMyapex,
satayevd604b212021-07-21 14:23:52 +0100600 java.FixtureConfigureApexBootJars("myapex:foo"),
satayevb3090502021-06-15 17:49:10 +0100601 android.FixtureWithRootAndroidBp(`
602 platform_bootclasspath {
603 name: "platform-bootclasspath",
604 fragments: [
605 {
606 apex: "myapex",
607 module:"foo-fragment",
608 },
609 ],
610 }
611
612 apex {
613 name: "myapex",
614 key: "myapex.key",
615 bootclasspath_fragments: ["foo-fragment"],
616 updatable: false,
617 }
618
619 apex_key {
620 name: "myapex.key",
621 public_key: "testkey.avbpubkey",
622 private_key: "testkey.pem",
623 }
624
625 bootclasspath_fragment {
626 name: "foo-fragment",
627 generate_classpaths_proto: false,
628 contents: ["foo"],
629 apex_available: ["myapex"],
Paul Duffin9fd56472022-03-31 15:42:30 +0100630 hidden_api: {
631 split_packages: ["*"],
632 },
satayevb3090502021-06-15 17:49:10 +0100633 }
634
635 java_library {
636 name: "foo",
637 srcs: ["a.java"],
638 system_modules: "none",
639 sdk_version: "none",
640 compile_dex: true,
641 apex_available: ["myapex"],
642 permitted_packages: ["foo"],
643 }
644 `),
645 ).RunTest(t)
646
647 java.CheckClasspathFragmentProtoContentInfoProvider(t, result,
648 true, // proto should be generated
649 "myapex:foo", // apex doesn't generate its own config, so must be in platform_bootclasspath
650 "bootclasspath.pb",
651 "out/soong/target/product/test_device/system/etc/classpaths",
652 )
653}
satayevd34eb0c2021-08-06 13:20:28 +0100654
655func TestBootJarNotInApex(t *testing.T) {
656 android.GroupFixturePreparers(
657 prepareForTestWithPlatformBootclasspath,
658 PrepareForTestWithApexBuildComponents,
659 prepareForTestWithMyapex,
660 java.FixtureConfigureApexBootJars("myapex:foo"),
661 ).ExtendWithErrorHandler(android.FixtureExpectsAtLeastOneErrorMatchingPattern(
662 `dependency "foo" of "myplatform-bootclasspath" missing variant`)).
663 RunTestWithBp(t, `
664 apex {
665 name: "myapex",
666 key: "myapex.key",
667 updatable: false,
668 }
669
670 apex_key {
671 name: "myapex.key",
672 public_key: "testkey.avbpubkey",
673 private_key: "testkey.pem",
674 }
675
676 java_library {
677 name: "foo",
678 srcs: ["b.java"],
679 installable: true,
680 apex_available: [
681 "myapex",
682 ],
683 }
684
685 bootclasspath_fragment {
686 name: "not-in-apex-fragment",
687 contents: [
688 "foo",
689 ],
Paul Duffin9fd56472022-03-31 15:42:30 +0100690 hidden_api: {
691 split_packages: ["*"],
692 },
satayevd34eb0c2021-08-06 13:20:28 +0100693 }
694
695 platform_bootclasspath {
696 name: "myplatform-bootclasspath",
697 }
698 `)
699}
700
701func TestBootFragmentNotInApex(t *testing.T) {
702 android.GroupFixturePreparers(
703 prepareForTestWithPlatformBootclasspath,
704 PrepareForTestWithApexBuildComponents,
705 prepareForTestWithMyapex,
706 java.FixtureConfigureApexBootJars("myapex:foo"),
707 ).ExtendWithErrorHandler(android.FixtureExpectsAtLeastOneErrorMatchingPattern(
708 `library foo.*have no corresponding fragment.*`)).RunTestWithBp(t, `
709 apex {
710 name: "myapex",
711 key: "myapex.key",
712 java_libs: ["foo"],
713 updatable: false,
714 }
715
716 apex_key {
717 name: "myapex.key",
718 public_key: "testkey.avbpubkey",
719 private_key: "testkey.pem",
720 }
721
722 java_library {
723 name: "foo",
724 srcs: ["b.java"],
725 installable: true,
726 apex_available: ["myapex"],
727 permitted_packages: ["foo"],
728 }
729
730 bootclasspath_fragment {
731 name: "not-in-apex-fragment",
732 contents: ["foo"],
Paul Duffin9fd56472022-03-31 15:42:30 +0100733 hidden_api: {
734 split_packages: ["*"],
735 },
satayevd34eb0c2021-08-06 13:20:28 +0100736 }
737
738 platform_bootclasspath {
739 name: "myplatform-bootclasspath",
740 }
741 `)
742}
743
744func TestNonBootJarInFragment(t *testing.T) {
745 android.GroupFixturePreparers(
746 prepareForTestWithPlatformBootclasspath,
747 PrepareForTestWithApexBuildComponents,
748 prepareForTestWithMyapex,
749 java.FixtureConfigureApexBootJars("myapex:foo"),
750 ).ExtendWithErrorHandler(android.FixtureExpectsAtLeastOneErrorMatchingPattern(
751 `in contents must also be declared in PRODUCT_APEX_BOOT_JARS`)).
752 RunTestWithBp(t, `
753 apex {
754 name: "myapex",
755 key: "myapex.key",
756 bootclasspath_fragments: ["apex-fragment"],
757 updatable: false,
758 }
759
760 apex_key {
761 name: "myapex.key",
762 public_key: "testkey.avbpubkey",
763 private_key: "testkey.pem",
764 }
765
766 java_library {
767 name: "foo",
768 srcs: ["b.java"],
769 installable: true,
770 apex_available: ["myapex"],
771 permitted_packages: ["foo"],
772 }
773
774 java_library {
775 name: "bar",
776 srcs: ["b.java"],
777 installable: true,
778 apex_available: ["myapex"],
779 permitted_packages: ["bar"],
780 }
781
782 bootclasspath_fragment {
783 name: "apex-fragment",
784 contents: ["foo", "bar"],
785 apex_available:[ "myapex" ],
Paul Duffin9fd56472022-03-31 15:42:30 +0100786 hidden_api: {
787 split_packages: ["*"],
788 },
satayevd34eb0c2021-08-06 13:20:28 +0100789 }
790
791 platform_bootclasspath {
792 name: "myplatform-bootclasspath",
793 fragments: [{
794 apex: "myapex",
795 module:"apex-fragment",
796 }],
797 }
798 `)
799}
Spandan Das3d0d31a2024-05-03 21:36:48 +0000800
Spandan Dased7a0302024-08-26 18:06:25 +0000801// Skip bcp_fragment content validation of source apexes if prebuilts are active.
802func TestNonBootJarInPrebuilts(t *testing.T) {
803 testCases := []struct {
804 description string
805 selectedApexContributions string
806 expectedError string
807 }{
808 {
809 description: "source is active",
810 selectedApexContributions: "",
811 expectedError: "in contents must also be declared in PRODUCT_APEX_BOOT_JARS",
812 },
813 {
814 description: "prebuilts are active",
815 selectedApexContributions: "myapex.prebuilt.contributions",
816 expectedError: "", // skip content validation of source bcp fragment
817 },
818 }
819 bp := `
820// Source
821apex {
822 name: "myapex",
823 key: "myapex.key",
824 bootclasspath_fragments: ["apex-fragment"],
825 updatable: false,
826 min_sdk_version: "29",
827}
828
829override_apex {
830 name: "myapex.override", // overrides the min_sdk_version, thereby creating different variants of its transitive deps
831 base: "myapex",
832 min_sdk_version: "34",
833}
834
835apex_key {
836 name: "myapex.key",
837 public_key: "testkey.avbpubkey",
838 private_key: "testkey.pem",
839}
840
841java_library {
842 name: "foo",
843 srcs: ["b.java"],
844 installable: true,
845 apex_available: ["myapex"],
846 permitted_packages: ["foo"],
847 min_sdk_version: "29",
848}
849
850java_library {
851 name: "bar",
852 srcs: ["b.java"],
853 installable: true,
854 apex_available: ["myapex"],
855 permitted_packages: ["bar"],
856 min_sdk_version: "29",
857}
858
859bootclasspath_fragment {
860 name: "apex-fragment",
861 contents: ["foo", "bar"],
862 apex_available:[ "myapex" ],
863 hidden_api: {
864 split_packages: ["*"],
865 },
866}
867
868platform_bootclasspath {
869 name: "myplatform-bootclasspath",
870 fragments: [{
871 apex: "myapex",
872 module:"apex-fragment",
873 }],
874}
875
876// prebuilts
877prebuilt_apex {
878 name: "myapex",
879 apex_name: "myapex",
880 src: "myapex.apex",
881 exported_bootclasspath_fragments: ["apex-fragment"],
882 }
883
884 prebuilt_bootclasspath_fragment {
885 name: "apex-fragment",
886 contents: ["foo"],
887 hidden_api: {
888 annotation_flags: "my-bootclasspath-fragment/annotation-flags.csv",
889 metadata: "my-bootclasspath-fragment/metadata.csv",
890 index: "my-bootclasspath-fragment/index.csv",
891 stub_flags: "my-bootclasspath-fragment/stub-flags.csv",
892 all_flags: "my-bootclasspath-fragment/all-flags.csv",
893 },
894 }
895 java_import {
896 name: "foo",
897 jars: ["foo.jar"],
898 }
899
900apex_contributions {
901 name: "myapex.prebuilt.contributions",
902 api_domain: "myapex",
903 contents: ["prebuilt_myapex"],
904}
905`
906
907 for _, tc := range testCases {
908 fixture := android.GroupFixturePreparers(
909 prepareForTestWithPlatformBootclasspath,
910 PrepareForTestWithApexBuildComponents,
911 prepareForTestWithMyapex,
912 java.FixtureConfigureApexBootJars("myapex:foo"),
913 android.PrepareForTestWithBuildFlag("RELEASE_APEX_CONTRIBUTIONS_ADSERVICES", tc.selectedApexContributions),
914 )
915 if tc.expectedError != "" {
916 fixture = fixture.ExtendWithErrorHandler(android.FixtureExpectsAtLeastOneErrorMatchingPattern(tc.expectedError))
917 }
918 fixture.RunTestWithBp(t, bp)
919 }
920
921}
922
Spandan Das3d0d31a2024-05-03 21:36:48 +0000923// Source and prebuilt apex provide different set of boot jars
924func TestNonBootJarMissingInPrebuiltFragment(t *testing.T) {
925 bp := `
926 apex {
927 name: "myapex",
928 key: "myapex.key",
929 bootclasspath_fragments: ["apex-fragment"],
930 updatable: false,
931 }
932
933 apex_key {
934 name: "myapex.key",
935 public_key: "testkey.avbpubkey",
936 private_key: "testkey.pem",
937 }
938
939 java_library {
940 name: "foo",
941 srcs: ["b.java"],
942 installable: true,
943 apex_available: ["myapex"],
944 permitted_packages: ["foo"],
945 }
946
947 java_library {
948 name: "bar",
949 srcs: ["b.java"],
950 installable: true,
951 apex_available: ["myapex"],
952 permitted_packages: ["bar"],
953 }
954
955 bootclasspath_fragment {
956 name: "apex-fragment",
957 contents: ["foo", "bar"],
958 apex_available:[ "myapex" ],
959 hidden_api: {
960 split_packages: ["*"],
961 },
962 }
963
964 prebuilt_apex {
965 name: "com.google.android.myapex", // mainline prebuilt selection logic in soong relies on the naming convention com.google.android
966 apex_name: "myapex",
967 source_apex_name: "myapex",
968 src: "myapex.apex",
969 exported_bootclasspath_fragments: ["apex-fragment"],
970 }
971
972 java_import {
973 name: "foo",
974 jars: ["foo.jar"],
975 apex_available: ["myapex"],
976 permitted_packages: ["foo"],
977 }
978
979 prebuilt_bootclasspath_fragment {
980 name: "apex-fragment",
981 contents: ["foo"], // Unlike the source fragment, this is missing bar
982 apex_available:[ "myapex" ],
983 hidden_api: {
984 annotation_flags: "my-bootclasspath-fragment/annotation-flags.csv",
985 metadata: "my-bootclasspath-fragment/metadata.csv",
986 index: "my-bootclasspath-fragment/index.csv",
987 stub_flags: "my-bootclasspath-fragment/stub-flags.csv",
988 all_flags: "my-bootclasspath-fragment/all-flags.csv",
989 },
990 }
991
Spandan Das5f1f9402024-05-21 18:59:23 +0000992 // Another prebuilt apex, but this is not selected during the build.
993 prebuilt_apex {
994 name: "com.google.android.myapex.v2", // mainline prebuilt selection logic in soong relies on the naming convention com.google.android
995 apex_name: "myapex",
996 source_apex_name: "myapex",
997 src: "myapex.apex",
998 exported_bootclasspath_fragments: ["apex-fragment.v2"],
999 }
1000
1001 java_import {
1002 name: "bar",
1003 jars: ["bar.jar"],
1004 apex_available: ["myapex"],
1005 permitted_packages: ["bar"],
1006 }
1007
1008 prebuilt_bootclasspath_fragment {
1009 name: "apex-fragment.v2",
1010 contents: ["bar"], // Unlike the source fragment, this is missing foo
1011 apex_available:[ "myapex" ],
1012 hidden_api: {
1013 annotation_flags: "my-bootclasspath-fragment/annotation-flags.csv",
1014 metadata: "my-bootclasspath-fragment/metadata.csv",
1015 index: "my-bootclasspath-fragment/index.csv",
1016 stub_flags: "my-bootclasspath-fragment/stub-flags.csv",
1017 all_flags: "my-bootclasspath-fragment/all-flags.csv",
1018 },
1019 }
1020
1021
Spandan Das3d0d31a2024-05-03 21:36:48 +00001022 apex_contributions {
1023 name: "my_apex_contributions",
1024 api_domain: "myapex",
1025 contents: [%v],
1026 }
1027 `
1028 testCases := []struct {
1029 desc string
1030 configuredBootJars []string
1031 apexContributionContents string
1032 errorExpected bool
1033 }{
1034 {
1035 desc: "Source apex is selected, and APEX_BOOT_JARS is correctly configured for source apex builds",
1036 configuredBootJars: []string{"myapex:foo", "myapex:bar"},
1037 },
1038 {
1039 desc: "Source apex is selected, and APEX_BOOT_JARS is missing bar",
1040 configuredBootJars: []string{"myapex:foo"},
1041 errorExpected: true,
1042 },
1043 {
1044 desc: "Prebuilt apex is selected, and APEX_BOOT_JARS is correctly configured for prebuilt apex build",
1045 configuredBootJars: []string{"myapex:foo"},
1046 apexContributionContents: `"prebuilt_com.google.android.myapex"`,
1047 },
1048 {
1049 desc: "Prebuilt apex is selected, and APEX_BOOT_JARS is missing foo",
1050 configuredBootJars: []string{"myapex:bar"},
1051 apexContributionContents: `"prebuilt_com.google.android.myapex"`,
1052 errorExpected: true,
1053 },
1054 }
1055
1056 for _, tc := range testCases {
1057 fixture := android.GroupFixturePreparers(
1058 prepareForTestWithPlatformBootclasspath,
1059 PrepareForTestWithApexBuildComponents,
1060 prepareForTestWithMyapex,
1061 java.FixtureConfigureApexBootJars(tc.configuredBootJars...),
Colin Crossa66b4632024-08-08 15:50:47 -07001062 android.PrepareForTestWithBuildFlag("RELEASE_APEX_CONTRIBUTIONS_ART", "my_apex_contributions"),
Spandan Das3d0d31a2024-05-03 21:36:48 +00001063 )
1064 if tc.errorExpected {
1065 fixture = fixture.ExtendWithErrorHandler(
1066 android.FixtureExpectsAtLeastOneErrorMatchingPattern(`in contents.*must also be declared in PRODUCT_APEX_BOOT_JARS`),
1067 )
1068 }
1069 fixture.RunTestWithBp(t, fmt.Sprintf(bp, tc.apexContributionContents))
1070 }
1071}