• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// 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 sdk
16
17import (
18	"fmt"
19	"path/filepath"
20	"strings"
21	"testing"
22
23	"android/soong/android"
24	"android/soong/java"
25)
26
27// fixtureAddPlatformBootclasspathForBootclasspathFragment adds a platform_bootclasspath module that
28// references the bootclasspath fragment.
29func fixtureAddPlatformBootclasspathForBootclasspathFragment(apex, fragment string) android.FixturePreparer {
30	return fixtureAddPlatformBootclasspathForBootclasspathFragmentWithExtra(apex, fragment, "")
31}
32
33// fixtureAddPlatformBootclasspathForBootclasspathFragmentWithExtra is the same as above, but also adds extra fragments.
34func fixtureAddPlatformBootclasspathForBootclasspathFragmentWithExtra(apex, fragment, extraFragments string) android.FixturePreparer {
35	return android.GroupFixturePreparers(
36		// Add a platform_bootclasspath module.
37		android.FixtureAddTextFile("frameworks/base/boot/Android.bp", fmt.Sprintf(`
38			platform_bootclasspath {
39				name: "platform-bootclasspath",
40				fragments: [
41					{
42						apex: "%s",
43						module: "%s",
44					},
45					%s
46				],
47			}
48		`, apex, fragment, extraFragments)),
49		android.FixtureAddFile("frameworks/base/boot/boot-profile.txt", nil),
50		android.FixtureAddFile("frameworks/base/boot/boot-image-profile.txt", nil),
51		android.FixtureAddFile("art/build/boot/boot-image-profile.txt", nil),
52		android.FixtureAddFile("build/soong/scripts/check_boot_jars/package_allowed_list.txt", nil),
53	)
54}
55
56// fixtureAddPrebuiltApexForBootclasspathFragment adds a prebuilt_apex that exports the fragment.
57func fixtureAddPrebuiltApexForBootclasspathFragment(apex, fragment string) android.FixturePreparer {
58	apexFile := fmt.Sprintf("%s.apex", apex)
59	dir := "prebuilts/apex"
60	return android.GroupFixturePreparers(
61		// A preparer to add a prebuilt apex to the test fixture.
62		android.FixtureAddTextFile(filepath.Join(dir, "Android.bp"), fmt.Sprintf(`
63			prebuilt_apex {
64				name: "%s",
65				src: "%s",
66				exported_bootclasspath_fragments: [
67					"%s",
68				],
69				prefer: false,
70			}
71		`, apex, apexFile, fragment)),
72		android.FixtureAddFile(filepath.Join(dir, apexFile), nil),
73	)
74}
75
76func TestSnapshotWithBootclasspathFragment_ImageName(t *testing.T) {
77	t.Parallel()
78	result := android.GroupFixturePreparers(
79		prepareForSdkTestWithJava,
80		java.PrepareForTestWithDexpreopt,
81		prepareForSdkTestWithApex,
82
83		// Some additional files needed for the art apex.
84		android.FixtureMergeMockFs(android.MockFS{
85			"com.android.art.avbpubkey":                          nil,
86			"com.android.art.pem":                                nil,
87			"system/sepolicy/apex/com.android.art-file_contexts": nil,
88		}),
89
90		// Add a platform_bootclasspath that depends on the fragment.
91		fixtureAddPlatformBootclasspathForBootclasspathFragmentWithExtra(
92			"com.android.art", "art-bootclasspath-fragment", java.ApexBootJarFragmentsForPlatformBootclasspath),
93
94		java.PrepareForBootImageConfigTest,
95		java.PrepareApexBootJarConfigsAndModules,
96		android.FixtureWithRootAndroidBp(`
97			sdk {
98				name: "mysdk",
99				bootclasspath_fragments: ["art-bootclasspath-fragment"],
100			}
101
102			apex {
103				name: "com.android.art",
104				key: "com.android.art.key",
105				bootclasspath_fragments: [
106					"art-bootclasspath-fragment",
107				],
108				updatable: false,
109			}
110
111			bootclasspath_fragment {
112				name: "art-bootclasspath-fragment",
113				image_name: "art",
114				contents: ["core1", "core2"],
115				apex_available: ["com.android.art"],
116				hidden_api: {
117					split_packages: ["*"],
118				},
119			}
120
121			apex_key {
122				name: "com.android.art.key",
123				public_key: "com.android.art.avbpubkey",
124				private_key: "com.android.art.pem",
125			}
126
127			java_library {
128				name: "core1",
129				srcs: ["Test.java"],
130				system_modules: "none",
131				sdk_version: "none",
132				compile_dex: true,
133				apex_available: ["com.android.art"],
134			}
135
136			java_library {
137				name: "core2",
138				srcs: ["Test.java"],
139				system_modules: "none",
140				sdk_version: "none",
141				compile_dex: true,
142				apex_available: ["com.android.art"],
143			}
144`),
145	).RunTest(t)
146
147	// A preparer to update the test fixture used when processing an unpackage snapshot.
148	preparerForSnapshot := fixtureAddPrebuiltApexForBootclasspathFragment("com.android.art", "art-bootclasspath-fragment")
149
150	// Check that source on its own configures the bootImageConfig correctly.
151	java.CheckMutatedArtBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
152	java.CheckMutatedFrameworkBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
153
154	CheckSnapshot(t, result, "mysdk", "",
155		checkAndroidBpContents(`
156// This is auto-generated. DO NOT EDIT.
157
158apex_contributions_defaults {
159    name: "mysdk.contributions",
160    contents: [],
161}
162
163prebuilt_bootclasspath_fragment {
164    name: "art-bootclasspath-fragment",
165    prefer: false,
166    visibility: ["//visibility:public"],
167    apex_available: ["com.android.art"],
168    image_name: "art",
169    contents: [
170        "core1",
171        "core2",
172    ],
173    hidden_api: {
174        annotation_flags: "hiddenapi/annotation-flags.csv",
175        metadata: "hiddenapi/metadata.csv",
176        index: "hiddenapi/index.csv",
177        signature_patterns: "hiddenapi/signature-patterns.csv",
178        filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
179        filtered_flags: "hiddenapi/filtered-flags.csv",
180    },
181}
182
183java_import {
184    name: "core1",
185    prefer: false,
186    visibility: ["//visibility:public"],
187    apex_available: ["com.android.art"],
188    jars: ["java_boot_libs/snapshot/jars/are/invalid/core1.jar"],
189}
190
191java_import {
192    name: "core2",
193    prefer: false,
194    visibility: ["//visibility:public"],
195    apex_available: ["com.android.art"],
196    jars: ["java_boot_libs/snapshot/jars/are/invalid/core2.jar"],
197}
198
199`),
200		checkAllCopyRules(`
201.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/annotation-flags.csv -> hiddenapi/annotation-flags.csv
202.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/metadata.csv -> hiddenapi/metadata.csv
203.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/index.csv -> hiddenapi/index.csv
204.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/signature-patterns.csv -> hiddenapi/signature-patterns.csv
205.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/filtered-stub-flags.csv -> hiddenapi/filtered-stub-flags.csv
206.intermediates/art-bootclasspath-fragment/android_common/modular-hiddenapi/filtered-flags.csv -> hiddenapi/filtered-flags.csv
207.intermediates/mysdk/common_os/empty -> java_boot_libs/snapshot/jars/are/invalid/core1.jar
208.intermediates/mysdk/common_os/empty -> java_boot_libs/snapshot/jars/are/invalid/core2.jar
209		`),
210		snapshotTestPreparer(checkSnapshotWithoutSource, android.GroupFixturePreparers(
211			preparerForSnapshot,
212			// Flag ART prebuilts
213			android.FixtureMergeMockFs(android.MockFS{
214				"apex_contributions/Android.bp": []byte(`
215				apex_contributions {
216					name: "prebuilt_art_contributions",
217					contents: ["prebuilt_com.android.art"],
218					api_domain: "com.android.art",
219				}
220			`)}),
221			android.PrepareForTestWithBuildFlag("RELEASE_APEX_CONTRIBUTIONS_ART", "prebuilt_art_contributions"),
222		)),
223
224		// Check the behavior of the snapshot without the source.
225		snapshotTestChecker(checkSnapshotWithoutSource, func(t *testing.T, result *android.TestResult) {
226			// Make sure that the boot jars package check rule includes the dex jars retrieved from the prebuilt apex.
227			checkBootJarsPackageCheckRule(t, result,
228				append(
229					[]string{
230						"out/soong/.intermediates/prebuilts/apex/com.android.art/android_common_prebuilt_com.android.art/deapexer/javalib/core1.jar",
231						"out/soong/.intermediates/prebuilts/apex/com.android.art/android_common_prebuilt_com.android.art/deapexer/javalib/core2.jar",
232						"out/soong/.intermediates/default/java/framework/android_common/aligned/framework.jar",
233					},
234					java.ApexBootJarDexJarPaths...,
235				)...,
236			)
237			java.CheckMutatedArtBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
238			java.CheckMutatedFrameworkBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
239		}),
240
241		snapshotTestPreparer(checkSnapshotWithSourcePreferred, preparerForSnapshot),
242
243		// Check the behavior of the snapshot when the source is preferred.
244		snapshotTestChecker(checkSnapshotWithSourcePreferred, func(t *testing.T, result *android.TestResult) {
245			java.CheckMutatedArtBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
246			java.CheckMutatedFrameworkBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
247		}),
248
249		snapshotTestPreparer(checkSnapshotPreferredWithSource, preparerForSnapshot),
250
251		// Check the behavior of the snapshot when it is preferred.
252		snapshotTestChecker(checkSnapshotPreferredWithSource, func(t *testing.T, result *android.TestResult) {
253			java.CheckMutatedArtBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
254			java.CheckMutatedFrameworkBootImageConfig(t, result, "out/soong/.intermediates/default/java/dex_bootjars/android_common/meta_lic")
255		}),
256	)
257
258	// Make sure that the boot jars package check rule includes the dex jars created from the source.
259	checkBootJarsPackageCheckRule(t, result,
260		append(
261			[]string{
262				"out/soong/.intermediates/core1/android_common_apex10000/aligned/core1.jar",
263				"out/soong/.intermediates/core2/android_common_apex10000/aligned/core2.jar",
264				"out/soong/.intermediates/default/java/framework/android_common/aligned/framework.jar",
265			},
266			java.ApexBootJarDexJarPaths...,
267		)...,
268	)
269}
270
271// checkBootJarsPackageCheckRule checks that the supplied module is an input to the boot jars
272// package check rule.
273func checkBootJarsPackageCheckRule(t *testing.T, result *android.TestResult, expectedModules ...string) {
274	t.Helper()
275	platformBcp := result.ModuleForTests(t, "platform-bootclasspath", "android_common")
276	bootJarsCheckRule := platformBcp.Rule("boot_jars_package_check")
277	command := bootJarsCheckRule.RuleParams.Command
278	expectedCommandArgs := " build/soong/scripts/check_boot_jars/package_allowed_list.txt " + strings.Join(expectedModules, " ") + " &&"
279	android.AssertStringDoesContain(t, "boot jars package check", command, expectedCommandArgs)
280}
281
282func testSnapshotWithBootClasspathFragment_Contents(t *testing.T, sdk string, copyRules string) {
283	result := android.GroupFixturePreparers(
284		prepareForSdkTestWithJava,
285		java.PrepareForTestWithJavaDefaultModules,
286		java.PrepareForTestWithJavaSdkLibraryFiles,
287		java.FixtureWithLastReleaseApis("mysdklibrary", "myothersdklibrary", "mycoreplatform"),
288		java.FixtureConfigureApexBootJars("myapex:mybootlib", "myapex:myothersdklibrary"),
289		prepareForSdkTestWithApex,
290
291		// Add a platform_bootclasspath that depends on the fragment.
292		fixtureAddPlatformBootclasspathForBootclasspathFragment("myapex", "mybootclasspathfragment"),
293
294		android.PrepareForTestWithBuildFlag("RELEASE_HIDDEN_API_EXPORTABLE_STUBS", "true"),
295		// Make sure that we have atleast one platform library so that we can check the monolithic hiddenapi
296		// file creation.
297		java.FixtureConfigureBootJars("platform:foo"),
298		android.FixtureModifyMockFS(func(fs android.MockFS) {
299			fs["platform/Android.bp"] = []byte(`
300		java_library {
301			name: "foo",
302			srcs: ["Test.java"],
303			compile_dex: true,
304		}
305		`)
306			fs["platform/Test.java"] = nil
307		}),
308
309		android.FixtureWithRootAndroidBp(sdk+`
310			apex {
311				name: "myapex",
312				key: "myapex.key",
313				min_sdk_version: "2",
314				bootclasspath_fragments: ["mybootclasspathfragment"],
315			}
316
317			bootclasspath_fragment {
318				name: "mybootclasspathfragment",
319				apex_available: ["myapex"],
320				contents: [
321					// This should be automatically added to the sdk_snapshot as a java_boot_libs module.
322					"mybootlib",
323					// This should be automatically added to the sdk_snapshot as a java_sdk_libs module.
324					"myothersdklibrary",
325				],
326				api: {
327					stub_libs: ["mysdklibrary"],
328				},
329				core_platform_api: {
330					// This should be automatically added to the sdk_snapshot as a java_sdk_libs module.
331					stub_libs: ["mycoreplatform"],
332				},
333				hidden_api: {
334					split_packages: ["*"],
335				},
336			}
337
338			java_library {
339				name: "mybootlib",
340				apex_available: ["myapex"],
341				srcs: ["Test.java"],
342				system_modules: "none",
343				sdk_version: "none",
344				min_sdk_version: "2",
345				compile_dex: true,
346				permitted_packages: ["mybootlib"],
347			}
348
349			java_sdk_library {
350				name: "mysdklibrary",
351				apex_available: ["myapex"],
352				srcs: ["Test.java"],
353				shared_library: false,
354				public: {enabled: true},
355				min_sdk_version: "2",
356				sdk_version: "current",
357			}
358
359			java_sdk_library {
360				name: "myothersdklibrary",
361				apex_available: ["myapex"],
362				srcs: ["Test.java"],
363				compile_dex: true,
364				public: {enabled: true},
365				min_sdk_version: "2",
366				permitted_packages: ["myothersdklibrary"],
367				sdk_version: "current",
368			}
369
370			java_sdk_library {
371				name: "mycoreplatform",
372				apex_available: ["myapex"],
373				srcs: ["Test.java"],
374				compile_dex: true,
375				public: {enabled: true},
376				min_sdk_version: "2",
377				sdk_version: "current",
378			}
379		`),
380	).RunTest(t)
381
382	// A preparer to update the test fixture used when processing an unpackage snapshot.
383	preparerForSnapshot := fixtureAddPrebuiltApexForBootclasspathFragment("myapex", "mybootclasspathfragment")
384
385	CheckSnapshot(t, result, "mysdk", "",
386		checkAndroidBpContents(`
387// This is auto-generated. DO NOT EDIT.
388
389apex_contributions_defaults {
390    name: "mysdk.contributions",
391    contents: [
392        "prebuilt_myothersdklibrary",
393        "prebuilt_mysdklibrary",
394        "prebuilt_mycoreplatform",
395    ],
396}
397
398prebuilt_bootclasspath_fragment {
399    name: "mybootclasspathfragment",
400    prefer: false,
401    visibility: ["//visibility:public"],
402    apex_available: ["myapex"],
403    contents: [
404        "mybootlib",
405        "myothersdklibrary",
406    ],
407    api: {
408        stub_libs: ["mysdklibrary"],
409    },
410    core_platform_api: {
411        stub_libs: ["mycoreplatform"],
412    },
413    hidden_api: {
414        annotation_flags: "hiddenapi/annotation-flags.csv",
415        metadata: "hiddenapi/metadata.csv",
416        index: "hiddenapi/index.csv",
417        signature_patterns: "hiddenapi/signature-patterns.csv",
418        filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
419        filtered_flags: "hiddenapi/filtered-flags.csv",
420    },
421}
422
423java_import {
424    name: "mybootlib",
425    prefer: false,
426    visibility: ["//visibility:public"],
427    apex_available: ["myapex"],
428    jars: ["java_boot_libs/snapshot/jars/are/invalid/mybootlib.jar"],
429    min_sdk_version: "2",
430    permitted_packages: ["mybootlib"],
431}
432
433java_sdk_library_import {
434    name: "myothersdklibrary",
435    prefer: false,
436    visibility: ["//visibility:public"],
437    apex_available: ["myapex"],
438    shared_library: true,
439    compile_dex: true,
440    permitted_packages: ["myothersdklibrary"],
441    public: {
442        jars: ["sdk_library/public/myothersdklibrary-stubs.jar"],
443        stub_srcs: ["sdk_library/public/myothersdklibrary_stub_sources"],
444        current_api: "sdk_library/public/myothersdklibrary.txt",
445        removed_api: "sdk_library/public/myothersdklibrary-removed.txt",
446        sdk_version: "current",
447    },
448}
449
450java_sdk_library_import {
451    name: "mysdklibrary",
452    prefer: false,
453    visibility: ["//visibility:public"],
454    apex_available: ["myapex"],
455    shared_library: false,
456    public: {
457        jars: ["sdk_library/public/mysdklibrary-stubs.jar"],
458        stub_srcs: ["sdk_library/public/mysdklibrary_stub_sources"],
459        current_api: "sdk_library/public/mysdklibrary.txt",
460        removed_api: "sdk_library/public/mysdklibrary-removed.txt",
461        sdk_version: "current",
462    },
463}
464
465java_sdk_library_import {
466    name: "mycoreplatform",
467    prefer: false,
468    visibility: ["//visibility:public"],
469    apex_available: ["myapex"],
470    shared_library: true,
471    compile_dex: true,
472    public: {
473        jars: ["sdk_library/public/mycoreplatform-stubs.jar"],
474        stub_srcs: ["sdk_library/public/mycoreplatform_stub_sources"],
475        current_api: "sdk_library/public/mycoreplatform.txt",
476        removed_api: "sdk_library/public/mycoreplatform-removed.txt",
477        sdk_version: "current",
478    },
479}
480		`),
481		checkAllCopyRules(copyRules),
482		snapshotTestPreparer(checkSnapshotWithoutSource, preparerForSnapshot),
483		snapshotTestChecker(checkSnapshotWithoutSource, func(t *testing.T, result *android.TestResult) {
484			module := result.ModuleForTests(t, "platform-bootclasspath", "android_common")
485			var rule android.TestingBuildParams
486			rule = module.Output("out/soong/hiddenapi/hiddenapi-flags.csv")
487			java.CheckHiddenAPIRuleInputs(t, "monolithic flags", `
488				out/soong/.intermediates/frameworks/base/boot/platform-bootclasspath/android_common/hiddenapi-monolithic/annotation-flags-from-classes.csv
489        out/soong/hiddenapi/hiddenapi-stub-flags.txt
490        snapshot/hiddenapi/annotation-flags.csv
491			`, rule)
492
493			rule = module.Output("out/soong/hiddenapi/hiddenapi-unsupported.csv")
494			java.CheckHiddenAPIRuleInputs(t, "monolithic metadata", `
495				out/soong/.intermediates/frameworks/base/boot/platform-bootclasspath/android_common/hiddenapi-monolithic/metadata-from-classes.csv
496        snapshot/hiddenapi/metadata.csv
497			`, rule)
498
499			rule = module.Output("out/soong/hiddenapi/hiddenapi-index.csv")
500			java.CheckHiddenAPIRuleInputs(t, "monolithic index", `
501				out/soong/.intermediates/frameworks/base/boot/platform-bootclasspath/android_common/hiddenapi-monolithic/index-from-classes.csv
502        snapshot/hiddenapi/index.csv
503			`, rule)
504
505			rule = module.Output("out/soong/hiddenapi/hiddenapi-flags.csv.valid")
506			android.AssertStringDoesContain(t, "verify-overlaps", rule.RuleParams.Command, " snapshot/hiddenapi/filtered-flags.csv:snapshot/hiddenapi/signature-patterns.csv ")
507		}),
508		snapshotTestPreparer(checkSnapshotWithSourcePreferred, preparerForSnapshot),
509		snapshotTestChecker(checkSnapshotWithSourcePreferred, func(t *testing.T, result *android.TestResult) {
510			module := result.ModuleForTests(t, "platform-bootclasspath", "android_common")
511			rule := module.Output("out/soong/hiddenapi/hiddenapi-flags.csv.valid")
512			android.AssertStringDoesContain(t, "verify-overlaps", rule.RuleParams.Command, " out/soong/.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/filtered-flags.csv:out/soong/.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/signature-patterns.csv ")
513		}),
514		snapshotTestPreparer(checkSnapshotPreferredWithSource, preparerForSnapshot),
515	)
516}
517
518func TestSnapshotWithBootClasspathFragment_Contents(t *testing.T) {
519	t.Parallel()
520	t.Run("added-directly", func(t *testing.T) {
521		t.Parallel()
522		testSnapshotWithBootClasspathFragment_Contents(t, `
523			sdk {
524				name: "mysdk",
525				bootclasspath_fragments: ["mybootclasspathfragment"],
526				java_sdk_libs: [
527					// This is not strictly needed as it should be automatically added to the sdk_snapshot as
528					// a java_sdk_libs module because it is used in the mybootclasspathfragment's
529					// api.stub_libs property. However, it is specified here to ensure that duplicates are
530					// correctly deduped.
531					"mysdklibrary",
532				],
533			}
534		`, `
535.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/annotation-flags.csv -> hiddenapi/annotation-flags.csv
536.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/metadata.csv -> hiddenapi/metadata.csv
537.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/index.csv -> hiddenapi/index.csv
538.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/signature-patterns.csv -> hiddenapi/signature-patterns.csv
539.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/filtered-stub-flags.csv -> hiddenapi/filtered-stub-flags.csv
540.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/filtered-flags.csv -> hiddenapi/filtered-flags.csv
541.intermediates/mysdk/common_os/empty -> java_boot_libs/snapshot/jars/are/invalid/mybootlib.jar
542.intermediates/myothersdklibrary.stubs.exportable/android_common/combined/myothersdklibrary.stubs.exportable.jar -> sdk_library/public/myothersdklibrary-stubs.jar
543.intermediates/myothersdklibrary.stubs.source/android_common/exportable/myothersdklibrary.stubs.source_api.txt -> sdk_library/public/myothersdklibrary.txt
544.intermediates/myothersdklibrary.stubs.source/android_common/exportable/myothersdklibrary.stubs.source_removed.txt -> sdk_library/public/myothersdklibrary-removed.txt
545.intermediates/mysdklibrary.stubs.exportable/android_common/combined/mysdklibrary.stubs.exportable.jar -> sdk_library/public/mysdklibrary-stubs.jar
546.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_api.txt -> sdk_library/public/mysdklibrary.txt
547.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_removed.txt -> sdk_library/public/mysdklibrary-removed.txt
548.intermediates/mycoreplatform.stubs.exportable/android_common/combined/mycoreplatform.stubs.exportable.jar -> sdk_library/public/mycoreplatform-stubs.jar
549.intermediates/mycoreplatform.stubs.source/android_common/exportable/mycoreplatform.stubs.source_api.txt -> sdk_library/public/mycoreplatform.txt
550.intermediates/mycoreplatform.stubs.source/android_common/exportable/mycoreplatform.stubs.source_removed.txt -> sdk_library/public/mycoreplatform-removed.txt
551`)
552	})
553
554	copyBootclasspathFragmentFromApexVariantRules := `
555.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/annotation-flags.csv -> hiddenapi/annotation-flags.csv
556.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/metadata.csv -> hiddenapi/metadata.csv
557.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/index.csv -> hiddenapi/index.csv
558.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/signature-patterns.csv -> hiddenapi/signature-patterns.csv
559.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/filtered-stub-flags.csv -> hiddenapi/filtered-stub-flags.csv
560.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/filtered-flags.csv -> hiddenapi/filtered-flags.csv
561.intermediates/mysdk/common_os/empty -> java_boot_libs/snapshot/jars/are/invalid/mybootlib.jar
562.intermediates/myothersdklibrary.stubs.exportable/android_common/combined/myothersdklibrary.stubs.exportable.jar -> sdk_library/public/myothersdklibrary-stubs.jar
563.intermediates/myothersdklibrary.stubs.source/android_common/exportable/myothersdklibrary.stubs.source_api.txt -> sdk_library/public/myothersdklibrary.txt
564.intermediates/myothersdklibrary.stubs.source/android_common/exportable/myothersdklibrary.stubs.source_removed.txt -> sdk_library/public/myothersdklibrary-removed.txt
565.intermediates/mysdklibrary.stubs.exportable/android_common/combined/mysdklibrary.stubs.exportable.jar -> sdk_library/public/mysdklibrary-stubs.jar
566.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_api.txt -> sdk_library/public/mysdklibrary.txt
567.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_removed.txt -> sdk_library/public/mysdklibrary-removed.txt
568.intermediates/mycoreplatform.stubs.exportable/android_common/combined/mycoreplatform.stubs.exportable.jar -> sdk_library/public/mycoreplatform-stubs.jar
569.intermediates/mycoreplatform.stubs.source/android_common/exportable/mycoreplatform.stubs.source_api.txt -> sdk_library/public/mycoreplatform.txt
570.intermediates/mycoreplatform.stubs.source/android_common/exportable/mycoreplatform.stubs.source_removed.txt -> sdk_library/public/mycoreplatform-removed.txt
571`
572	t.Run("added-via-apex", func(t *testing.T) {
573		t.Parallel()
574		testSnapshotWithBootClasspathFragment_Contents(t, `
575			sdk {
576				name: "mysdk",
577				apexes: ["myapex"],
578			}
579		`, copyBootclasspathFragmentFromApexVariantRules)
580	})
581
582	t.Run("added-directly-and-indirectly", func(t *testing.T) {
583		t.Parallel()
584		testSnapshotWithBootClasspathFragment_Contents(t, `
585			sdk {
586				name: "mysdk",
587				apexes: ["myapex"],
588				// This is not strictly needed as it should be automatically added to the sdk_snapshot as
589				// a bootclasspath_fragments module because it is used in the myapex's
590				// bootclasspath_fragments property. However, it is specified here to ensure that duplicates
591				// are correctly deduped.
592				bootclasspath_fragments: ["mybootclasspathfragment"],
593				java_sdk_libs: [
594					// This is not strictly needed as it should be automatically added to the sdk_snapshot as
595					// a java_sdk_libs module because it is used in the mybootclasspathfragment's
596					// api.stub_libs property. However, it is specified here to ensure that duplicates are
597					// correctly deduped.
598					"mysdklibrary",
599				],
600			}
601		`, copyBootclasspathFragmentFromApexVariantRules)
602	})
603}
604
605// TestSnapshotWithBootClasspathFragment_Fragments makes sure that the fragments property of a
606// bootclasspath_fragment is correctly output to the sdk snapshot.
607func TestSnapshotWithBootClasspathFragment_Fragments(t *testing.T) {
608	t.Parallel()
609	result := android.GroupFixturePreparers(
610		prepareForSdkTestWithJava,
611		java.PrepareForTestWithJavaDefaultModules,
612		java.PrepareForTestWithJavaSdkLibraryFiles,
613		java.FixtureWithLastReleaseApis("mysdklibrary", "myothersdklibrary"),
614		java.FixtureConfigureApexBootJars("someapex:mysdklibrary", "myotherapex:myotherlib"),
615		prepareForSdkTestWithApex,
616
617		// Some additional files needed for the myotherapex.
618		android.FixtureMergeMockFs(android.MockFS{
619			"system/sepolicy/apex/myotherapex-file_contexts": nil,
620			"myotherapex/apex_manifest.json":                 nil,
621			"myotherapex/Test.java":                          nil,
622		}),
623
624		android.FixtureAddTextFile("myotherapex/Android.bp", `
625			apex {
626				name: "myotherapex",
627				key: "myapex.key",
628				min_sdk_version: "2",
629				bootclasspath_fragments: ["myotherbootclasspathfragment"],
630			}
631
632			bootclasspath_fragment {
633				name: "myotherbootclasspathfragment",
634				apex_available: ["myotherapex"],
635				contents: [
636					"myotherlib",
637				],
638				hidden_api: {
639					split_packages: ["*"],
640				},
641			}
642
643			java_library {
644				name: "myotherlib",
645				apex_available: ["myotherapex"],
646				srcs: ["Test.java"],
647				min_sdk_version: "2",
648				permitted_packages: ["myothersdklibrary"],
649				compile_dex: true,
650				sdk_version: "current",
651			}
652		`),
653
654		android.FixtureWithRootAndroidBp(`
655			sdk {
656				name: "mysdk",
657				bootclasspath_fragments: ["mybootclasspathfragment"],
658			}
659
660			bootclasspath_fragment {
661				name: "mybootclasspathfragment",
662				contents: [
663					"mysdklibrary",
664				],
665				fragments: [
666					{
667						apex: "myotherapex",
668						module: "myotherbootclasspathfragment"
669					},
670				],
671				hidden_api: {
672					split_packages: ["*"],
673				},
674			}
675
676			java_sdk_library {
677				name: "mysdklibrary",
678				srcs: ["Test.java"],
679				shared_library: false,
680				public: {enabled: true},
681				min_sdk_version: "2",
682				sdk_version: "current",
683			}
684		`),
685	).RunTest(t)
686
687	// A preparer to update the test fixture used when processing an unpackage snapshot.
688	preparerForSnapshot := fixtureAddPrebuiltApexForBootclasspathFragment("myapex", "mybootclasspathfragment")
689
690	CheckSnapshot(t, result, "mysdk", "",
691		checkAndroidBpContents(`
692// This is auto-generated. DO NOT EDIT.
693
694apex_contributions_defaults {
695    name: "mysdk.contributions",
696    contents: ["prebuilt_mysdklibrary"],
697}
698
699prebuilt_bootclasspath_fragment {
700    name: "mybootclasspathfragment",
701    prefer: false,
702    visibility: ["//visibility:public"],
703    apex_available: ["//apex_available:platform"],
704    contents: ["mysdklibrary"],
705    fragments: [
706        {
707            apex: "myotherapex",
708            module: "myotherbootclasspathfragment",
709        },
710    ],
711    hidden_api: {
712        annotation_flags: "hiddenapi/annotation-flags.csv",
713        metadata: "hiddenapi/metadata.csv",
714        index: "hiddenapi/index.csv",
715        signature_patterns: "hiddenapi/signature-patterns.csv",
716        filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
717        filtered_flags: "hiddenapi/filtered-flags.csv",
718    },
719}
720
721java_sdk_library_import {
722    name: "mysdklibrary",
723    prefer: false,
724    visibility: ["//visibility:public"],
725    apex_available: ["//apex_available:platform"],
726    shared_library: false,
727    public: {
728        jars: ["sdk_library/public/mysdklibrary-stubs.jar"],
729        stub_srcs: ["sdk_library/public/mysdklibrary_stub_sources"],
730        current_api: "sdk_library/public/mysdklibrary.txt",
731        removed_api: "sdk_library/public/mysdklibrary-removed.txt",
732        sdk_version: "current",
733    },
734}
735		`),
736		snapshotTestPreparer(checkSnapshotWithoutSource, preparerForSnapshot),
737		snapshotTestPreparer(checkSnapshotWithSourcePreferred, preparerForSnapshot),
738		snapshotTestPreparer(checkSnapshotPreferredWithSource, preparerForSnapshot),
739	)
740}
741
742// Test that bootclasspath_fragment works with sdk.
743func TestBasicSdkWithBootclasspathFragment(t *testing.T) {
744	t.Parallel()
745	android.GroupFixturePreparers(
746		prepareForSdkTestWithApex,
747		prepareForSdkTestWithJava,
748		java.PrepareForTestWithJavaDefaultModules,
749		android.FixtureMergeMockFs(android.MockFS{
750			"java/mybootlib.jar":                nil,
751			"hiddenapi/annotation-flags.csv":    nil,
752			"hiddenapi/index.csv":               nil,
753			"hiddenapi/metadata.csv":            nil,
754			"hiddenapi/signature-patterns.csv":  nil,
755			"hiddenapi/filtered-stub-flags.csv": nil,
756			"hiddenapi/filtered-flags.csv":      nil,
757		}),
758		android.FixtureWithRootAndroidBp(`
759		sdk {
760			name: "mysdk",
761			bootclasspath_fragments: ["mybootclasspathfragment"],
762		}
763
764		apex {
765			name: "myapex",
766			key: "myapex.key",
767			min_sdk_version: "1",
768			bootclasspath_fragments: ["mybootclasspathfragment"],
769		}
770
771		bootclasspath_fragment {
772			name: "mybootclasspathfragment",
773			image_name: "art",
774			contents: ["mybootlib"],
775			apex_available: ["myapex"],
776			hidden_api: {
777				split_packages: ["*"],
778			},
779		}
780
781		java_library {
782			name: "mybootlib",
783			apex_available: ["myapex"],
784			srcs: ["Test.java"],
785			system_modules: "none",
786			sdk_version: "none",
787			min_sdk_version: "1",
788			compile_dex: true,
789		}
790
791		prebuilt_bootclasspath_fragment {
792			name: "mybootclasspathfragment",
793			prefer: false,
794			visibility: ["//visibility:public"],
795			apex_available: [
796				"myapex",
797			],
798			image_name: "art",
799			contents: ["mybootlib"],
800			hidden_api: {
801				annotation_flags: "hiddenapi/annotation-flags.csv",
802				metadata: "hiddenapi/metadata.csv",
803				index: "hiddenapi/index.csv",
804				signature_patterns: "hiddenapi/signature-patterns.csv",
805				filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
806				filtered_flags: "hiddenapi/filtered-flags.csv",
807			},
808		}
809
810		java_import {
811			name: "mybootlib",
812			visibility: ["//visibility:public"],
813			apex_available: ["myapex"],
814			jars: ["java/mybootlib.jar"],
815		}
816	`),
817	).RunTest(t)
818}
819
820func TestSnapshotWithBootclasspathFragment_HiddenAPI(t *testing.T) {
821	t.Parallel()
822	result := android.GroupFixturePreparers(
823		prepareForSdkTestWithJava,
824		java.PrepareForTestWithJavaDefaultModules,
825		java.PrepareForTestWithJavaSdkLibraryFiles,
826		java.FixtureWithLastReleaseApis("mysdklibrary", "mynewlibrary"),
827		java.FixtureConfigureApexBootJars("myapex:mybootlib", "myapex:mynewlibrary"),
828		prepareForSdkTestWithApex,
829
830		// Add a platform_bootclasspath that depends on the fragment.
831		fixtureAddPlatformBootclasspathForBootclasspathFragment("myapex", "mybootclasspathfragment"),
832
833		android.PrepareForTestWithBuildFlag("RELEASE_HIDDEN_API_EXPORTABLE_STUBS", "true"),
834
835		android.MockFS{
836			"my-blocked.txt":                   nil,
837			"my-max-target-o-low-priority.txt": nil,
838			"my-max-target-p.txt":              nil,
839			"my-max-target-q.txt":              nil,
840			"my-max-target-r-low-priority.txt": nil,
841			"my-removed.txt":                   nil,
842			"my-unsupported-packages.txt":      nil,
843			"my-unsupported.txt":               nil,
844			"my-new-max-target-q.txt":          nil,
845		}.AddToFixture(),
846		android.FixtureWithRootAndroidBp(`
847			sdk {
848				name: "mysdk",
849				bootclasspath_fragments: ["mybootclasspathfragment"],
850			}
851
852			apex {
853				name: "myapex",
854				key: "myapex.key",
855				min_sdk_version: "1",
856				bootclasspath_fragments: ["mybootclasspathfragment"],
857			}
858
859			bootclasspath_fragment {
860				name: "mybootclasspathfragment",
861				apex_available: ["myapex"],
862				contents: ["mybootlib", "mynewlibrary"],
863				api: {
864					stub_libs: ["mysdklibrary"],
865				},
866				hidden_api: {
867					unsupported: [
868							"my-unsupported.txt",
869					],
870					removed: [
871							"my-removed.txt",
872					],
873					max_target_r_low_priority: [
874							"my-max-target-r-low-priority.txt",
875					],
876					max_target_q: [
877							"my-max-target-q.txt",
878					],
879					max_target_p: [
880							"my-max-target-p.txt",
881					],
882					max_target_o_low_priority: [
883							"my-max-target-o-low-priority.txt",
884					],
885					blocked: [
886							"my-blocked.txt",
887					],
888					unsupported_packages: [
889							"my-unsupported-packages.txt",
890					],
891					split_packages: ["sdklibrary"],
892					package_prefixes: ["sdklibrary.all.mine"],
893					single_packages: ["sdklibrary.mine"],
894				},
895			}
896
897			java_library {
898				name: "mybootlib",
899				apex_available: ["myapex"],
900				srcs: ["Test.java"],
901				system_modules: "none",
902				sdk_version: "none",
903				min_sdk_version: "1",
904				compile_dex: true,
905				permitted_packages: ["mybootlib"],
906			}
907
908			java_sdk_library {
909				name: "mysdklibrary",
910				srcs: ["Test.java"],
911				compile_dex: true,
912				public: {enabled: true},
913				permitted_packages: ["mysdklibrary"],
914				min_sdk_version: "current",
915				sdk_version: "current",
916			}
917
918			java_sdk_library {
919				name: "mynewlibrary",
920				apex_available: ["myapex"],
921				srcs: ["Test.java"],
922				min_sdk_version: "10",
923				compile_dex: true,
924				public: {enabled: true},
925				permitted_packages: ["mysdklibrary"],
926				hidden_api: {
927					max_target_q: [
928							"my-new-max-target-q.txt",
929					],
930					split_packages: ["sdklibrary", "newlibrary"],
931					package_prefixes: ["newlibrary.all.mine"],
932					single_packages: ["newlibrary.mine"],
933				},
934				sdk_version: "current",
935			}
936		`),
937	).RunTest(t)
938
939	// A preparer to update the test fixture used when processing an unpackage snapshot.
940	preparerForSnapshot := fixtureAddPrebuiltApexForBootclasspathFragment("myapex", "mybootclasspathfragment")
941
942	CheckSnapshot(t, result, "mysdk", "",
943		checkAndroidBpContents(`
944// This is auto-generated. DO NOT EDIT.
945
946apex_contributions_defaults {
947    name: "mysdk.contributions",
948    contents: [
949        "prebuilt_mynewlibrary",
950        "prebuilt_mysdklibrary",
951    ],
952}
953
954prebuilt_bootclasspath_fragment {
955    name: "mybootclasspathfragment",
956    prefer: false,
957    visibility: ["//visibility:public"],
958    apex_available: ["myapex"],
959    contents: [
960        "mybootlib",
961        "mynewlibrary",
962    ],
963    api: {
964        stub_libs: ["mysdklibrary"],
965    },
966    hidden_api: {
967        unsupported: ["hiddenapi/my-unsupported.txt"],
968        removed: ["hiddenapi/my-removed.txt"],
969        max_target_r_low_priority: ["hiddenapi/my-max-target-r-low-priority.txt"],
970        max_target_q: [
971            "hiddenapi/my-max-target-q.txt",
972            "hiddenapi/my-new-max-target-q.txt",
973        ],
974        max_target_p: ["hiddenapi/my-max-target-p.txt"],
975        max_target_o_low_priority: ["hiddenapi/my-max-target-o-low-priority.txt"],
976        blocked: ["hiddenapi/my-blocked.txt"],
977        unsupported_packages: ["hiddenapi/my-unsupported-packages.txt"],
978        annotation_flags: "hiddenapi/annotation-flags.csv",
979        metadata: "hiddenapi/metadata.csv",
980        index: "hiddenapi/index.csv",
981        signature_patterns: "hiddenapi/signature-patterns.csv",
982        filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
983        filtered_flags: "hiddenapi/filtered-flags.csv",
984    },
985}
986
987java_import {
988    name: "mybootlib",
989    prefer: false,
990    visibility: ["//visibility:public"],
991    apex_available: ["myapex"],
992    jars: ["java_boot_libs/snapshot/jars/are/invalid/mybootlib.jar"],
993    min_sdk_version: "1",
994    permitted_packages: ["mybootlib"],
995}
996
997java_sdk_library_import {
998    name: "mynewlibrary",
999    prefer: false,
1000    visibility: ["//visibility:public"],
1001    apex_available: ["myapex"],
1002    shared_library: true,
1003    compile_dex: true,
1004    permitted_packages: ["mysdklibrary"],
1005    public: {
1006        jars: ["sdk_library/public/mynewlibrary-stubs.jar"],
1007        stub_srcs: ["sdk_library/public/mynewlibrary_stub_sources"],
1008        current_api: "sdk_library/public/mynewlibrary.txt",
1009        removed_api: "sdk_library/public/mynewlibrary-removed.txt",
1010        sdk_version: "current",
1011    },
1012}
1013
1014java_sdk_library_import {
1015    name: "mysdklibrary",
1016    prefer: false,
1017    visibility: ["//visibility:public"],
1018    apex_available: ["//apex_available:platform"],
1019    shared_library: true,
1020    compile_dex: true,
1021    permitted_packages: ["mysdklibrary"],
1022    public: {
1023        jars: ["sdk_library/public/mysdklibrary-stubs.jar"],
1024        stub_srcs: ["sdk_library/public/mysdklibrary_stub_sources"],
1025        current_api: "sdk_library/public/mysdklibrary.txt",
1026        removed_api: "sdk_library/public/mysdklibrary-removed.txt",
1027        sdk_version: "current",
1028    },
1029}
1030`),
1031		checkAllCopyRules(`
1032my-unsupported.txt -> hiddenapi/my-unsupported.txt
1033my-removed.txt -> hiddenapi/my-removed.txt
1034my-max-target-r-low-priority.txt -> hiddenapi/my-max-target-r-low-priority.txt
1035my-max-target-q.txt -> hiddenapi/my-max-target-q.txt
1036my-new-max-target-q.txt -> hiddenapi/my-new-max-target-q.txt
1037my-max-target-p.txt -> hiddenapi/my-max-target-p.txt
1038my-max-target-o-low-priority.txt -> hiddenapi/my-max-target-o-low-priority.txt
1039my-blocked.txt -> hiddenapi/my-blocked.txt
1040my-unsupported-packages.txt -> hiddenapi/my-unsupported-packages.txt
1041.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/annotation-flags.csv -> hiddenapi/annotation-flags.csv
1042.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/metadata.csv -> hiddenapi/metadata.csv
1043.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/index.csv -> hiddenapi/index.csv
1044.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/signature-patterns.csv -> hiddenapi/signature-patterns.csv
1045.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/filtered-stub-flags.csv -> hiddenapi/filtered-stub-flags.csv
1046.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi/filtered-flags.csv -> hiddenapi/filtered-flags.csv
1047.intermediates/mysdk/common_os/empty -> java_boot_libs/snapshot/jars/are/invalid/mybootlib.jar
1048.intermediates/mynewlibrary.stubs.exportable/android_common/combined/mynewlibrary.stubs.exportable.jar -> sdk_library/public/mynewlibrary-stubs.jar
1049.intermediates/mynewlibrary.stubs.source/android_common/exportable/mynewlibrary.stubs.source_api.txt -> sdk_library/public/mynewlibrary.txt
1050.intermediates/mynewlibrary.stubs.source/android_common/exportable/mynewlibrary.stubs.source_removed.txt -> sdk_library/public/mynewlibrary-removed.txt
1051.intermediates/mysdklibrary.stubs.exportable/android_common/combined/mysdklibrary.stubs.exportable.jar -> sdk_library/public/mysdklibrary-stubs.jar
1052.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_api.txt -> sdk_library/public/mysdklibrary.txt
1053.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_removed.txt -> sdk_library/public/mysdklibrary-removed.txt
1054`),
1055		snapshotTestPreparer(checkSnapshotWithoutSource, preparerForSnapshot),
1056		snapshotTestPreparer(checkSnapshotWithSourcePreferred, preparerForSnapshot),
1057		snapshotTestPreparer(checkSnapshotPreferredWithSource, preparerForSnapshot),
1058	)
1059}
1060
1061func testSnapshotWithBootClasspathFragment_MinSdkVersion(t *testing.T, targetBuildRelease string,
1062	expectedSdkSnapshot string,
1063	expectedCopyRules string,
1064	expectedStubFlagsInputs []string,
1065	suffix string) {
1066
1067	result := android.GroupFixturePreparers(
1068		prepareForSdkTestWithJava,
1069		java.PrepareForTestWithJavaDefaultModules,
1070		java.PrepareForTestWithJavaSdkLibraryFiles,
1071		java.FixtureWithLastReleaseApis("mysdklibrary", "mynewsdklibrary"),
1072		java.FixtureConfigureApexBootJars("myapex:mysdklibrary", "myapex:mynewsdklibrary"),
1073		prepareForSdkTestWithApex,
1074
1075		// Add a platform_bootclasspath that depends on the fragment.
1076		fixtureAddPlatformBootclasspathForBootclasspathFragment("myapex", "mybootclasspathfragment"),
1077
1078		android.FixtureMergeEnv(map[string]string{
1079			"SOONG_SDK_SNAPSHOT_TARGET_BUILD_RELEASE": targetBuildRelease,
1080		}),
1081		android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
1082			variables.Platform_version_active_codenames = []string{"VanillaIceCream"}
1083		}),
1084
1085		android.PrepareForTestWithBuildFlag("RELEASE_HIDDEN_API_EXPORTABLE_STUBS", "true"),
1086
1087		android.FixtureWithRootAndroidBp(`
1088			sdk {
1089				name: "mysdk",
1090				apexes: ["myapex"],
1091			}
1092
1093			apex {
1094				name: "myapex",
1095				key: "myapex.key",
1096				min_sdk_version: "S",
1097				bootclasspath_fragments: ["mybootclasspathfragment"],
1098			}
1099
1100			bootclasspath_fragment {
1101				name: "mybootclasspathfragment",
1102				apex_available: ["myapex"],
1103				contents: [
1104					"mysdklibrary",
1105					"mynewsdklibrary",
1106				],
1107
1108				hidden_api: {
1109					split_packages: [],
1110				},
1111			}
1112
1113			java_sdk_library {
1114				name: "mysdklibrary",
1115				apex_available: ["myapex"],
1116				srcs: ["Test.java"],
1117				shared_library: false,
1118				public: {enabled: true},
1119				min_sdk_version: "S",
1120				sdk_version: "current",
1121			}
1122
1123			java_sdk_library {
1124				name: "mynewsdklibrary",
1125				apex_available: ["myapex"],
1126				srcs: ["Test.java"],
1127				compile_dex: true,
1128				public: {enabled: true},
1129				min_sdk_version: "Tiramisu",
1130				permitted_packages: ["mynewsdklibrary"],
1131				sdk_version: "current",
1132			}
1133		`),
1134	).RunTest(t)
1135
1136	bcpf := result.ModuleForTests(t, "mybootclasspathfragment", "android_common")
1137	rule := bcpf.Output("out/soong/.intermediates/mybootclasspathfragment/android_common/modular-hiddenapi" + suffix + "/stub-flags.csv")
1138	android.AssertPathsRelativeToTopEquals(t, "stub flags inputs", android.SortedUniqueStrings(expectedStubFlagsInputs), android.SortedUniquePaths(rule.Implicits))
1139
1140	CheckSnapshot(t, result, "mysdk", "",
1141		checkAndroidBpContents(expectedSdkSnapshot),
1142		checkAllCopyRules(expectedCopyRules),
1143	)
1144}
1145
1146func TestSnapshotWithBootClasspathFragment_MinSdkVersion(t *testing.T) {
1147	t.Parallel()
1148	t.Run("target S build", func(t *testing.T) {
1149		t.Parallel()
1150		expectedSnapshot := `
1151// This is auto-generated. DO NOT EDIT.
1152
1153prebuilt_bootclasspath_fragment {
1154    name: "mybootclasspathfragment",
1155    prefer: false,
1156    visibility: ["//visibility:public"],
1157    apex_available: ["myapex"],
1158    contents: ["mysdklibrary"],
1159    hidden_api: {
1160        annotation_flags: "hiddenapi/annotation-flags.csv",
1161        metadata: "hiddenapi/metadata.csv",
1162        index: "hiddenapi/index.csv",
1163        stub_flags: "hiddenapi/stub-flags.csv",
1164        all_flags: "hiddenapi/all-flags.csv",
1165    },
1166}
1167
1168java_sdk_library_import {
1169    name: "mysdklibrary",
1170    prefer: false,
1171    visibility: ["//visibility:public"],
1172    apex_available: ["myapex"],
1173    shared_library: false,
1174    public: {
1175        jars: ["sdk_library/public/mysdklibrary-stubs.jar"],
1176        stub_srcs: ["sdk_library/public/mysdklibrary_stub_sources"],
1177        current_api: "sdk_library/public/mysdklibrary.txt",
1178        removed_api: "sdk_library/public/mysdklibrary-removed.txt",
1179        sdk_version: "current",
1180    },
1181}
1182`
1183		expectedCopyRules := `
1184.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi-for-sdk-snapshot/annotation-flags.csv -> hiddenapi/annotation-flags.csv
1185.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi-for-sdk-snapshot/metadata.csv -> hiddenapi/metadata.csv
1186.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi-for-sdk-snapshot/index.csv -> hiddenapi/index.csv
1187.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi-for-sdk-snapshot/stub-flags.csv -> hiddenapi/stub-flags.csv
1188.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi-for-sdk-snapshot/all-flags.csv -> hiddenapi/all-flags.csv
1189.intermediates/mysdklibrary.stubs.exportable/android_common/combined/mysdklibrary.stubs.exportable.jar -> sdk_library/public/mysdklibrary-stubs.jar
1190.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_api.txt -> sdk_library/public/mysdklibrary.txt
1191.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_removed.txt -> sdk_library/public/mysdklibrary-removed.txt
1192`
1193
1194		// On S the stub flags should only be generated from mysdklibrary as mynewsdklibrary is not part
1195		// of the snapshot.
1196		expectedStubFlagsInputs := []string{
1197			"out/soong/.intermediates/mysdklibrary.stubs.exportable/android_common/dex/mysdklibrary.stubs.exportable.jar",
1198			"out/soong/.intermediates/mysdklibrary.impl/android_common/aligned/mysdklibrary.jar",
1199		}
1200
1201		testSnapshotWithBootClasspathFragment_MinSdkVersion(t, "S",
1202			expectedSnapshot, expectedCopyRules, expectedStubFlagsInputs, "-for-sdk-snapshot")
1203	})
1204
1205	t.Run("target-Tiramisu-build", func(t *testing.T) {
1206		t.Parallel()
1207		expectedSnapshot := `
1208// This is auto-generated. DO NOT EDIT.
1209
1210prebuilt_bootclasspath_fragment {
1211    name: "mybootclasspathfragment",
1212    prefer: false,
1213    visibility: ["//visibility:public"],
1214    apex_available: ["myapex"],
1215    contents: [
1216        "mysdklibrary",
1217        "mynewsdklibrary",
1218    ],
1219    hidden_api: {
1220        annotation_flags: "hiddenapi/annotation-flags.csv",
1221        metadata: "hiddenapi/metadata.csv",
1222        index: "hiddenapi/index.csv",
1223        signature_patterns: "hiddenapi/signature-patterns.csv",
1224        filtered_stub_flags: "hiddenapi/filtered-stub-flags.csv",
1225        filtered_flags: "hiddenapi/filtered-flags.csv",
1226    },
1227}
1228
1229java_sdk_library_import {
1230    name: "mysdklibrary",
1231    prefer: false,
1232    visibility: ["//visibility:public"],
1233    apex_available: ["myapex"],
1234    shared_library: false,
1235    public: {
1236        jars: ["sdk_library/public/mysdklibrary-stubs.jar"],
1237        stub_srcs: ["sdk_library/public/mysdklibrary_stub_sources"],
1238        current_api: "sdk_library/public/mysdklibrary.txt",
1239        removed_api: "sdk_library/public/mysdklibrary-removed.txt",
1240        sdk_version: "current",
1241    },
1242}
1243
1244java_sdk_library_import {
1245    name: "mynewsdklibrary",
1246    prefer: false,
1247    visibility: ["//visibility:public"],
1248    apex_available: ["myapex"],
1249    shared_library: true,
1250    compile_dex: true,
1251    permitted_packages: ["mynewsdklibrary"],
1252    public: {
1253        jars: ["sdk_library/public/mynewsdklibrary-stubs.jar"],
1254        stub_srcs: ["sdk_library/public/mynewsdklibrary_stub_sources"],
1255        current_api: "sdk_library/public/mynewsdklibrary.txt",
1256        removed_api: "sdk_library/public/mynewsdklibrary-removed.txt",
1257        sdk_version: "current",
1258    },
1259}
1260`
1261		expectedCopyRules := `
1262.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/annotation-flags.csv -> hiddenapi/annotation-flags.csv
1263.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/metadata.csv -> hiddenapi/metadata.csv
1264.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/index.csv -> hiddenapi/index.csv
1265.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/signature-patterns.csv -> hiddenapi/signature-patterns.csv
1266.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/filtered-stub-flags.csv -> hiddenapi/filtered-stub-flags.csv
1267.intermediates/mybootclasspathfragment/android_common_myapex/modular-hiddenapi/filtered-flags.csv -> hiddenapi/filtered-flags.csv
1268.intermediates/mysdklibrary.stubs.exportable/android_common/combined/mysdklibrary.stubs.exportable.jar -> sdk_library/public/mysdklibrary-stubs.jar
1269.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_api.txt -> sdk_library/public/mysdklibrary.txt
1270.intermediates/mysdklibrary.stubs.source/android_common/exportable/mysdklibrary.stubs.source_removed.txt -> sdk_library/public/mysdklibrary-removed.txt
1271.intermediates/mynewsdklibrary.stubs.exportable/android_common/combined/mynewsdklibrary.stubs.exportable.jar -> sdk_library/public/mynewsdklibrary-stubs.jar
1272.intermediates/mynewsdklibrary.stubs.source/android_common/exportable/mynewsdklibrary.stubs.source_api.txt -> sdk_library/public/mynewsdklibrary.txt
1273.intermediates/mynewsdklibrary.stubs.source/android_common/exportable/mynewsdklibrary.stubs.source_removed.txt -> sdk_library/public/mynewsdklibrary-removed.txt
1274`
1275
1276		// On tiramisu the stub flags should be generated from both mynewsdklibrary and mysdklibrary as
1277		// they are both part of the snapshot.
1278		expectedStubFlagsInputs := []string{
1279			"out/soong/.intermediates/mynewsdklibrary.stubs.exportable/android_common/dex/mynewsdklibrary.stubs.exportable.jar",
1280			"out/soong/.intermediates/mynewsdklibrary.impl/android_common/aligned/mynewsdklibrary.jar",
1281			"out/soong/.intermediates/mysdklibrary.stubs.exportable/android_common/dex/mysdklibrary.stubs.exportable.jar",
1282			"out/soong/.intermediates/mysdklibrary.impl/android_common/aligned/mysdklibrary.jar",
1283		}
1284
1285		testSnapshotWithBootClasspathFragment_MinSdkVersion(t, "Tiramisu",
1286			expectedSnapshot, expectedCopyRules, expectedStubFlagsInputs, "")
1287	})
1288}
1289
1290func TestSnapshotWithEmptyBootClasspathFragment(t *testing.T) {
1291	t.Parallel()
1292	result := android.GroupFixturePreparers(
1293		prepareForSdkTestWithJava,
1294		java.PrepareForTestWithJavaDefaultModules,
1295		java.PrepareForTestWithJavaSdkLibraryFiles,
1296		java.FixtureWithLastReleaseApis("mysdklibrary", "mynewsdklibrary"),
1297		java.FixtureConfigureApexBootJars("myapex:mysdklibrary", "myapex:mynewsdklibrary"),
1298		prepareForSdkTestWithApex,
1299		// Add a platform_bootclasspath that depends on the fragment.
1300		fixtureAddPlatformBootclasspathForBootclasspathFragment("myapex", "mybootclasspathfragment"),
1301		android.FixtureMergeEnv(map[string]string{
1302			"SOONG_SDK_SNAPSHOT_TARGET_BUILD_RELEASE": "S",
1303		}),
1304		android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
1305			variables.Platform_version_active_codenames = []string{"VanillaIceCream"}
1306		}),
1307		android.FixtureWithRootAndroidBp(`
1308			sdk {
1309				name: "mysdk",
1310				apexes: ["myapex"],
1311			}
1312			apex {
1313				name: "myapex",
1314				key: "myapex.key",
1315				min_sdk_version: "S",
1316				bootclasspath_fragments: ["mybootclasspathfragment"],
1317			}
1318			bootclasspath_fragment {
1319				name: "mybootclasspathfragment",
1320				apex_available: ["myapex"],
1321				contents: ["mysdklibrary", "mynewsdklibrary"],
1322				hidden_api: {
1323					split_packages: [],
1324				},
1325			}
1326			java_sdk_library {
1327				name: "mysdklibrary",
1328				apex_available: ["myapex"],
1329				srcs: ["Test.java"],
1330				shared_library: false,
1331				public: {enabled: true},
1332				min_sdk_version: "Tiramisu",
1333				sdk_version: "current",
1334			}
1335			java_sdk_library {
1336				name: "mynewsdklibrary",
1337				apex_available: ["myapex"],
1338				srcs: ["Test.java"],
1339				compile_dex: true,
1340				public: {enabled: true},
1341				min_sdk_version: "Tiramisu",
1342				permitted_packages: ["mynewsdklibrary"],
1343				sdk_version: "current",
1344			}
1345		`),
1346	).RunTest(t)
1347
1348	CheckSnapshot(t, result, "mysdk", "", checkAndroidBpContents(`// This is auto-generated. DO NOT EDIT.`))
1349}
1350