blob: 22f7c9f3526a1c0c1c735c6c9df4b4de80d82595 [file] [log] [blame]
Colin Crossd00350c2017-11-17 10:55:38 -08001// Copyright 2017 Google Inc. All rights reserved.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
Colin Cross74d1ec02015-04-28 13:30:13 -070015package cc
16
17import (
Jeff Gaston294356f2017-09-27 17:05:30 -070018 "fmt"
Jiyong Park6a43f042017-10-12 23:05:00 +090019 "os"
Colin Cross74d1ec02015-04-28 13:30:13 -070020 "reflect"
Paul Duffin3cb603e2021-02-19 13:57:10 +000021 "regexp"
Cory Barker9cfcf6d2022-07-22 17:22:02 +000022 "runtime"
Colin Crossdd81e672024-10-17 14:01:12 -070023 "slices"
Jeff Gaston294356f2017-09-27 17:05:30 -070024 "strings"
Colin Cross74d1ec02015-04-28 13:30:13 -070025 "testing"
Colin Crosse1bb5d02019-09-24 14:55:04 -070026
Vinh Tran367d89d2023-04-28 11:21:25 -040027 "android/soong/aidl_library"
Colin Crosse1bb5d02019-09-24 14:55:04 -070028 "android/soong/android"
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +090029
30 "github.com/google/blueprint"
Colin Cross74d1ec02015-04-28 13:30:13 -070031)
32
Yu Liue4312402023-01-18 09:15:31 -080033func init() {
34 registerTestMutators(android.InitRegistrationContext)
35}
36
Jiyong Park6a43f042017-10-12 23:05:00 +090037func TestMain(m *testing.M) {
Paul Duffinc3e6ce02021-03-22 23:21:32 +000038 os.Exit(m.Run())
Jiyong Park6a43f042017-10-12 23:05:00 +090039}
40
Paul Duffin2e6f90e2021-03-22 23:20:25 +000041var prepareForCcTest = android.GroupFixturePreparers(
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +090042 PrepareForIntegrationTestWithCc,
43 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
44 variables.VendorApiLevel = StringPtr("202404")
45 }),
46)
47
Yu Liue4312402023-01-18 09:15:31 -080048var apexVariationName = "apex28"
49var apexVersion = "28"
50
51func registerTestMutators(ctx android.RegistrationContext) {
52 ctx.PostDepsMutators(func(ctx android.RegisterMutatorsContext) {
Colin Crossd27205e2024-09-12 22:41:37 -070053 ctx.Transition("apex", &testApexTransitionMutator{})
Yu Liue4312402023-01-18 09:15:31 -080054 })
55}
56
Colin Crossd27205e2024-09-12 22:41:37 -070057type testApexTransitionMutator struct{}
58
59func (t *testApexTransitionMutator) Split(ctx android.BaseModuleContext) []string {
60 return []string{apexVariationName}
61}
62
63func (t *testApexTransitionMutator) OutgoingTransition(ctx android.OutgoingTransitionContext, sourceVariation string) string {
64 return sourceVariation
65}
66
67func (t *testApexTransitionMutator) IncomingTransition(ctx android.IncomingTransitionContext, incomingVariation string) string {
68 return incomingVariation
69}
70
71func (t *testApexTransitionMutator) Mutate(ctx android.BottomUpMutatorContext, variation string) {
Yu Liue4312402023-01-18 09:15:31 -080072 apexInfo := android.ApexInfo{
73 ApexVariationName: apexVariationName,
74 MinSdkVersion: android.ApiLevelForTest(apexVersion),
75 }
Colin Crossd27205e2024-09-12 22:41:37 -070076 android.SetProvider(ctx, android.ApexInfoProvider, apexInfo)
Yu Liue4312402023-01-18 09:15:31 -080077}
78
Paul Duffin8567f222021-03-23 00:02:06 +000079// testCcWithConfig runs tests using the prepareForCcTest
Paul Duffin02a3d652021-02-24 18:51:54 +000080//
81// See testCc for an explanation as to how to stop using this deprecated method.
82//
83// deprecated
Colin Cross98be1bb2019-12-13 20:41:13 -080084func testCcWithConfig(t *testing.T, config android.Config) *android.TestContext {
Colin Crosse1bb5d02019-09-24 14:55:04 -070085 t.Helper()
Paul Duffin8567f222021-03-23 00:02:06 +000086 result := prepareForCcTest.RunTestWithConfig(t, config)
Paul Duffin02a3d652021-02-24 18:51:54 +000087 return result.TestContext
Jiyong Park6a43f042017-10-12 23:05:00 +090088}
89
Paul Duffin8567f222021-03-23 00:02:06 +000090// testCc runs tests using the prepareForCcTest
Paul Duffin02a3d652021-02-24 18:51:54 +000091//
Paul Duffin8567f222021-03-23 00:02:06 +000092// Do not add any new usages of this, instead use the prepareForCcTest directly as it makes it much
Paul Duffin02a3d652021-02-24 18:51:54 +000093// easier to customize the test behavior.
94//
95// If it is necessary to customize the behavior of an existing test that uses this then please first
Paul Duffin8567f222021-03-23 00:02:06 +000096// convert the test to using prepareForCcTest first and then in a following change add the
Paul Duffin02a3d652021-02-24 18:51:54 +000097// appropriate fixture preparers. Keeping the conversion change separate makes it easy to verify
98// that it did not change the test behavior unexpectedly.
99//
100// deprecated
Logan Chienf3511742017-10-31 18:04:35 +0800101func testCc(t *testing.T, bp string) *android.TestContext {
Logan Chiend3c59a22018-03-29 14:08:15 +0800102 t.Helper()
Paul Duffin8567f222021-03-23 00:02:06 +0000103 result := prepareForCcTest.RunTestWithBp(t, bp)
Paul Duffin02a3d652021-02-24 18:51:54 +0000104 return result.TestContext
Logan Chienf3511742017-10-31 18:04:35 +0800105}
106
Paul Duffin8567f222021-03-23 00:02:06 +0000107// testCcErrorWithConfig runs tests using the prepareForCcTest
Paul Duffin02a3d652021-02-24 18:51:54 +0000108//
109// See testCc for an explanation as to how to stop using this deprecated method.
110//
111// deprecated
Justin Yun5f7f7e82019-11-18 19:52:14 +0900112func testCcErrorWithConfig(t *testing.T, pattern string, config android.Config) {
Logan Chiend3c59a22018-03-29 14:08:15 +0800113 t.Helper()
Logan Chienf3511742017-10-31 18:04:35 +0800114
Paul Duffin8567f222021-03-23 00:02:06 +0000115 prepareForCcTest.
Paul Duffin02a3d652021-02-24 18:51:54 +0000116 ExtendWithErrorHandler(android.FixtureExpectsAtLeastOneErrorMatchingPattern(pattern)).
117 RunTestWithConfig(t, config)
Logan Chienf3511742017-10-31 18:04:35 +0800118}
119
Paul Duffin8567f222021-03-23 00:02:06 +0000120// testCcError runs tests using the prepareForCcTest
Paul Duffin02a3d652021-02-24 18:51:54 +0000121//
122// See testCc for an explanation as to how to stop using this deprecated method.
123//
124// deprecated
Justin Yun5f7f7e82019-11-18 19:52:14 +0900125func testCcError(t *testing.T, pattern string, bp string) {
Jooyung Han479ca172020-10-19 18:51:07 +0900126 t.Helper()
Paul Duffinc3e6ce02021-03-22 23:21:32 +0000127 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Justin Yun5f7f7e82019-11-18 19:52:14 +0900128 testCcErrorWithConfig(t, pattern, config)
129 return
130}
131
Logan Chienf3511742017-10-31 18:04:35 +0800132const (
Colin Cross7113d202019-11-20 16:39:12 -0800133 coreVariant = "android_arm64_armv8-a_shared"
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +0900134 vendorVariant = "android_vendor_arm64_armv8-a_shared"
135 productVariant = "android_product_arm64_armv8-a_shared"
Colin Crossfb0c16e2019-11-20 17:12:35 -0800136 recoveryVariant = "android_recovery_arm64_armv8-a_shared"
Logan Chienf3511742017-10-31 18:04:35 +0800137)
138
Paul Duffindb462dd2021-03-21 22:01:55 +0000139// Test that the PrepareForTestWithCcDefaultModules provides all the files that it uses by
140// running it in a fixture that requires all source files to exist.
141func TestPrepareForTestWithCcDefaultModules(t *testing.T) {
142 android.GroupFixturePreparers(
143 PrepareForTestWithCcDefaultModules,
144 android.PrepareForTestDisallowNonExistentPaths,
145 ).RunTest(t)
146}
147
Jiyong Park6a43f042017-10-12 23:05:00 +0900148func TestVendorSrc(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400149 t.Parallel()
Jiyong Park6a43f042017-10-12 23:05:00 +0900150 ctx := testCc(t, `
151 cc_library {
152 name: "libTest",
153 srcs: ["foo.c"],
Yi Konge7fe9912019-06-02 00:53:50 -0700154 no_libcrt: true,
Logan Chienf3511742017-10-31 18:04:35 +0800155 nocrt: true,
156 system_shared_libs: [],
Jiyong Park6a43f042017-10-12 23:05:00 +0900157 vendor_available: true,
158 target: {
159 vendor: {
160 srcs: ["bar.c"],
161 },
162 },
163 }
Jiyong Park6a43f042017-10-12 23:05:00 +0900164 `)
165
Logan Chienf3511742017-10-31 18:04:35 +0800166 ld := ctx.ModuleForTests("libTest", vendorVariant).Rule("ld")
Jiyong Park6a43f042017-10-12 23:05:00 +0900167 var objs []string
168 for _, o := range ld.Inputs {
169 objs = append(objs, o.Base())
170 }
Colin Cross95d33fe2018-01-03 13:40:46 -0800171 if len(objs) != 2 || objs[0] != "foo.o" || objs[1] != "bar.o" {
Jiyong Park6a43f042017-10-12 23:05:00 +0900172 t.Errorf("inputs of libTest must be []string{\"foo.o\", \"bar.o\"}, but was %#v.", objs)
173 }
174}
175
Justin Yun7f99ec72021-04-12 13:19:28 +0900176func checkInstallPartition(t *testing.T, ctx *android.TestContext, name, variant, expected string) {
177 mod := ctx.ModuleForTests(name, variant).Module().(*Module)
178 partitionDefined := false
179 checkPartition := func(specific bool, partition string) {
180 if specific {
181 if expected != partition && !partitionDefined {
182 // The variant is installed to the 'partition'
183 t.Errorf("%s variant of %q must not be installed to %s partition", variant, name, partition)
184 }
185 partitionDefined = true
186 } else {
187 // The variant is not installed to the 'partition'
188 if expected == partition {
189 t.Errorf("%s variant of %q must be installed to %s partition", variant, name, partition)
190 }
191 }
192 }
193 socSpecific := func(m *Module) bool {
Colin Crossea30d852023-11-29 16:00:16 -0800194 return m.SocSpecific() || m.InstallInVendor()
Justin Yun7f99ec72021-04-12 13:19:28 +0900195 }
196 deviceSpecific := func(m *Module) bool {
Colin Crossea30d852023-11-29 16:00:16 -0800197 return m.DeviceSpecific() || m.InstallInOdm()
Justin Yun7f99ec72021-04-12 13:19:28 +0900198 }
199 productSpecific := func(m *Module) bool {
Colin Crossea30d852023-11-29 16:00:16 -0800200 return m.ProductSpecific() || m.InstallInProduct()
Justin Yun7f99ec72021-04-12 13:19:28 +0900201 }
202 systemExtSpecific := func(m *Module) bool {
203 return m.SystemExtSpecific()
204 }
205 checkPartition(socSpecific(mod), "vendor")
206 checkPartition(deviceSpecific(mod), "odm")
207 checkPartition(productSpecific(mod), "product")
208 checkPartition(systemExtSpecific(mod), "system_ext")
209 if !partitionDefined && expected != "system" {
210 t.Errorf("%s variant of %q is expected to be installed to %s partition,"+
211 " but installed to system partition", variant, name, expected)
212 }
213}
214
215func TestInstallPartition(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400216 t.Parallel()
Justin Yun7f99ec72021-04-12 13:19:28 +0900217 t.Helper()
218 ctx := prepareForCcTest.RunTestWithBp(t, `
219 cc_library {
220 name: "libsystem",
221 }
222 cc_library {
223 name: "libsystem_ext",
224 system_ext_specific: true,
225 }
226 cc_library {
227 name: "libproduct",
228 product_specific: true,
229 }
230 cc_library {
231 name: "libvendor",
232 vendor: true,
233 }
234 cc_library {
235 name: "libodm",
236 device_specific: true,
237 }
238 cc_library {
239 name: "liball_available",
240 vendor_available: true,
241 product_available: true,
242 }
243 cc_library {
244 name: "libsystem_ext_all_available",
245 system_ext_specific: true,
246 vendor_available: true,
247 product_available: true,
248 }
249 cc_library {
250 name: "liball_available_odm",
251 odm_available: true,
252 product_available: true,
253 }
254 cc_library {
255 name: "libproduct_vendoravailable",
256 product_specific: true,
257 vendor_available: true,
258 }
259 cc_library {
260 name: "libproduct_odmavailable",
261 product_specific: true,
262 odm_available: true,
263 }
264 `).TestContext
265
266 checkInstallPartition(t, ctx, "libsystem", coreVariant, "system")
267 checkInstallPartition(t, ctx, "libsystem_ext", coreVariant, "system_ext")
268 checkInstallPartition(t, ctx, "libproduct", productVariant, "product")
269 checkInstallPartition(t, ctx, "libvendor", vendorVariant, "vendor")
270 checkInstallPartition(t, ctx, "libodm", vendorVariant, "odm")
271
272 checkInstallPartition(t, ctx, "liball_available", coreVariant, "system")
273 checkInstallPartition(t, ctx, "liball_available", productVariant, "product")
274 checkInstallPartition(t, ctx, "liball_available", vendorVariant, "vendor")
275
276 checkInstallPartition(t, ctx, "libsystem_ext_all_available", coreVariant, "system_ext")
277 checkInstallPartition(t, ctx, "libsystem_ext_all_available", productVariant, "product")
278 checkInstallPartition(t, ctx, "libsystem_ext_all_available", vendorVariant, "vendor")
279
280 checkInstallPartition(t, ctx, "liball_available_odm", coreVariant, "system")
281 checkInstallPartition(t, ctx, "liball_available_odm", productVariant, "product")
282 checkInstallPartition(t, ctx, "liball_available_odm", vendorVariant, "odm")
283
284 checkInstallPartition(t, ctx, "libproduct_vendoravailable", productVariant, "product")
285 checkInstallPartition(t, ctx, "libproduct_vendoravailable", vendorVariant, "vendor")
286
287 checkInstallPartition(t, ctx, "libproduct_odmavailable", productVariant, "product")
288 checkInstallPartition(t, ctx, "libproduct_odmavailable", vendorVariant, "odm")
289}
290
Colin Crossf61d03d2023-11-02 16:56:39 -0700291func checkWriteFileOutput(t *testing.T, ctx *android.TestContext, params android.TestingBuildParams, expected []string) {
Jooyung Han2216fb12019-11-06 16:46:15 +0900292 t.Helper()
Colin Crossf61d03d2023-11-02 16:56:39 -0700293 content := android.ContentFromFileRuleForTests(t, ctx, params)
Colin Crosscf371cc2020-11-13 11:48:42 -0800294 actual := strings.FieldsFunc(content, func(r rune) bool { return r == '\n' })
Jooyung Han2216fb12019-11-06 16:46:15 +0900295 assertArrayString(t, actual, expected)
296}
297
Chris Parsons79d66a52020-06-05 17:26:16 -0400298func TestDataLibs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400299 t.Parallel()
Chris Parsons79d66a52020-06-05 17:26:16 -0400300 bp := `
301 cc_test_library {
302 name: "test_lib",
303 srcs: ["test_lib.cpp"],
304 gtest: false,
305 }
306
307 cc_test {
308 name: "main_test",
309 data_libs: ["test_lib"],
310 gtest: false,
311 }
Chris Parsons216e10a2020-07-09 17:12:52 -0400312 `
Chris Parsons79d66a52020-06-05 17:26:16 -0400313
Paul Duffinc3e6ce02021-03-22 23:21:32 +0000314 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Chris Parsons79d66a52020-06-05 17:26:16 -0400315
316 ctx := testCcWithConfig(t, config)
mrziwangabdb2932024-06-18 12:43:41 -0700317 testingModule := ctx.ModuleForTests("main_test", "android_arm_armv7-a-neon")
318 testBinary := testingModule.Module().(*Module).linker.(*testBinary)
Yu Liu51c22312024-08-20 23:56:15 +0000319 outputFiles := testingModule.OutputFiles(ctx, t, "")
Chris Parsons79d66a52020-06-05 17:26:16 -0400320 if len(outputFiles) != 1 {
321 t.Errorf("expected exactly one output file. output files: [%s]", outputFiles)
322 return
323 }
324 if len(testBinary.dataPaths()) != 1 {
Colin Cross7e2e7942023-11-16 12:56:02 -0800325 t.Errorf("expected exactly one test data file. test data files: [%v]", testBinary.dataPaths())
Chris Parsons79d66a52020-06-05 17:26:16 -0400326 return
327 }
328
329 outputPath := outputFiles[0].String()
Chris Parsons216e10a2020-07-09 17:12:52 -0400330 testBinaryPath := testBinary.dataPaths()[0].SrcPath.String()
Chris Parsons79d66a52020-06-05 17:26:16 -0400331
332 if !strings.HasSuffix(outputPath, "/main_test") {
333 t.Errorf("expected test output file to be 'main_test', but was '%s'", outputPath)
334 return
335 }
336 if !strings.HasSuffix(testBinaryPath, "/test_lib.so") {
337 t.Errorf("expected test data file to be 'test_lib.so', but was '%s'", testBinaryPath)
338 return
339 }
340}
341
Chris Parsons216e10a2020-07-09 17:12:52 -0400342func TestDataLibsRelativeInstallPath(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400343 t.Parallel()
Chris Parsons216e10a2020-07-09 17:12:52 -0400344 bp := `
345 cc_test_library {
346 name: "test_lib",
347 srcs: ["test_lib.cpp"],
348 relative_install_path: "foo/bar/baz",
349 gtest: false,
350 }
351
Ivan Lozano4e5f07d2021-11-04 14:09:38 -0400352 cc_binary {
353 name: "test_bin",
354 relative_install_path: "foo/bar/baz",
355 compile_multilib: "both",
356 }
357
Chris Parsons216e10a2020-07-09 17:12:52 -0400358 cc_test {
359 name: "main_test",
360 data_libs: ["test_lib"],
Ivan Lozano4e5f07d2021-11-04 14:09:38 -0400361 data_bins: ["test_bin"],
Chris Parsons216e10a2020-07-09 17:12:52 -0400362 gtest: false,
363 }
364 `
365
Paul Duffinc3e6ce02021-03-22 23:21:32 +0000366 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Chris Parsons216e10a2020-07-09 17:12:52 -0400367
368 ctx := testCcWithConfig(t, config)
mrziwangabdb2932024-06-18 12:43:41 -0700369 testingModule := ctx.ModuleForTests("main_test", "android_arm_armv7-a-neon")
370 module := testingModule.Module()
Chris Parsons216e10a2020-07-09 17:12:52 -0400371 testBinary := module.(*Module).linker.(*testBinary)
Yu Liu51c22312024-08-20 23:56:15 +0000372 outputFiles := testingModule.OutputFiles(ctx, t, "")
Chris Parsons216e10a2020-07-09 17:12:52 -0400373 if len(outputFiles) != 1 {
Ivan Lozano4e5f07d2021-11-04 14:09:38 -0400374 t.Fatalf("expected exactly one output file. output files: [%s]", outputFiles)
Chris Parsons216e10a2020-07-09 17:12:52 -0400375 }
Ivan Lozano4e5f07d2021-11-04 14:09:38 -0400376 if len(testBinary.dataPaths()) != 2 {
Colin Cross7e2e7942023-11-16 12:56:02 -0800377 t.Fatalf("expected exactly one test data file. test data files: [%v]", testBinary.dataPaths())
Chris Parsons216e10a2020-07-09 17:12:52 -0400378 }
379
380 outputPath := outputFiles[0].String()
Chris Parsons216e10a2020-07-09 17:12:52 -0400381
382 if !strings.HasSuffix(outputPath, "/main_test") {
383 t.Errorf("expected test output file to be 'main_test', but was '%s'", outputPath)
384 }
Yu Liue70976d2024-10-15 20:45:35 +0000385 entries := android.AndroidMkInfoForTest(t, ctx, module).PrimaryInfo
Chris Parsons216e10a2020-07-09 17:12:52 -0400386 if !strings.HasSuffix(entries.EntryMap["LOCAL_TEST_DATA"][0], ":test_lib.so:foo/bar/baz") {
387 t.Errorf("expected LOCAL_TEST_DATA to end with `:test_lib.so:foo/bar/baz`,"+
Chris Parsons1f6d90f2020-06-17 16:10:42 -0400388 " but was '%s'", entries.EntryMap["LOCAL_TEST_DATA"][0])
Chris Parsons216e10a2020-07-09 17:12:52 -0400389 }
Ivan Lozano4e5f07d2021-11-04 14:09:38 -0400390 if !strings.HasSuffix(entries.EntryMap["LOCAL_TEST_DATA"][1], ":test_bin:foo/bar/baz") {
391 t.Errorf("expected LOCAL_TEST_DATA to end with `:test_bin:foo/bar/baz`,"+
392 " but was '%s'", entries.EntryMap["LOCAL_TEST_DATA"][1])
393 }
Chris Parsons216e10a2020-07-09 17:12:52 -0400394}
395
Trevor Radcliffef389cb42022-03-24 21:06:14 +0000396func TestTestBinaryTestSuites(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400397 t.Parallel()
Trevor Radcliffef389cb42022-03-24 21:06:14 +0000398 bp := `
399 cc_test {
400 name: "main_test",
401 srcs: ["main_test.cpp"],
402 test_suites: [
403 "suite_1",
404 "suite_2",
405 ],
406 gtest: false,
407 }
408 `
409
410 ctx := prepareForCcTest.RunTestWithBp(t, bp).TestContext
411 module := ctx.ModuleForTests("main_test", "android_arm_armv7-a-neon").Module()
412
Yu Liue70976d2024-10-15 20:45:35 +0000413 entries := android.AndroidMkInfoForTest(t, ctx, module).PrimaryInfo
Trevor Radcliffef389cb42022-03-24 21:06:14 +0000414 compatEntries := entries.EntryMap["LOCAL_COMPATIBILITY_SUITE"]
415 if len(compatEntries) != 2 {
416 t.Errorf("expected two elements in LOCAL_COMPATIBILITY_SUITE. got %d", len(compatEntries))
417 }
418 if compatEntries[0] != "suite_1" {
419 t.Errorf("expected LOCAL_COMPATIBILITY_SUITE to be`suite_1`,"+
420 " but was '%s'", compatEntries[0])
421 }
422 if compatEntries[1] != "suite_2" {
423 t.Errorf("expected LOCAL_COMPATIBILITY_SUITE to be`suite_2`,"+
424 " but was '%s'", compatEntries[1])
425 }
426}
427
428func TestTestLibraryTestSuites(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400429 t.Parallel()
Trevor Radcliffef389cb42022-03-24 21:06:14 +0000430 bp := `
431 cc_test_library {
432 name: "main_test_lib",
433 srcs: ["main_test_lib.cpp"],
434 test_suites: [
435 "suite_1",
436 "suite_2",
437 ],
438 gtest: false,
439 }
440 `
441
442 ctx := prepareForCcTest.RunTestWithBp(t, bp).TestContext
443 module := ctx.ModuleForTests("main_test_lib", "android_arm_armv7-a-neon_shared").Module()
444
Yu Liue70976d2024-10-15 20:45:35 +0000445 entries := android.AndroidMkInfoForTest(t, ctx, module).PrimaryInfo
Trevor Radcliffef389cb42022-03-24 21:06:14 +0000446 compatEntries := entries.EntryMap["LOCAL_COMPATIBILITY_SUITE"]
447 if len(compatEntries) != 2 {
448 t.Errorf("expected two elements in LOCAL_COMPATIBILITY_SUITE. got %d", len(compatEntries))
449 }
450 if compatEntries[0] != "suite_1" {
451 t.Errorf("expected LOCAL_COMPATIBILITY_SUITE to be`suite_1`,"+
452 " but was '%s'", compatEntries[0])
453 }
454 if compatEntries[1] != "suite_2" {
455 t.Errorf("expected LOCAL_COMPATIBILITY_SUITE to be`suite_2`,"+
456 " but was '%s'", compatEntries[1])
457 }
458}
459
Jooyung Hana70f0672019-01-18 15:20:43 +0900460func TestDoubleLoadbleDep(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400461 t.Parallel()
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +0900462 // okay to link : LLNDK -> double_loadable
Jooyung Hana70f0672019-01-18 15:20:43 +0900463 testCc(t, `
464 cc_library {
465 name: "libllndk",
466 shared_libs: ["libdoubleloadable"],
Colin Cross203b4212021-04-26 17:19:41 -0700467 llndk: {
468 symbol_file: "libllndk.map.txt",
469 }
Jooyung Hana70f0672019-01-18 15:20:43 +0900470 }
471
472 cc_library {
473 name: "libdoubleloadable",
474 vendor_available: true,
Justin Yun63e9ec72020-10-29 16:49:43 +0900475 product_available: true,
Jooyung Hana70f0672019-01-18 15:20:43 +0900476 double_loadable: true,
477 }
478 `)
Jooyung Hana70f0672019-01-18 15:20:43 +0900479 // okay to link : double_loadable -> double_loadable
480 testCc(t, `
481 cc_library {
482 name: "libdoubleloadable1",
483 shared_libs: ["libdoubleloadable2"],
484 vendor_available: true,
485 double_loadable: true,
486 }
487
488 cc_library {
489 name: "libdoubleloadable2",
490 vendor_available: true,
491 double_loadable: true,
492 }
493 `)
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +0900494 // okay to link : double_loadable -> double_loadable
Jooyung Hana70f0672019-01-18 15:20:43 +0900495 testCc(t, `
496 cc_library {
497 name: "libdoubleloadable",
498 vendor_available: true,
Justin Yun63e9ec72020-10-29 16:49:43 +0900499 product_available: true,
Jooyung Hana70f0672019-01-18 15:20:43 +0900500 double_loadable: true,
501 shared_libs: ["libnondoubleloadable"],
502 }
503
504 cc_library {
505 name: "libnondoubleloadable",
Justin Yunfd9e8042020-12-23 18:23:14 +0900506 vendor_available: true,
507 product_available: true,
Jooyung Hana70f0672019-01-18 15:20:43 +0900508 double_loadable: true,
509 }
510 `)
511 // okay to link : LLNDK -> core-only -> vendor_available & double_loadable
512 testCc(t, `
513 cc_library {
514 name: "libllndk",
515 shared_libs: ["libcoreonly"],
Colin Cross203b4212021-04-26 17:19:41 -0700516 llndk: {
517 symbol_file: "libllndk.map.txt",
518 }
Jooyung Hana70f0672019-01-18 15:20:43 +0900519 }
520
521 cc_library {
522 name: "libcoreonly",
523 shared_libs: ["libvendoravailable"],
524 }
525
526 // indirect dependency of LLNDK
527 cc_library {
528 name: "libvendoravailable",
529 vendor_available: true,
530 double_loadable: true,
531 }
532 `)
533}
534
535func TestDoubleLoadableDepError(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400536 t.Parallel()
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +0900537 // Check whether an error is emitted when a LLNDK depends on a non-double_loadable lib.
Jooyung Hana70f0672019-01-18 15:20:43 +0900538 testCcError(t, "module \".*\" variant \".*\": link.* \".*\" which is not LL-NDK, VNDK-SP, .*double_loadable", `
539 cc_library {
540 name: "libllndk",
541 shared_libs: ["libnondoubleloadable"],
Colin Cross203b4212021-04-26 17:19:41 -0700542 llndk: {
543 symbol_file: "libllndk.map.txt",
544 }
Jooyung Hana70f0672019-01-18 15:20:43 +0900545 }
546
547 cc_library {
548 name: "libnondoubleloadable",
549 vendor_available: true,
Justin Yun63e9ec72020-10-29 16:49:43 +0900550 product_available: true,
Jooyung Hana70f0672019-01-18 15:20:43 +0900551 }
552 `)
553
554 // Check whether an error is emitted when a LLNDK depends on a non-double_loadable vendor_available lib.
555 testCcError(t, "module \".*\" variant \".*\": link.* \".*\" which is not LL-NDK, VNDK-SP, .*double_loadable", `
556 cc_library {
557 name: "libllndk",
Yi Konge7fe9912019-06-02 00:53:50 -0700558 no_libcrt: true,
Jooyung Hana70f0672019-01-18 15:20:43 +0900559 shared_libs: ["libnondoubleloadable"],
Colin Cross203b4212021-04-26 17:19:41 -0700560 llndk: {
561 symbol_file: "libllndk.map.txt",
562 }
Jooyung Hana70f0672019-01-18 15:20:43 +0900563 }
564
565 cc_library {
566 name: "libnondoubleloadable",
567 vendor_available: true,
568 }
569 `)
570
Jooyung Hana70f0672019-01-18 15:20:43 +0900571 // Check whether an error is emitted when a LLNDK depends on a non-double_loadable indirectly.
572 testCcError(t, "module \".*\" variant \".*\": link.* \".*\" which is not LL-NDK, VNDK-SP, .*double_loadable", `
573 cc_library {
574 name: "libllndk",
575 shared_libs: ["libcoreonly"],
Colin Cross203b4212021-04-26 17:19:41 -0700576 llndk: {
577 symbol_file: "libllndk.map.txt",
578 }
Jooyung Hana70f0672019-01-18 15:20:43 +0900579 }
580
581 cc_library {
582 name: "libcoreonly",
583 shared_libs: ["libvendoravailable"],
584 }
585
586 // indirect dependency of LLNDK
587 cc_library {
588 name: "libvendoravailable",
589 vendor_available: true,
590 }
591 `)
Jiyong Park0474e1f2021-01-14 14:26:06 +0900592
593 // The error is not from 'client' but from 'libllndk'
594 testCcError(t, "module \"libllndk\".* links a library \"libnondoubleloadable\".*double_loadable", `
595 cc_library {
596 name: "client",
597 vendor_available: true,
598 double_loadable: true,
599 shared_libs: ["libllndk"],
600 }
601 cc_library {
602 name: "libllndk",
603 shared_libs: ["libnondoubleloadable"],
Colin Cross203b4212021-04-26 17:19:41 -0700604 llndk: {
605 symbol_file: "libllndk.map.txt",
606 }
Jiyong Park0474e1f2021-01-14 14:26:06 +0900607 }
608 cc_library {
609 name: "libnondoubleloadable",
610 vendor_available: true,
611 }
612 `)
Logan Chiend3c59a22018-03-29 14:08:15 +0800613}
614
Jooyung Han38002912019-05-16 04:01:54 +0900615func TestMakeLinkType(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400616 t.Parallel()
Colin Cross98be1bb2019-12-13 20:41:13 -0800617 bp := `
618 cc_library {
Colin Cross98be1bb2019-12-13 20:41:13 -0800619 name: "libvendor",
620 vendor: true,
621 }
Colin Cross98be1bb2019-12-13 20:41:13 -0800622 vndk_prebuilt_shared {
623 name: "prevndk",
624 version: "27",
625 target_arch: "arm",
626 binder32bit: true,
627 vendor_available: true,
Justin Yun63e9ec72020-10-29 16:49:43 +0900628 product_available: true,
Colin Cross98be1bb2019-12-13 20:41:13 -0800629 vndk: {
630 enabled: true,
631 },
632 arch: {
633 arm: {
634 srcs: ["liba.so"],
635 },
636 },
637 }
638 cc_library {
639 name: "libllndk",
Colin Cross203b4212021-04-26 17:19:41 -0700640 llndk: {
641 symbol_file: "libllndk.map.txt",
642 }
Colin Cross98be1bb2019-12-13 20:41:13 -0800643 }
644 cc_library {
645 name: "libllndkprivate",
Colin Cross203b4212021-04-26 17:19:41 -0700646 llndk: {
647 symbol_file: "libllndkprivate.map.txt",
648 private: true,
649 }
Colin Cross78212242021-01-06 14:51:30 -0800650 }
Colin Cross78212242021-01-06 14:51:30 -0800651 llndk_libraries_txt {
652 name: "llndk.libraries.txt",
653 }
Colin Cross78212242021-01-06 14:51:30 -0800654 `
Colin Cross98be1bb2019-12-13 20:41:13 -0800655
Paul Duffinc3e6ce02021-03-22 23:21:32 +0000656 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Jooyung Han38002912019-05-16 04:01:54 +0900657 // native:vndk
Colin Cross98be1bb2019-12-13 20:41:13 -0800658 ctx := testCcWithConfig(t, config)
Jooyung Han38002912019-05-16 04:01:54 +0900659
Colin Crossfb0c16e2019-11-20 17:12:35 -0800660 vendorVariant27 := "android_vendor.27_arm64_armv8-a_shared"
Inseob Kim64c43952019-08-26 16:52:35 +0900661
Jooyung Han38002912019-05-16 04:01:54 +0900662 tests := []struct {
663 variant string
664 name string
665 expected string
666 }{
Jooyung Han38002912019-05-16 04:01:54 +0900667 {vendorVariant, "libvendor", "native:vendor"},
Colin Cross127bb8b2020-12-16 16:46:01 -0800668 {vendorVariant, "libllndk", "native:vndk"},
Kiyoung Kim9f26fcf2024-05-27 17:25:52 +0900669 {vendorVariant27, "prevndk.vndk.27.arm.binder32", "native:vendor"},
Jooyung Han38002912019-05-16 04:01:54 +0900670 {coreVariant, "libllndk", "native:platform"},
671 }
672 for _, test := range tests {
673 t.Run(test.name, func(t *testing.T) {
674 module := ctx.ModuleForTests(test.name, test.variant).Module().(*Module)
675 assertString(t, module.makeLinkType, test.expected)
676 })
677 }
678}
679
Jeff Gaston294356f2017-09-27 17:05:30 -0700680var staticLinkDepOrderTestCases = []struct {
681 // This is a string representation of a map[moduleName][]moduleDependency .
682 // It models the dependencies declared in an Android.bp file.
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800683 inStatic string
684
685 // This is a string representation of a map[moduleName][]moduleDependency .
686 // It models the dependencies declared in an Android.bp file.
687 inShared string
Jeff Gaston294356f2017-09-27 17:05:30 -0700688
689 // allOrdered is a string representation of a map[moduleName][]moduleDependency .
690 // The keys of allOrdered specify which modules we would like to check.
691 // The values of allOrdered specify the expected result (of the transitive closure of all
692 // dependencies) for each module to test
693 allOrdered string
694
695 // outOrdered is a string representation of a map[moduleName][]moduleDependency .
696 // The keys of outOrdered specify which modules we would like to check.
697 // The values of outOrdered specify the expected result (of the ordered linker command line)
698 // for each module to test.
699 outOrdered string
700}{
701 // Simple tests
702 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800703 inStatic: "",
Jeff Gaston294356f2017-09-27 17:05:30 -0700704 outOrdered: "",
705 },
706 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800707 inStatic: "a:",
Jeff Gaston294356f2017-09-27 17:05:30 -0700708 outOrdered: "a:",
709 },
710 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800711 inStatic: "a:b; b:",
Jeff Gaston294356f2017-09-27 17:05:30 -0700712 outOrdered: "a:b; b:",
713 },
714 // Tests of reordering
715 {
716 // diamond example
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800717 inStatic: "a:d,b,c; b:d; c:d; d:",
Jeff Gaston294356f2017-09-27 17:05:30 -0700718 outOrdered: "a:b,c,d; b:d; c:d; d:",
719 },
720 {
721 // somewhat real example
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800722 inStatic: "bsdiff_unittest:b,c,d,e,f,g,h,i; e:b",
Jeff Gaston294356f2017-09-27 17:05:30 -0700723 outOrdered: "bsdiff_unittest:c,d,e,b,f,g,h,i; e:b",
724 },
725 {
726 // multiple reorderings
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800727 inStatic: "a:b,c,d,e; d:b; e:c",
Jeff Gaston294356f2017-09-27 17:05:30 -0700728 outOrdered: "a:d,b,e,c; d:b; e:c",
729 },
730 {
731 // should reorder without adding new transitive dependencies
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800732 inStatic: "bin:lib2,lib1; lib1:lib2,liboptional",
Jeff Gaston294356f2017-09-27 17:05:30 -0700733 allOrdered: "bin:lib1,lib2,liboptional; lib1:lib2,liboptional",
734 outOrdered: "bin:lib1,lib2; lib1:lib2,liboptional",
735 },
736 {
737 // multiple levels of dependencies
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800738 inStatic: "a:b,c,d,e,f,g,h; f:b,c,d; b:c,d; c:d",
Jeff Gaston294356f2017-09-27 17:05:30 -0700739 allOrdered: "a:e,f,b,c,d,g,h; f:b,c,d; b:c,d; c:d",
740 outOrdered: "a:e,f,b,c,d,g,h; f:b,c,d; b:c,d; c:d",
741 },
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800742 // shared dependencies
743 {
744 // Note that this test doesn't recurse, to minimize the amount of logic it tests.
745 // So, we don't actually have to check that a shared dependency of c will change the order
746 // of a library that depends statically on b and on c. We only need to check that if c has
747 // a shared dependency on b, that that shows up in allOrdered.
748 inShared: "c:b",
749 allOrdered: "c:b",
750 outOrdered: "c:",
751 },
752 {
753 // This test doesn't actually include any shared dependencies but it's a reminder of what
754 // the second phase of the above test would look like
755 inStatic: "a:b,c; c:b",
756 allOrdered: "a:c,b; c:b",
757 outOrdered: "a:c,b; c:b",
758 },
Jeff Gaston294356f2017-09-27 17:05:30 -0700759 // tiebreakers for when two modules specifying different orderings and there is no dependency
760 // to dictate an order
761 {
762 // if the tie is between two modules at the end of a's deps, then a's order wins
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800763 inStatic: "a1:b,c,d,e; a2:b,c,e,d; b:d,e; c:e,d",
Jeff Gaston294356f2017-09-27 17:05:30 -0700764 outOrdered: "a1:b,c,d,e; a2:b,c,e,d; b:d,e; c:e,d",
765 },
766 {
767 // if the tie is between two modules at the start of a's deps, then c's order is used
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800768 inStatic: "a1:d,e,b1,c1; b1:d,e; c1:e,d; a2:d,e,b2,c2; b2:d,e; c2:d,e",
Jeff Gaston294356f2017-09-27 17:05:30 -0700769 outOrdered: "a1:b1,c1,e,d; b1:d,e; c1:e,d; a2:b2,c2,d,e; b2:d,e; c2:d,e",
770 },
771 // Tests involving duplicate dependencies
772 {
773 // simple duplicate
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800774 inStatic: "a:b,c,c,b",
Jeff Gaston294356f2017-09-27 17:05:30 -0700775 outOrdered: "a:c,b",
776 },
777 {
778 // duplicates with reordering
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800779 inStatic: "a:b,c,d,c; c:b",
Jeff Gaston294356f2017-09-27 17:05:30 -0700780 outOrdered: "a:d,c,b",
781 },
782 // Tests to confirm the nonexistence of infinite loops.
783 // These cases should never happen, so as long as the test terminates and the
784 // result is deterministic then that should be fine.
785 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800786 inStatic: "a:a",
Jeff Gaston294356f2017-09-27 17:05:30 -0700787 outOrdered: "a:a",
788 },
789 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800790 inStatic: "a:b; b:c; c:a",
Jeff Gaston294356f2017-09-27 17:05:30 -0700791 allOrdered: "a:b,c; b:c,a; c:a,b",
792 outOrdered: "a:b; b:c; c:a",
793 },
794 {
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800795 inStatic: "a:b,c; b:c,a; c:a,b",
Jeff Gaston294356f2017-09-27 17:05:30 -0700796 allOrdered: "a:c,a,b; b:a,b,c; c:b,c,a",
797 outOrdered: "a:c,b; b:a,c; c:b,a",
798 },
799}
800
801// converts from a string like "a:b,c; d:e" to (["a","b"], {"a":["b","c"], "d":["e"]}, [{"a", "a.o"}, {"b", "b.o"}])
802func parseModuleDeps(text string) (modulesInOrder []android.Path, allDeps map[android.Path][]android.Path) {
803 // convert from "a:b,c; d:e" to "a:b,c;d:e"
804 strippedText := strings.Replace(text, " ", "", -1)
805 if len(strippedText) < 1 {
806 return []android.Path{}, make(map[android.Path][]android.Path, 0)
807 }
808 allDeps = make(map[android.Path][]android.Path, 0)
809
810 // convert from "a:b,c;d:e" to ["a:b,c", "d:e"]
811 moduleTexts := strings.Split(strippedText, ";")
812
813 outputForModuleName := func(moduleName string) android.Path {
814 return android.PathForTesting(moduleName)
815 }
816
817 for _, moduleText := range moduleTexts {
818 // convert from "a:b,c" to ["a", "b,c"]
819 components := strings.Split(moduleText, ":")
820 if len(components) != 2 {
821 panic(fmt.Sprintf("illegal module dep string %q from larger string %q; must contain one ':', not %v", moduleText, text, len(components)-1))
822 }
823 moduleName := components[0]
824 moduleOutput := outputForModuleName(moduleName)
825 modulesInOrder = append(modulesInOrder, moduleOutput)
826
827 depString := components[1]
828 // convert from "b,c" to ["b", "c"]
829 depNames := strings.Split(depString, ",")
830 if len(depString) < 1 {
831 depNames = []string{}
832 }
833 var deps []android.Path
834 for _, depName := range depNames {
835 deps = append(deps, outputForModuleName(depName))
836 }
837 allDeps[moduleOutput] = deps
838 }
839 return modulesInOrder, allDeps
840}
841
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800842func TestStaticLibDepReordering(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400843 t.Parallel()
Jeff Gaston294356f2017-09-27 17:05:30 -0700844 ctx := testCc(t, `
845 cc_library {
846 name: "a",
847 static_libs: ["b", "c", "d"],
Jiyong Park374510b2018-03-19 18:23:01 +0900848 stl: "none",
Jeff Gaston294356f2017-09-27 17:05:30 -0700849 }
850 cc_library {
851 name: "b",
Jiyong Park374510b2018-03-19 18:23:01 +0900852 stl: "none",
Jeff Gaston294356f2017-09-27 17:05:30 -0700853 }
854 cc_library {
855 name: "c",
856 static_libs: ["b"],
Jiyong Park374510b2018-03-19 18:23:01 +0900857 stl: "none",
Jeff Gaston294356f2017-09-27 17:05:30 -0700858 }
859 cc_library {
860 name: "d",
Jiyong Park374510b2018-03-19 18:23:01 +0900861 stl: "none",
Jeff Gaston294356f2017-09-27 17:05:30 -0700862 }
863
864 `)
865
Colin Cross7113d202019-11-20 16:39:12 -0800866 variant := "android_arm64_armv8-a_static"
Jeff Gaston294356f2017-09-27 17:05:30 -0700867 moduleA := ctx.ModuleForTests("a", variant).Module().(*Module)
Yu Liu663e4502024-08-12 18:23:59 +0000868 staticLibInfo, _ := android.OtherModuleProvider(ctx, moduleA, StaticLibraryInfoProvider)
Colin Cross5a377182023-12-14 14:46:23 -0800869 actual := android.Paths(staticLibInfo.TransitiveStaticLibrariesForOrdering.ToList()).RelativeToTop()
Ivan Lozanod67a6b02021-05-20 13:01:32 -0400870 expected := GetOutputPaths(ctx, variant, []string{"a", "c", "b", "d"})
Jeff Gaston294356f2017-09-27 17:05:30 -0700871
872 if !reflect.DeepEqual(actual, expected) {
873 t.Errorf("staticDeps orderings were not propagated correctly"+
874 "\nactual: %v"+
875 "\nexpected: %v",
876 actual,
877 expected,
878 )
879 }
Jiyong Parkd08b6972017-09-26 10:50:54 +0900880}
Jeff Gaston294356f2017-09-27 17:05:30 -0700881
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800882func TestStaticLibDepReorderingWithShared(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400883 t.Parallel()
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800884 ctx := testCc(t, `
885 cc_library {
886 name: "a",
887 static_libs: ["b", "c"],
Jiyong Park374510b2018-03-19 18:23:01 +0900888 stl: "none",
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800889 }
890 cc_library {
891 name: "b",
Jiyong Park374510b2018-03-19 18:23:01 +0900892 stl: "none",
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800893 }
894 cc_library {
895 name: "c",
896 shared_libs: ["b"],
Jiyong Park374510b2018-03-19 18:23:01 +0900897 stl: "none",
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800898 }
899
900 `)
901
Colin Cross7113d202019-11-20 16:39:12 -0800902 variant := "android_arm64_armv8-a_static"
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800903 moduleA := ctx.ModuleForTests("a", variant).Module().(*Module)
Yu Liu663e4502024-08-12 18:23:59 +0000904 staticLibInfo, _ := android.OtherModuleProvider(ctx, moduleA, StaticLibraryInfoProvider)
Colin Cross5a377182023-12-14 14:46:23 -0800905 actual := android.Paths(staticLibInfo.TransitiveStaticLibrariesForOrdering.ToList()).RelativeToTop()
Ivan Lozanod67a6b02021-05-20 13:01:32 -0400906 expected := GetOutputPaths(ctx, variant, []string{"a", "c", "b"})
Jeff Gastonf5b6e8f2017-11-27 15:48:57 -0800907
908 if !reflect.DeepEqual(actual, expected) {
909 t.Errorf("staticDeps orderings did not account for shared libs"+
910 "\nactual: %v"+
911 "\nexpected: %v",
912 actual,
913 expected,
914 )
915 }
916}
917
Jooyung Hanb04a4992020-03-13 18:57:35 +0900918func checkEquals(t *testing.T, message string, expected, actual interface{}) {
Colin Crossd1f898e2020-08-18 18:35:15 -0700919 t.Helper()
Jooyung Hanb04a4992020-03-13 18:57:35 +0900920 if !reflect.DeepEqual(actual, expected) {
921 t.Errorf(message+
922 "\nactual: %v"+
923 "\nexpected: %v",
924 actual,
925 expected,
926 )
927 }
928}
929
Jooyung Han61b66e92020-03-21 14:21:46 +0000930func TestLlndkLibrary(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -0400931 t.Parallel()
Colin Cross0fb7fcd2021-03-02 11:00:07 -0800932 result := prepareForCcTest.RunTestWithBp(t, `
933 cc_library {
934 name: "libllndk",
935 stubs: { versions: ["1", "2"] },
936 llndk: {
937 symbol_file: "libllndk.map.txt",
938 },
939 export_include_dirs: ["include"],
940 }
941
942 cc_prebuilt_library_shared {
943 name: "libllndkprebuilt",
Spandan Das357ffcc2024-07-24 18:07:48 +0000944 stubs: { versions: ["1", "2"] , symbol_file: "libllndkprebuilt.map.txt" },
Colin Cross0fb7fcd2021-03-02 11:00:07 -0800945 llndk: {
946 symbol_file: "libllndkprebuilt.map.txt",
947 },
948 }
949
950 cc_library {
951 name: "libllndk_with_external_headers",
952 stubs: { versions: ["1", "2"] },
953 llndk: {
954 symbol_file: "libllndk.map.txt",
955 export_llndk_headers: ["libexternal_llndk_headers"],
956 },
957 header_libs: ["libexternal_headers"],
958 export_header_lib_headers: ["libexternal_headers"],
959 }
960 cc_library_headers {
961 name: "libexternal_headers",
962 export_include_dirs: ["include"],
963 vendor_available: true,
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +0900964 product_available: true,
Colin Cross0fb7fcd2021-03-02 11:00:07 -0800965 }
966 cc_library_headers {
967 name: "libexternal_llndk_headers",
968 export_include_dirs: ["include_llndk"],
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +0800969 export_system_include_dirs: ["include_system_llndk"],
Colin Cross0fb7fcd2021-03-02 11:00:07 -0800970 llndk: {
971 symbol_file: "libllndk.map.txt",
972 },
973 vendor_available: true,
974 }
975
976 cc_library {
977 name: "libllndk_with_override_headers",
978 stubs: { versions: ["1", "2"] },
979 llndk: {
980 symbol_file: "libllndk.map.txt",
981 override_export_include_dirs: ["include_llndk"],
982 },
983 export_include_dirs: ["include"],
984 }
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +0800985
986 cc_library {
987 name: "libllndk_with_system_headers",
988 llndk: {
989 symbol_file: "libllndk.map.txt",
990 export_llndk_headers: ["libexternal_llndk_headers"],
991 export_headers_as_system: true,
992 },
993 export_include_dirs: ["include"],
994 export_system_include_dirs: ["include_system"],
995 }
Colin Cross0fb7fcd2021-03-02 11:00:07 -0800996 `)
997 actual := result.ModuleVariantsForTests("libllndk")
998 for i := 0; i < len(actual); i++ {
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +0900999 if !strings.HasPrefix(actual[i], "android_vendor_") {
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001000 actual = append(actual[:i], actual[i+1:]...)
1001 i--
1002 }
1003 }
1004 expected := []string{
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001005 "android_vendor_arm64_armv8-a_shared",
1006 "android_vendor_arm_armv7-a-neon_shared",
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001007 }
1008 android.AssertArrayString(t, "variants for llndk stubs", expected, actual)
1009
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001010 params := result.ModuleForTests("libllndk", "android_vendor_arm_armv7-a-neon_shared").Description("generate stub")
Jooyung Han33eb6152024-03-11 15:46:48 +09001011 android.AssertSame(t, "use Vendor API level for default stubs", "202404", params.Args["apiLevel"])
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001012
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001013 checkExportedIncludeDirs := func(module, variant string, expectedSystemDirs []string, expectedDirs ...string) {
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001014 t.Helper()
1015 m := result.ModuleForTests(module, variant).Module()
Yu Liu663e4502024-08-12 18:23:59 +00001016 f, _ := android.OtherModuleProvider(result, m, FlagExporterInfoProvider)
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001017 android.AssertPathsRelativeToTopEquals(t, "exported include dirs for "+module+"["+variant+"]",
1018 expectedDirs, f.IncludeDirs)
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001019 android.AssertPathsRelativeToTopEquals(t, "exported include dirs for "+module+"["+variant+"]",
1020 expectedSystemDirs, f.SystemIncludeDirs)
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001021 }
1022
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001023 checkExportedIncludeDirs("libllndk", coreVariant, nil, "include")
1024 checkExportedIncludeDirs("libllndk", vendorVariant, nil, "include")
1025 checkExportedIncludeDirs("libllndk_with_external_headers", coreVariant, nil, "include")
1026 checkExportedIncludeDirs("libllndk_with_external_headers", vendorVariant,
1027 []string{"include_system_llndk"}, "include_llndk")
1028 checkExportedIncludeDirs("libllndk_with_override_headers", coreVariant, nil, "include")
1029 checkExportedIncludeDirs("libllndk_with_override_headers", vendorVariant, nil, "include_llndk")
1030 checkExportedIncludeDirs("libllndk_with_system_headers", coreVariant, []string{"include_system"}, "include")
1031 checkExportedIncludeDirs("libllndk_with_system_headers", vendorVariant,
1032 []string{"include_system", "include", "include_system_llndk"}, "include_llndk")
Hsin-Yi Chen64b2d032024-03-29 19:12:35 +08001033
1034 checkAbiLinkerIncludeDirs := func(module string) {
1035 t.Helper()
1036 coreModule := result.ModuleForTests(module, coreVariant)
1037 abiCheckFlags := ""
1038 for _, output := range coreModule.AllOutputs() {
1039 if strings.HasSuffix(output, ".so.llndk.lsdump") {
1040 abiCheckFlags = coreModule.Output(output).Args["exportedHeaderFlags"]
1041 }
1042 }
1043 vendorModule := result.ModuleForTests(module, vendorVariant).Module()
Yu Liu663e4502024-08-12 18:23:59 +00001044 vendorInfo, _ := android.OtherModuleProvider(result, vendorModule, FlagExporterInfoProvider)
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001045 vendorDirs := android.Concat(vendorInfo.IncludeDirs, vendorInfo.SystemIncludeDirs)
Hsin-Yi Chen64b2d032024-03-29 19:12:35 +08001046 android.AssertStringEquals(t, module+" has different exported include dirs for vendor variant and ABI check",
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001047 android.JoinPathsWithPrefix(vendorDirs, "-I"), abiCheckFlags)
Hsin-Yi Chen64b2d032024-03-29 19:12:35 +08001048 }
1049 checkAbiLinkerIncludeDirs("libllndk")
1050 checkAbiLinkerIncludeDirs("libllndk_with_override_headers")
1051 checkAbiLinkerIncludeDirs("libllndk_with_external_headers")
Hsin-Yi Chen5f228b02024-04-02 12:38:47 +08001052 checkAbiLinkerIncludeDirs("libllndk_with_system_headers")
Colin Cross0fb7fcd2021-03-02 11:00:07 -08001053}
1054
Jiyong Parka46a4d52017-12-14 19:54:34 +09001055func TestLlndkHeaders(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001056 t.Parallel()
Jiyong Parka46a4d52017-12-14 19:54:34 +09001057 ctx := testCc(t, `
Colin Cross627280f2021-04-26 16:53:58 -07001058 cc_library_headers {
Jiyong Parka46a4d52017-12-14 19:54:34 +09001059 name: "libllndk_headers",
1060 export_include_dirs: ["my_include"],
Colin Cross627280f2021-04-26 16:53:58 -07001061 llndk: {
1062 llndk_headers: true,
1063 },
Jiyong Parka46a4d52017-12-14 19:54:34 +09001064 }
1065 cc_library {
Colin Cross0477b422020-10-13 18:43:54 -07001066 name: "libllndk",
Colin Cross627280f2021-04-26 16:53:58 -07001067 llndk: {
1068 symbol_file: "libllndk.map.txt",
1069 export_llndk_headers: ["libllndk_headers"],
1070 }
Colin Cross0477b422020-10-13 18:43:54 -07001071 }
1072
1073 cc_library {
Jiyong Parka46a4d52017-12-14 19:54:34 +09001074 name: "libvendor",
1075 shared_libs: ["libllndk"],
1076 vendor: true,
1077 srcs: ["foo.c"],
Yi Konge7fe9912019-06-02 00:53:50 -07001078 no_libcrt: true,
Logan Chienf3511742017-10-31 18:04:35 +08001079 nocrt: true,
Jiyong Parka46a4d52017-12-14 19:54:34 +09001080 }
1081 `)
1082
1083 // _static variant is used since _shared reuses *.o from the static variant
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001084 cc := ctx.ModuleForTests("libvendor", "android_vendor_arm_armv7-a-neon_static").Rule("cc")
Jiyong Parka46a4d52017-12-14 19:54:34 +09001085 cflags := cc.Args["cFlags"]
1086 if !strings.Contains(cflags, "-Imy_include") {
1087 t.Errorf("cflags for libvendor must contain -Imy_include, but was %#v.", cflags)
1088 }
1089}
1090
Logan Chien43d34c32017-12-20 01:17:32 +08001091func checkRuntimeLibs(t *testing.T, expected []string, module *Module) {
1092 actual := module.Properties.AndroidMkRuntimeLibs
1093 if !reflect.DeepEqual(actual, expected) {
1094 t.Errorf("incorrect runtime_libs for shared libs"+
1095 "\nactual: %v"+
1096 "\nexpected: %v",
1097 actual,
1098 expected,
1099 )
1100 }
1101}
1102
1103const runtimeLibAndroidBp = `
1104 cc_library {
Justin Yun8a2600c2020-12-07 12:44:03 +09001105 name: "liball_available",
1106 vendor_available: true,
1107 product_available: true,
1108 no_libcrt : true,
1109 nocrt : true,
1110 system_shared_libs : [],
1111 }
1112 cc_library {
Logan Chien43d34c32017-12-20 01:17:32 +08001113 name: "libvendor_available1",
1114 vendor_available: true,
Justin Yun8a2600c2020-12-07 12:44:03 +09001115 runtime_libs: ["liball_available"],
Yi Konge7fe9912019-06-02 00:53:50 -07001116 no_libcrt : true,
Logan Chien43d34c32017-12-20 01:17:32 +08001117 nocrt : true,
1118 system_shared_libs : [],
1119 }
1120 cc_library {
1121 name: "libvendor_available2",
1122 vendor_available: true,
Justin Yun8a2600c2020-12-07 12:44:03 +09001123 runtime_libs: ["liball_available"],
Logan Chien43d34c32017-12-20 01:17:32 +08001124 target: {
1125 vendor: {
Justin Yun8a2600c2020-12-07 12:44:03 +09001126 exclude_runtime_libs: ["liball_available"],
Logan Chien43d34c32017-12-20 01:17:32 +08001127 }
1128 },
Yi Konge7fe9912019-06-02 00:53:50 -07001129 no_libcrt : true,
Logan Chien43d34c32017-12-20 01:17:32 +08001130 nocrt : true,
1131 system_shared_libs : [],
1132 }
1133 cc_library {
Justin Yuncbca3732021-02-03 19:24:13 +09001134 name: "libproduct_vendor",
1135 product_specific: true,
1136 vendor_available: true,
1137 no_libcrt : true,
1138 nocrt : true,
1139 system_shared_libs : [],
1140 }
1141 cc_library {
Logan Chien43d34c32017-12-20 01:17:32 +08001142 name: "libcore",
Justin Yun8a2600c2020-12-07 12:44:03 +09001143 runtime_libs: ["liball_available"],
Yi Konge7fe9912019-06-02 00:53:50 -07001144 no_libcrt : true,
Logan Chien43d34c32017-12-20 01:17:32 +08001145 nocrt : true,
1146 system_shared_libs : [],
1147 }
1148 cc_library {
1149 name: "libvendor1",
1150 vendor: true,
Yi Konge7fe9912019-06-02 00:53:50 -07001151 no_libcrt : true,
Logan Chien43d34c32017-12-20 01:17:32 +08001152 nocrt : true,
1153 system_shared_libs : [],
1154 }
1155 cc_library {
1156 name: "libvendor2",
1157 vendor: true,
Justin Yuncbca3732021-02-03 19:24:13 +09001158 runtime_libs: ["liball_available", "libvendor1", "libproduct_vendor"],
Justin Yun8a2600c2020-12-07 12:44:03 +09001159 no_libcrt : true,
1160 nocrt : true,
1161 system_shared_libs : [],
1162 }
1163 cc_library {
1164 name: "libproduct_available1",
1165 product_available: true,
1166 runtime_libs: ["liball_available"],
1167 no_libcrt : true,
1168 nocrt : true,
1169 system_shared_libs : [],
1170 }
1171 cc_library {
1172 name: "libproduct1",
1173 product_specific: true,
1174 no_libcrt : true,
1175 nocrt : true,
1176 system_shared_libs : [],
1177 }
1178 cc_library {
1179 name: "libproduct2",
1180 product_specific: true,
Justin Yuncbca3732021-02-03 19:24:13 +09001181 runtime_libs: ["liball_available", "libproduct1", "libproduct_vendor"],
Yi Konge7fe9912019-06-02 00:53:50 -07001182 no_libcrt : true,
Logan Chien43d34c32017-12-20 01:17:32 +08001183 nocrt : true,
1184 system_shared_libs : [],
1185 }
1186`
1187
1188func TestRuntimeLibs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001189 t.Parallel()
Logan Chien43d34c32017-12-20 01:17:32 +08001190 ctx := testCc(t, runtimeLibAndroidBp)
1191
1192 // runtime_libs for core variants use the module names without suffixes.
Colin Cross7113d202019-11-20 16:39:12 -08001193 variant := "android_arm64_armv8-a_shared"
Logan Chien43d34c32017-12-20 01:17:32 +08001194
Justin Yun8a2600c2020-12-07 12:44:03 +09001195 module := ctx.ModuleForTests("libvendor_available1", variant).Module().(*Module)
1196 checkRuntimeLibs(t, []string{"liball_available"}, module)
1197
1198 module = ctx.ModuleForTests("libproduct_available1", variant).Module().(*Module)
1199 checkRuntimeLibs(t, []string{"liball_available"}, module)
Logan Chien43d34c32017-12-20 01:17:32 +08001200
1201 module = ctx.ModuleForTests("libcore", variant).Module().(*Module)
Justin Yun8a2600c2020-12-07 12:44:03 +09001202 checkRuntimeLibs(t, []string{"liball_available"}, module)
Logan Chien43d34c32017-12-20 01:17:32 +08001203
1204 // runtime_libs for vendor variants have '.vendor' suffixes if the modules have both core
1205 // and vendor variants.
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001206 variant = "android_vendor_arm64_armv8-a_shared"
Logan Chien43d34c32017-12-20 01:17:32 +08001207
Justin Yun8a2600c2020-12-07 12:44:03 +09001208 module = ctx.ModuleForTests("libvendor_available1", variant).Module().(*Module)
1209 checkRuntimeLibs(t, []string{"liball_available.vendor"}, module)
Logan Chien43d34c32017-12-20 01:17:32 +08001210
1211 module = ctx.ModuleForTests("libvendor2", variant).Module().(*Module)
Justin Yuncbca3732021-02-03 19:24:13 +09001212 checkRuntimeLibs(t, []string{"liball_available.vendor", "libvendor1", "libproduct_vendor.vendor"}, module)
Justin Yun8a2600c2020-12-07 12:44:03 +09001213
1214 // runtime_libs for product variants have '.product' suffixes if the modules have both core
1215 // and product variants.
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001216 variant = "android_product_arm64_armv8-a_shared"
Justin Yun8a2600c2020-12-07 12:44:03 +09001217
1218 module = ctx.ModuleForTests("libproduct_available1", variant).Module().(*Module)
1219 checkRuntimeLibs(t, []string{"liball_available.product"}, module)
1220
1221 module = ctx.ModuleForTests("libproduct2", variant).Module().(*Module)
Justin Yund00f5ca2021-02-03 19:43:02 +09001222 checkRuntimeLibs(t, []string{"liball_available.product", "libproduct1", "libproduct_vendor"}, module)
Logan Chien43d34c32017-12-20 01:17:32 +08001223}
1224
1225func TestExcludeRuntimeLibs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001226 t.Parallel()
Logan Chien43d34c32017-12-20 01:17:32 +08001227 ctx := testCc(t, runtimeLibAndroidBp)
1228
Colin Cross7113d202019-11-20 16:39:12 -08001229 variant := "android_arm64_armv8-a_shared"
Justin Yun8a2600c2020-12-07 12:44:03 +09001230 module := ctx.ModuleForTests("libvendor_available2", variant).Module().(*Module)
1231 checkRuntimeLibs(t, []string{"liball_available"}, module)
Logan Chien43d34c32017-12-20 01:17:32 +08001232
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09001233 variant = "android_vendor_arm64_armv8-a_shared"
Justin Yun8a2600c2020-12-07 12:44:03 +09001234 module = ctx.ModuleForTests("libvendor_available2", variant).Module().(*Module)
Logan Chien43d34c32017-12-20 01:17:32 +08001235 checkRuntimeLibs(t, nil, module)
1236}
1237
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001238func checkStaticLibs(t *testing.T, expected []string, module *Module) {
Jooyung Han03b51852020-02-26 22:45:42 +09001239 t.Helper()
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001240 actual := module.Properties.AndroidMkStaticLibs
1241 if !reflect.DeepEqual(actual, expected) {
1242 t.Errorf("incorrect static_libs"+
1243 "\nactual: %v"+
1244 "\nexpected: %v",
1245 actual,
1246 expected,
1247 )
1248 }
1249}
1250
1251const staticLibAndroidBp = `
1252 cc_library {
1253 name: "lib1",
1254 }
1255 cc_library {
1256 name: "lib2",
1257 static_libs: ["lib1"],
1258 }
1259`
1260
1261func TestStaticLibDepExport(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001262 t.Parallel()
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001263 ctx := testCc(t, staticLibAndroidBp)
1264
1265 // Check the shared version of lib2.
Colin Cross7113d202019-11-20 16:39:12 -08001266 variant := "android_arm64_armv8-a_shared"
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001267 module := ctx.ModuleForTests("lib2", variant).Module().(*Module)
Colin Cross4c4c1be2022-02-10 11:41:18 -08001268 checkStaticLibs(t, []string{"lib1", "libc++demangle", "libclang_rt.builtins"}, module)
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001269
1270 // Check the static version of lib2.
Colin Cross7113d202019-11-20 16:39:12 -08001271 variant = "android_arm64_armv8-a_static"
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001272 module = ctx.ModuleForTests("lib2", variant).Module().(*Module)
1273 // libc++_static is linked additionally.
Colin Cross4c4c1be2022-02-10 11:41:18 -08001274 checkStaticLibs(t, []string{"lib1", "libc++_static", "libc++demangle", "libclang_rt.builtins"}, module)
Jaewoong Jung16c7d3d2018-11-16 01:19:56 +00001275}
1276
Jiyong Parkd08b6972017-09-26 10:50:54 +09001277var compilerFlagsTestCases = []struct {
1278 in string
1279 out bool
1280}{
1281 {
1282 in: "a",
1283 out: false,
1284 },
1285 {
1286 in: "-a",
1287 out: true,
1288 },
1289 {
1290 in: "-Ipath/to/something",
1291 out: false,
1292 },
1293 {
1294 in: "-isystempath/to/something",
1295 out: false,
1296 },
1297 {
1298 in: "--coverage",
1299 out: false,
1300 },
1301 {
1302 in: "-include a/b",
1303 out: true,
1304 },
1305 {
1306 in: "-include a/b c/d",
1307 out: false,
1308 },
1309 {
1310 in: "-DMACRO",
1311 out: true,
1312 },
1313 {
1314 in: "-DMAC RO",
1315 out: false,
1316 },
1317 {
1318 in: "-a -b",
1319 out: false,
1320 },
1321 {
1322 in: "-DMACRO=definition",
1323 out: true,
1324 },
1325 {
1326 in: "-DMACRO=defi nition",
1327 out: true, // TODO(jiyong): this should be false
1328 },
1329 {
1330 in: "-DMACRO(x)=x + 1",
1331 out: true,
1332 },
1333 {
1334 in: "-DMACRO=\"defi nition\"",
1335 out: true,
1336 },
1337}
1338
1339type mockContext struct {
1340 BaseModuleContext
1341 result bool
1342}
1343
1344func (ctx *mockContext) PropertyErrorf(property, format string, args ...interface{}) {
1345 // CheckBadCompilerFlags calls this function when the flag should be rejected
1346 ctx.result = false
1347}
1348
1349func TestCompilerFlags(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001350 t.Parallel()
Jiyong Parkd08b6972017-09-26 10:50:54 +09001351 for _, testCase := range compilerFlagsTestCases {
1352 ctx := &mockContext{result: true}
1353 CheckBadCompilerFlags(ctx, "", []string{testCase.in})
1354 if ctx.result != testCase.out {
1355 t.Errorf("incorrect output:")
1356 t.Errorf(" input: %#v", testCase.in)
1357 t.Errorf(" expected: %#v", testCase.out)
1358 t.Errorf(" got: %#v", ctx.result)
1359 }
1360 }
Jeff Gaston294356f2017-09-27 17:05:30 -07001361}
Jiyong Park374510b2018-03-19 18:23:01 +09001362
Jiyong Park37b25202018-07-11 10:49:27 +09001363func TestRecovery(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001364 t.Parallel()
Jiyong Park37b25202018-07-11 10:49:27 +09001365 ctx := testCc(t, `
1366 cc_library_shared {
1367 name: "librecovery",
1368 recovery: true,
1369 }
1370 cc_library_shared {
1371 name: "librecovery32",
1372 recovery: true,
1373 compile_multilib:"32",
1374 }
Jiyong Park5baac542018-08-28 09:55:37 +09001375 cc_library_shared {
1376 name: "libHalInRecovery",
1377 recovery_available: true,
1378 vendor: true,
1379 }
Jiyong Park37b25202018-07-11 10:49:27 +09001380 `)
1381
1382 variants := ctx.ModuleVariantsForTests("librecovery")
Colin Crossfb0c16e2019-11-20 17:12:35 -08001383 const arm64 = "android_recovery_arm64_armv8-a_shared"
Jiyong Park37b25202018-07-11 10:49:27 +09001384 if len(variants) != 1 || !android.InList(arm64, variants) {
1385 t.Errorf("variants of librecovery must be \"%s\" only, but was %#v", arm64, variants)
1386 }
1387
1388 variants = ctx.ModuleVariantsForTests("librecovery32")
1389 if android.InList(arm64, variants) {
1390 t.Errorf("multilib was set to 32 for librecovery32, but its variants has %s.", arm64)
1391 }
Jiyong Park5baac542018-08-28 09:55:37 +09001392
1393 recoveryModule := ctx.ModuleForTests("libHalInRecovery", recoveryVariant).Module().(*Module)
1394 if !recoveryModule.Platform() {
1395 t.Errorf("recovery variant of libHalInRecovery must not specific to device, soc, or product")
1396 }
Jiyong Park7ed9de32018-10-15 22:25:07 +09001397}
Jiyong Park5baac542018-08-28 09:55:37 +09001398
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001399func TestDataLibsPrebuiltSharedTestLibrary(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001400 t.Parallel()
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001401 bp := `
1402 cc_prebuilt_test_library_shared {
1403 name: "test_lib",
1404 relative_install_path: "foo/bar/baz",
1405 srcs: ["srcpath/dontusethispath/baz.so"],
1406 }
1407
1408 cc_test {
1409 name: "main_test",
1410 data_libs: ["test_lib"],
1411 gtest: false,
1412 }
1413 `
1414
Paul Duffinc3e6ce02021-03-22 23:21:32 +00001415 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001416
1417 ctx := testCcWithConfig(t, config)
mrziwangabdb2932024-06-18 12:43:41 -07001418 testingModule := ctx.ModuleForTests("main_test", "android_arm_armv7-a-neon")
1419 module := testingModule.Module()
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001420 testBinary := module.(*Module).linker.(*testBinary)
Yu Liu51c22312024-08-20 23:56:15 +00001421 outputFiles := testingModule.OutputFiles(ctx, t, "")
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001422 if len(outputFiles) != 1 {
1423 t.Errorf("expected exactly one output file. output files: [%s]", outputFiles)
1424 }
1425 if len(testBinary.dataPaths()) != 1 {
Colin Cross7e2e7942023-11-16 12:56:02 -08001426 t.Errorf("expected exactly one test data file. test data files: [%v]", testBinary.dataPaths())
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001427 }
1428
1429 outputPath := outputFiles[0].String()
1430
1431 if !strings.HasSuffix(outputPath, "/main_test") {
1432 t.Errorf("expected test output file to be 'main_test', but was '%s'", outputPath)
1433 }
Yu Liue70976d2024-10-15 20:45:35 +00001434 entries := android.AndroidMkInfoForTest(t, ctx, module).PrimaryInfo
Chris Parsons1f6d90f2020-06-17 16:10:42 -04001435 if !strings.HasSuffix(entries.EntryMap["LOCAL_TEST_DATA"][0], ":test_lib.so:foo/bar/baz") {
1436 t.Errorf("expected LOCAL_TEST_DATA to end with `:test_lib.so:foo/bar/baz`,"+
1437 " but was '%s'", entries.EntryMap["LOCAL_TEST_DATA"][0])
1438 }
1439}
1440
Jiyong Park7ed9de32018-10-15 22:25:07 +09001441func TestVersionedStubs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001442 t.Parallel()
Jiyong Park7ed9de32018-10-15 22:25:07 +09001443 ctx := testCc(t, `
1444 cc_library_shared {
1445 name: "libFoo",
Jiyong Parkda732bd2018-11-02 18:23:15 +09001446 srcs: ["foo.c"],
Jiyong Park7ed9de32018-10-15 22:25:07 +09001447 stubs: {
1448 symbol_file: "foo.map.txt",
1449 versions: ["1", "2", "3"],
1450 },
1451 }
Jiyong Parkda732bd2018-11-02 18:23:15 +09001452
Jiyong Park7ed9de32018-10-15 22:25:07 +09001453 cc_library_shared {
1454 name: "libBar",
Jiyong Parkda732bd2018-11-02 18:23:15 +09001455 srcs: ["bar.c"],
Jiyong Park7ed9de32018-10-15 22:25:07 +09001456 shared_libs: ["libFoo#1"],
1457 }`)
1458
1459 variants := ctx.ModuleVariantsForTests("libFoo")
1460 expectedVariants := []string{
Colin Cross7113d202019-11-20 16:39:12 -08001461 "android_arm64_armv8-a_shared",
1462 "android_arm64_armv8-a_shared_1",
1463 "android_arm64_armv8-a_shared_2",
1464 "android_arm64_armv8-a_shared_3",
Jiyong Parkd4a3a132021-03-17 20:21:35 +09001465 "android_arm64_armv8-a_shared_current",
Colin Cross7113d202019-11-20 16:39:12 -08001466 "android_arm_armv7-a-neon_shared",
1467 "android_arm_armv7-a-neon_shared_1",
1468 "android_arm_armv7-a-neon_shared_2",
1469 "android_arm_armv7-a-neon_shared_3",
Jiyong Parkd4a3a132021-03-17 20:21:35 +09001470 "android_arm_armv7-a-neon_shared_current",
Jiyong Park7ed9de32018-10-15 22:25:07 +09001471 }
1472 variantsMismatch := false
1473 if len(variants) != len(expectedVariants) {
1474 variantsMismatch = true
1475 } else {
1476 for _, v := range expectedVariants {
1477 if !inList(v, variants) {
1478 variantsMismatch = false
1479 }
1480 }
1481 }
1482 if variantsMismatch {
1483 t.Errorf("variants of libFoo expected:\n")
1484 for _, v := range expectedVariants {
1485 t.Errorf("%q\n", v)
1486 }
1487 t.Errorf(", but got:\n")
1488 for _, v := range variants {
1489 t.Errorf("%q\n", v)
1490 }
1491 }
1492
Colin Cross7113d202019-11-20 16:39:12 -08001493 libBarLinkRule := ctx.ModuleForTests("libBar", "android_arm64_armv8-a_shared").Rule("ld")
Jiyong Park7ed9de32018-10-15 22:25:07 +09001494 libFlags := libBarLinkRule.Args["libFlags"]
Colin Cross7113d202019-11-20 16:39:12 -08001495 libFoo1StubPath := "libFoo/android_arm64_armv8-a_shared_1/libFoo.so"
Jiyong Park7ed9de32018-10-15 22:25:07 +09001496 if !strings.Contains(libFlags, libFoo1StubPath) {
1497 t.Errorf("%q is not found in %q", libFoo1StubPath, libFlags)
1498 }
Jiyong Parkda732bd2018-11-02 18:23:15 +09001499
Colin Cross7113d202019-11-20 16:39:12 -08001500 libBarCompileRule := ctx.ModuleForTests("libBar", "android_arm64_armv8-a_shared").Rule("cc")
Jiyong Parkda732bd2018-11-02 18:23:15 +09001501 cFlags := libBarCompileRule.Args["cFlags"]
1502 libFoo1VersioningMacro := "-D__LIBFOO_API__=1"
1503 if !strings.Contains(cFlags, libFoo1VersioningMacro) {
1504 t.Errorf("%q is not found in %q", libFoo1VersioningMacro, cFlags)
1505 }
Jiyong Park37b25202018-07-11 10:49:27 +09001506}
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001507
Liz Kammer48cdbeb2023-03-17 10:17:50 -04001508func TestStubsForLibraryInMultipleApexes(t *testing.T) {
1509 t.Parallel()
1510 ctx := testCc(t, `
1511 cc_library_shared {
1512 name: "libFoo",
1513 srcs: ["foo.c"],
1514 stubs: {
1515 symbol_file: "foo.map.txt",
1516 versions: ["current"],
1517 },
1518 apex_available: ["bar", "a1"],
1519 }
1520
1521 cc_library_shared {
1522 name: "libBar",
1523 srcs: ["bar.c"],
1524 shared_libs: ["libFoo"],
1525 apex_available: ["a1"],
1526 }
1527
1528 cc_library_shared {
1529 name: "libA1",
1530 srcs: ["a1.c"],
1531 shared_libs: ["libFoo"],
1532 apex_available: ["a1"],
1533 }
1534
1535 cc_library_shared {
1536 name: "libBarA1",
1537 srcs: ["bara1.c"],
1538 shared_libs: ["libFoo"],
1539 apex_available: ["bar", "a1"],
1540 }
1541
1542 cc_library_shared {
1543 name: "libAnyApex",
1544 srcs: ["anyApex.c"],
1545 shared_libs: ["libFoo"],
1546 apex_available: ["//apex_available:anyapex"],
1547 }
1548
1549 cc_library_shared {
1550 name: "libBaz",
1551 srcs: ["baz.c"],
1552 shared_libs: ["libFoo"],
1553 apex_available: ["baz"],
1554 }
1555
1556 cc_library_shared {
1557 name: "libQux",
1558 srcs: ["qux.c"],
1559 shared_libs: ["libFoo"],
1560 apex_available: ["qux", "bar"],
1561 }`)
1562
1563 variants := ctx.ModuleVariantsForTests("libFoo")
1564 expectedVariants := []string{
1565 "android_arm64_armv8-a_shared",
1566 "android_arm64_armv8-a_shared_current",
1567 "android_arm_armv7-a-neon_shared",
1568 "android_arm_armv7-a-neon_shared_current",
1569 }
1570 variantsMismatch := false
1571 if len(variants) != len(expectedVariants) {
1572 variantsMismatch = true
1573 } else {
1574 for _, v := range expectedVariants {
1575 if !inList(v, variants) {
1576 variantsMismatch = false
1577 }
1578 }
1579 }
1580 if variantsMismatch {
1581 t.Errorf("variants of libFoo expected:\n")
1582 for _, v := range expectedVariants {
1583 t.Errorf("%q\n", v)
1584 }
1585 t.Errorf(", but got:\n")
1586 for _, v := range variants {
1587 t.Errorf("%q\n", v)
1588 }
1589 }
1590
1591 linkAgainstFoo := []string{"libBarA1"}
1592 linkAgainstFooStubs := []string{"libBar", "libA1", "libBaz", "libQux", "libAnyApex"}
1593
1594 libFooPath := "libFoo/android_arm64_armv8-a_shared/libFoo.so"
1595 for _, lib := range linkAgainstFoo {
1596 libLinkRule := ctx.ModuleForTests(lib, "android_arm64_armv8-a_shared").Rule("ld")
1597 libFlags := libLinkRule.Args["libFlags"]
1598 if !strings.Contains(libFlags, libFooPath) {
1599 t.Errorf("%q: %q is not found in %q", lib, libFooPath, libFlags)
1600 }
1601 }
1602
1603 libFooStubPath := "libFoo/android_arm64_armv8-a_shared_current/libFoo.so"
1604 for _, lib := range linkAgainstFooStubs {
1605 libLinkRule := ctx.ModuleForTests(lib, "android_arm64_armv8-a_shared").Rule("ld")
1606 libFlags := libLinkRule.Args["libFlags"]
1607 if !strings.Contains(libFlags, libFooStubPath) {
1608 t.Errorf("%q: %q is not found in %q", lib, libFooStubPath, libFlags)
1609 }
1610 }
1611}
1612
Jooyung Hanb04a4992020-03-13 18:57:35 +09001613func TestVersioningMacro(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001614 t.Parallel()
Jooyung Hanb04a4992020-03-13 18:57:35 +09001615 for _, tc := range []struct{ moduleName, expected string }{
1616 {"libc", "__LIBC_API__"},
1617 {"libfoo", "__LIBFOO_API__"},
1618 {"libfoo@1", "__LIBFOO_1_API__"},
1619 {"libfoo-v1", "__LIBFOO_V1_API__"},
1620 {"libfoo.v1", "__LIBFOO_V1_API__"},
1621 } {
1622 checkEquals(t, tc.moduleName, tc.expected, versioningMacroName(tc.moduleName))
1623 }
1624}
1625
Liz Kammer83cf81b2022-09-22 08:24:20 -04001626func pathsToBase(paths android.Paths) []string {
1627 var ret []string
1628 for _, p := range paths {
1629 ret = append(ret, p.Base())
1630 }
1631 return ret
1632}
1633
1634func TestStaticLibArchiveArgs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001635 t.Parallel()
Liz Kammer83cf81b2022-09-22 08:24:20 -04001636 ctx := testCc(t, `
1637 cc_library_static {
1638 name: "foo",
1639 srcs: ["foo.c"],
1640 }
1641
1642 cc_library_static {
1643 name: "bar",
1644 srcs: ["bar.c"],
1645 }
1646
1647 cc_library_shared {
1648 name: "qux",
1649 srcs: ["qux.c"],
1650 }
1651
1652 cc_library_static {
1653 name: "baz",
1654 srcs: ["baz.c"],
1655 static_libs: ["foo"],
1656 shared_libs: ["qux"],
1657 whole_static_libs: ["bar"],
1658 }`)
1659
1660 variant := "android_arm64_armv8-a_static"
1661 arRule := ctx.ModuleForTests("baz", variant).Rule("ar")
1662
1663 // For static libraries, the object files of a whole static dep are included in the archive
1664 // directly
1665 if g, w := pathsToBase(arRule.Inputs), []string{"bar.o", "baz.o"}; !reflect.DeepEqual(w, g) {
1666 t.Errorf("Expected input objects %q, got %q", w, g)
1667 }
1668
1669 // non whole static dependencies are not linked into the archive
1670 if len(arRule.Implicits) > 0 {
1671 t.Errorf("Expected 0 additional deps, got %q", arRule.Implicits)
1672 }
1673}
1674
1675func TestSharedLibLinkingArgs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001676 t.Parallel()
Liz Kammer83cf81b2022-09-22 08:24:20 -04001677 ctx := testCc(t, `
1678 cc_library_static {
1679 name: "foo",
1680 srcs: ["foo.c"],
1681 }
1682
1683 cc_library_static {
1684 name: "bar",
1685 srcs: ["bar.c"],
1686 }
1687
1688 cc_library_shared {
1689 name: "qux",
1690 srcs: ["qux.c"],
1691 }
1692
1693 cc_library_shared {
1694 name: "baz",
1695 srcs: ["baz.c"],
1696 static_libs: ["foo"],
1697 shared_libs: ["qux"],
1698 whole_static_libs: ["bar"],
1699 }`)
1700
1701 variant := "android_arm64_armv8-a_shared"
1702 linkRule := ctx.ModuleForTests("baz", variant).Rule("ld")
1703 libFlags := linkRule.Args["libFlags"]
1704 // When dynamically linking, we expect static dependencies to be found on the command line
1705 if expected := "foo.a"; !strings.Contains(libFlags, expected) {
1706 t.Errorf("Static lib %q was not found in %q", expected, libFlags)
1707 }
1708 // When dynamically linking, we expect whole static dependencies to be found on the command line
1709 if expected := "bar.a"; !strings.Contains(libFlags, expected) {
1710 t.Errorf("Static lib %q was not found in %q", expected, libFlags)
1711 }
1712
1713 // When dynamically linking, we expect shared dependencies to be found on the command line
1714 if expected := "qux.so"; !strings.Contains(libFlags, expected) {
1715 t.Errorf("Shared lib %q was not found in %q", expected, libFlags)
1716 }
1717
1718 // We should only have the objects from the shared library srcs, not the whole static dependencies
1719 if g, w := pathsToBase(linkRule.Inputs), []string{"baz.o"}; !reflect.DeepEqual(w, g) {
1720 t.Errorf("Expected input objects %q, got %q", w, g)
1721 }
1722}
1723
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001724func TestStaticExecutable(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001725 t.Parallel()
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001726 ctx := testCc(t, `
1727 cc_binary {
1728 name: "static_test",
Pete Bentleyfcf55bf2019-08-16 20:14:32 +01001729 srcs: ["foo.c", "baz.o"],
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001730 static_executable: true,
1731 }`)
1732
Colin Cross7113d202019-11-20 16:39:12 -08001733 variant := "android_arm64_armv8-a"
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001734 binModuleRule := ctx.ModuleForTests("static_test", variant).Rule("ld")
1735 libFlags := binModuleRule.Args["libFlags"]
Ryan Prichardb49fe1b2019-10-11 15:03:34 -07001736 systemStaticLibs := []string{"libc.a", "libm.a"}
Jaewoong Jung232c07c2018-12-18 11:08:25 -08001737 for _, lib := range systemStaticLibs {
1738 if !strings.Contains(libFlags, lib) {
1739 t.Errorf("Static lib %q was not found in %q", lib, libFlags)
1740 }
1741 }
1742 systemSharedLibs := []string{"libc.so", "libm.so", "libdl.so"}
1743 for _, lib := range systemSharedLibs {
1744 if strings.Contains(libFlags, lib) {
1745 t.Errorf("Shared lib %q was found in %q", lib, libFlags)
1746 }
1747 }
1748}
Jiyong Parke4bb9862019-02-01 00:31:10 +09001749
1750func TestStaticDepsOrderWithStubs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001751 t.Parallel()
Jiyong Parke4bb9862019-02-01 00:31:10 +09001752 ctx := testCc(t, `
1753 cc_binary {
1754 name: "mybin",
1755 srcs: ["foo.c"],
Colin Cross0de8a1e2020-09-18 14:15:30 -07001756 static_libs: ["libfooC", "libfooB"],
Jiyong Parke4bb9862019-02-01 00:31:10 +09001757 static_executable: true,
1758 stl: "none",
1759 }
1760
1761 cc_library {
Colin Crossf9aabd72020-02-15 11:29:50 -08001762 name: "libfooB",
Jiyong Parke4bb9862019-02-01 00:31:10 +09001763 srcs: ["foo.c"],
Colin Crossf9aabd72020-02-15 11:29:50 -08001764 shared_libs: ["libfooC"],
Jiyong Parke4bb9862019-02-01 00:31:10 +09001765 stl: "none",
1766 }
1767
1768 cc_library {
Colin Crossf9aabd72020-02-15 11:29:50 -08001769 name: "libfooC",
Jiyong Parke4bb9862019-02-01 00:31:10 +09001770 srcs: ["foo.c"],
1771 stl: "none",
1772 stubs: {
1773 versions: ["1"],
1774 },
1775 }`)
1776
Colin Cross0de8a1e2020-09-18 14:15:30 -07001777 mybin := ctx.ModuleForTests("mybin", "android_arm64_armv8-a").Rule("ld")
1778 actual := mybin.Implicits[:2]
Ivan Lozanod67a6b02021-05-20 13:01:32 -04001779 expected := GetOutputPaths(ctx, "android_arm64_armv8-a_static", []string{"libfooB", "libfooC"})
Jiyong Parke4bb9862019-02-01 00:31:10 +09001780
1781 if !reflect.DeepEqual(actual, expected) {
1782 t.Errorf("staticDeps orderings were not propagated correctly"+
1783 "\nactual: %v"+
1784 "\nexpected: %v",
1785 actual,
1786 expected,
1787 )
1788 }
1789}
Jooyung Han38002912019-05-16 04:01:54 +09001790
Jooyung Hand48f3c32019-08-23 11:18:57 +09001791func TestErrorsIfAModuleDependsOnDisabled(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001792 t.Parallel()
Jooyung Hand48f3c32019-08-23 11:18:57 +09001793 testCcError(t, `module "libA" .* depends on disabled module "libB"`, `
1794 cc_library {
1795 name: "libA",
1796 srcs: ["foo.c"],
1797 shared_libs: ["libB"],
1798 stl: "none",
1799 }
1800
1801 cc_library {
1802 name: "libB",
1803 srcs: ["foo.c"],
1804 enabled: false,
1805 stl: "none",
1806 }
1807 `)
1808}
1809
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001810func VerifyAFLFuzzTargetVariant(t *testing.T, variant string) {
1811 bp := `
1812 cc_fuzz {
Cory Barkera1da26f2022-06-07 20:12:06 +00001813 name: "test_afl_fuzz_target",
1814 srcs: ["foo.c"],
1815 host_supported: true,
1816 static_libs: [
1817 "afl_fuzz_static_lib",
1818 ],
1819 shared_libs: [
1820 "afl_fuzz_shared_lib",
1821 ],
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001822 fuzzing_frameworks: {
1823 afl: true,
1824 libfuzzer: false,
1825 },
Cory Barkera1da26f2022-06-07 20:12:06 +00001826 }
1827 cc_library {
1828 name: "afl_fuzz_static_lib",
1829 host_supported: true,
1830 srcs: ["static_file.c"],
1831 }
1832 cc_library {
1833 name: "libfuzzer_only_static_lib",
1834 host_supported: true,
1835 srcs: ["static_file.c"],
1836 }
1837 cc_library {
1838 name: "afl_fuzz_shared_lib",
1839 host_supported: true,
1840 srcs: ["shared_file.c"],
1841 static_libs: [
1842 "second_static_lib",
1843 ],
1844 }
1845 cc_library_headers {
1846 name: "libafl_headers",
1847 vendor_available: true,
1848 host_supported: true,
1849 export_include_dirs: [
1850 "include",
1851 "instrumentation",
1852 ],
1853 }
1854 cc_object {
1855 name: "afl-compiler-rt",
1856 vendor_available: true,
1857 host_supported: true,
1858 cflags: [
1859 "-fPIC",
1860 ],
1861 srcs: [
1862 "instrumentation/afl-compiler-rt.o.c",
1863 ],
1864 }
1865 cc_library {
1866 name: "second_static_lib",
1867 host_supported: true,
1868 srcs: ["second_file.c"],
1869 }
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001870 cc_object {
Cory Barkera1da26f2022-06-07 20:12:06 +00001871 name: "aflpp_driver",
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001872 host_supported: true,
Cory Barkera1da26f2022-06-07 20:12:06 +00001873 srcs: [
1874 "aflpp_driver.c",
1875 ],
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001876 }`
1877
1878 testEnv := map[string]string{
1879 "FUZZ_FRAMEWORK": "AFL",
1880 }
1881
1882 ctx := android.GroupFixturePreparers(prepareForCcTest, android.FixtureMergeEnv(testEnv)).RunTestWithBp(t, bp)
Cory Barkera1da26f2022-06-07 20:12:06 +00001883
1884 checkPcGuardFlag := func(
1885 modName string, variantName string, shouldHave bool) {
1886 cc := ctx.ModuleForTests(modName, variantName).Rule("cc")
1887
1888 cFlags, ok := cc.Args["cFlags"]
1889 if !ok {
1890 t.Errorf("Could not find cFlags for module %s and variant %s",
1891 modName, variantName)
1892 }
1893
1894 if strings.Contains(
1895 cFlags, "-fsanitize-coverage=trace-pc-guard") != shouldHave {
1896 t.Errorf("Flag was found: %t. Expected to find flag: %t. "+
1897 "Test failed for module %s and variant %s",
1898 !shouldHave, shouldHave, modName, variantName)
1899 }
1900 }
1901
Cory Barkera1da26f2022-06-07 20:12:06 +00001902 moduleName := "test_afl_fuzz_target"
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001903 checkPcGuardFlag(moduleName, variant+"_fuzzer", true)
Cory Barkera1da26f2022-06-07 20:12:06 +00001904
1905 moduleName = "afl_fuzz_static_lib"
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001906 checkPcGuardFlag(moduleName, variant+"_static", false)
Colin Cross597bad62024-10-08 15:10:55 -07001907 checkPcGuardFlag(moduleName, variant+"_static_fuzzer_afl", true)
Cory Barkera1da26f2022-06-07 20:12:06 +00001908
1909 moduleName = "second_static_lib"
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001910 checkPcGuardFlag(moduleName, variant+"_static", false)
Colin Cross597bad62024-10-08 15:10:55 -07001911 checkPcGuardFlag(moduleName, variant+"_static_fuzzer_afl", true)
Cory Barkera1da26f2022-06-07 20:12:06 +00001912
1913 ctx.ModuleForTests("afl_fuzz_shared_lib",
1914 "android_arm64_armv8-a_shared").Rule("cc")
1915 ctx.ModuleForTests("afl_fuzz_shared_lib",
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001916 "android_arm64_armv8-a_shared_fuzzer").Rule("cc")
1917}
1918
1919func TestAFLFuzzTargetForDevice(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001920 t.Parallel()
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001921 VerifyAFLFuzzTargetVariant(t, "android_arm64_armv8-a")
1922}
1923
1924func TestAFLFuzzTargetForLinuxHost(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001925 t.Parallel()
Cory Barker9cfcf6d2022-07-22 17:22:02 +00001926 if runtime.GOOS != "linux" {
1927 t.Skip("requires linux")
1928 }
1929
1930 VerifyAFLFuzzTargetVariant(t, "linux_glibc_x86_64")
Cory Barkera1da26f2022-06-07 20:12:06 +00001931}
1932
Mitch Phillipsda9a4632019-07-15 09:34:09 -07001933// Simple smoke test for the cc_fuzz target that ensures the rule compiles
1934// correctly.
1935func TestFuzzTarget(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001936 t.Parallel()
Mitch Phillipsda9a4632019-07-15 09:34:09 -07001937 ctx := testCc(t, `
1938 cc_fuzz {
1939 name: "fuzz_smoke_test",
1940 srcs: ["foo.c"],
1941 }`)
1942
Paul Duffin075c4172019-12-19 19:06:13 +00001943 variant := "android_arm64_armv8-a_fuzzer"
Mitch Phillipsda9a4632019-07-15 09:34:09 -07001944 ctx.ModuleForTests("fuzz_smoke_test", variant).Rule("cc")
1945}
1946
Jooyung Han38002912019-05-16 04:01:54 +09001947func assertString(t *testing.T, got, expected string) {
1948 t.Helper()
1949 if got != expected {
1950 t.Errorf("expected %q got %q", expected, got)
1951 }
1952}
1953
1954func assertArrayString(t *testing.T, got, expected []string) {
1955 t.Helper()
1956 if len(got) != len(expected) {
1957 t.Errorf("expected %d (%q) got (%d) %q", len(expected), expected, len(got), got)
1958 return
1959 }
1960 for i := range got {
1961 if got[i] != expected[i] {
1962 t.Errorf("expected %d-th %q (%q) got %q (%q)",
1963 i, expected[i], expected, got[i], got)
1964 return
1965 }
1966 }
1967}
Colin Crosse1bb5d02019-09-24 14:55:04 -07001968
Jooyung Han0302a842019-10-30 18:43:49 +09001969func assertMapKeys(t *testing.T, m map[string]string, expected []string) {
1970 t.Helper()
Cole Faust18994c72023-02-28 16:02:16 -08001971 assertArrayString(t, android.SortedKeys(m), expected)
Jooyung Han0302a842019-10-30 18:43:49 +09001972}
1973
Colin Crosse1bb5d02019-09-24 14:55:04 -07001974func TestDefaults(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04001975 t.Parallel()
Colin Crosse1bb5d02019-09-24 14:55:04 -07001976 ctx := testCc(t, `
1977 cc_defaults {
1978 name: "defaults",
1979 srcs: ["foo.c"],
1980 static: {
1981 srcs: ["bar.c"],
1982 },
1983 shared: {
1984 srcs: ["baz.c"],
1985 },
1986 }
1987
1988 cc_library_static {
1989 name: "libstatic",
1990 defaults: ["defaults"],
1991 }
1992
1993 cc_library_shared {
1994 name: "libshared",
1995 defaults: ["defaults"],
1996 }
1997
1998 cc_library {
1999 name: "libboth",
2000 defaults: ["defaults"],
2001 }
2002
2003 cc_binary {
2004 name: "binary",
2005 defaults: ["defaults"],
2006 }`)
2007
Colin Cross7113d202019-11-20 16:39:12 -08002008 shared := ctx.ModuleForTests("libshared", "android_arm64_armv8-a_shared").Rule("ld")
Colin Crosse1bb5d02019-09-24 14:55:04 -07002009 if g, w := pathsToBase(shared.Inputs), []string{"foo.o", "baz.o"}; !reflect.DeepEqual(w, g) {
2010 t.Errorf("libshared ld rule wanted %q, got %q", w, g)
2011 }
Colin Cross7113d202019-11-20 16:39:12 -08002012 bothShared := ctx.ModuleForTests("libboth", "android_arm64_armv8-a_shared").Rule("ld")
Colin Crosse1bb5d02019-09-24 14:55:04 -07002013 if g, w := pathsToBase(bothShared.Inputs), []string{"foo.o", "baz.o"}; !reflect.DeepEqual(w, g) {
2014 t.Errorf("libboth ld rule wanted %q, got %q", w, g)
2015 }
Colin Cross7113d202019-11-20 16:39:12 -08002016 binary := ctx.ModuleForTests("binary", "android_arm64_armv8-a").Rule("ld")
Colin Crosse1bb5d02019-09-24 14:55:04 -07002017 if g, w := pathsToBase(binary.Inputs), []string{"foo.o"}; !reflect.DeepEqual(w, g) {
2018 t.Errorf("binary ld rule wanted %q, got %q", w, g)
2019 }
2020
Colin Cross7113d202019-11-20 16:39:12 -08002021 static := ctx.ModuleForTests("libstatic", "android_arm64_armv8-a_static").Rule("ar")
Colin Crosse1bb5d02019-09-24 14:55:04 -07002022 if g, w := pathsToBase(static.Inputs), []string{"foo.o", "bar.o"}; !reflect.DeepEqual(w, g) {
2023 t.Errorf("libstatic ar rule wanted %q, got %q", w, g)
2024 }
Colin Cross7113d202019-11-20 16:39:12 -08002025 bothStatic := ctx.ModuleForTests("libboth", "android_arm64_armv8-a_static").Rule("ar")
Colin Crosse1bb5d02019-09-24 14:55:04 -07002026 if g, w := pathsToBase(bothStatic.Inputs), []string{"foo.o", "bar.o"}; !reflect.DeepEqual(w, g) {
2027 t.Errorf("libboth ar rule wanted %q, got %q", w, g)
2028 }
2029}
Colin Crosseabaedd2020-02-06 17:01:55 -08002030
2031func TestProductVariableDefaults(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002032 t.Parallel()
Colin Crosseabaedd2020-02-06 17:01:55 -08002033 bp := `
2034 cc_defaults {
2035 name: "libfoo_defaults",
2036 srcs: ["foo.c"],
2037 cppflags: ["-DFOO"],
2038 product_variables: {
2039 debuggable: {
2040 cppflags: ["-DBAR"],
2041 },
2042 },
2043 }
2044
2045 cc_library {
2046 name: "libfoo",
2047 defaults: ["libfoo_defaults"],
2048 }
2049 `
2050
Paul Duffin8567f222021-03-23 00:02:06 +00002051 result := android.GroupFixturePreparers(
2052 prepareForCcTest,
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002053 android.PrepareForTestWithVariables,
Colin Crosseabaedd2020-02-06 17:01:55 -08002054
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002055 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
2056 variables.Debuggable = BoolPtr(true)
2057 }),
2058 ).RunTestWithBp(t, bp)
Colin Crosseabaedd2020-02-06 17:01:55 -08002059
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002060 libfoo := result.Module("libfoo", "android_arm64_armv8-a_static").(*Module)
Paul Duffine84b1332021-03-12 11:59:43 +00002061 android.AssertStringListContains(t, "cppflags", libfoo.flags.Local.CppFlags, "-DBAR")
Colin Crosseabaedd2020-02-06 17:01:55 -08002062}
Colin Crosse4f6eba2020-09-22 18:11:25 -07002063
2064func TestEmptyWholeStaticLibsAllowMissingDependencies(t *testing.T) {
2065 t.Parallel()
2066 bp := `
2067 cc_library_static {
2068 name: "libfoo",
2069 srcs: ["foo.c"],
2070 whole_static_libs: ["libbar"],
2071 }
2072
2073 cc_library_static {
2074 name: "libbar",
2075 whole_static_libs: ["libmissing"],
2076 }
2077 `
2078
Paul Duffin8567f222021-03-23 00:02:06 +00002079 result := android.GroupFixturePreparers(
2080 prepareForCcTest,
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002081 android.PrepareForTestWithAllowMissingDependencies,
2082 ).RunTestWithBp(t, bp)
Colin Crosse4f6eba2020-09-22 18:11:25 -07002083
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002084 libbar := result.ModuleForTests("libbar", "android_arm64_armv8-a_static").Output("libbar.a")
Paul Duffine84b1332021-03-12 11:59:43 +00002085 android.AssertDeepEquals(t, "libbar rule", android.ErrorRule, libbar.Rule)
Colin Crosse4f6eba2020-09-22 18:11:25 -07002086
Paul Duffine84b1332021-03-12 11:59:43 +00002087 android.AssertStringDoesContain(t, "libbar error", libbar.Args["error"], "missing dependencies: libmissing")
Colin Crosse4f6eba2020-09-22 18:11:25 -07002088
Paul Duffin7d8a8ad2021-03-07 15:58:39 +00002089 libfoo := result.ModuleForTests("libfoo", "android_arm64_armv8-a_static").Output("libfoo.a")
Paul Duffine84b1332021-03-12 11:59:43 +00002090 android.AssertStringListContains(t, "libfoo.a dependencies", libfoo.Inputs.Strings(), libbar.Output.String())
Colin Crosse4f6eba2020-09-22 18:11:25 -07002091}
Colin Crosse9fe2942020-11-10 18:12:15 -08002092
2093func TestInstallSharedLibs(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002094 t.Parallel()
Colin Crosse9fe2942020-11-10 18:12:15 -08002095 bp := `
2096 cc_binary {
2097 name: "bin",
2098 host_supported: true,
2099 shared_libs: ["libshared"],
2100 runtime_libs: ["libruntime"],
2101 srcs: [":gen"],
2102 }
2103
2104 cc_library_shared {
2105 name: "libshared",
2106 host_supported: true,
2107 shared_libs: ["libtransitive"],
2108 }
2109
2110 cc_library_shared {
2111 name: "libtransitive",
2112 host_supported: true,
2113 }
2114
2115 cc_library_shared {
2116 name: "libruntime",
2117 host_supported: true,
2118 }
2119
2120 cc_binary_host {
2121 name: "tool",
2122 srcs: ["foo.cpp"],
2123 }
2124
2125 genrule {
2126 name: "gen",
2127 tools: ["tool"],
2128 out: ["gen.cpp"],
2129 cmd: "$(location tool) $(out)",
2130 }
2131 `
2132
Paul Duffinc3e6ce02021-03-22 23:21:32 +00002133 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
Colin Crosse9fe2942020-11-10 18:12:15 -08002134 ctx := testCcWithConfig(t, config)
2135
2136 hostBin := ctx.ModuleForTests("bin", config.BuildOSTarget.String()).Description("install")
2137 hostShared := ctx.ModuleForTests("libshared", config.BuildOSTarget.String()+"_shared").Description("install")
2138 hostRuntime := ctx.ModuleForTests("libruntime", config.BuildOSTarget.String()+"_shared").Description("install")
2139 hostTransitive := ctx.ModuleForTests("libtransitive", config.BuildOSTarget.String()+"_shared").Description("install")
2140 hostTool := ctx.ModuleForTests("tool", config.BuildOSTarget.String()).Description("install")
2141
2142 if g, w := hostBin.Implicits.Strings(), hostShared.Output.String(); !android.InList(w, g) {
2143 t.Errorf("expected host bin dependency %q, got %q", w, g)
2144 }
2145
2146 if g, w := hostBin.Implicits.Strings(), hostTransitive.Output.String(); !android.InList(w, g) {
2147 t.Errorf("expected host bin dependency %q, got %q", w, g)
2148 }
2149
2150 if g, w := hostShared.Implicits.Strings(), hostTransitive.Output.String(); !android.InList(w, g) {
2151 t.Errorf("expected host bin dependency %q, got %q", w, g)
2152 }
2153
2154 if g, w := hostBin.Implicits.Strings(), hostRuntime.Output.String(); !android.InList(w, g) {
2155 t.Errorf("expected host bin dependency %q, got %q", w, g)
2156 }
2157
2158 if g, w := hostBin.Implicits.Strings(), hostTool.Output.String(); android.InList(w, g) {
2159 t.Errorf("expected no host bin dependency %q, got %q", w, g)
2160 }
2161
2162 deviceBin := ctx.ModuleForTests("bin", "android_arm64_armv8-a").Description("install")
2163 deviceShared := ctx.ModuleForTests("libshared", "android_arm64_armv8-a_shared").Description("install")
2164 deviceTransitive := ctx.ModuleForTests("libtransitive", "android_arm64_armv8-a_shared").Description("install")
2165 deviceRuntime := ctx.ModuleForTests("libruntime", "android_arm64_armv8-a_shared").Description("install")
2166
2167 if g, w := deviceBin.OrderOnly.Strings(), deviceShared.Output.String(); !android.InList(w, g) {
2168 t.Errorf("expected device bin dependency %q, got %q", w, g)
2169 }
2170
2171 if g, w := deviceBin.OrderOnly.Strings(), deviceTransitive.Output.String(); !android.InList(w, g) {
2172 t.Errorf("expected device bin dependency %q, got %q", w, g)
2173 }
2174
2175 if g, w := deviceShared.OrderOnly.Strings(), deviceTransitive.Output.String(); !android.InList(w, g) {
2176 t.Errorf("expected device bin dependency %q, got %q", w, g)
2177 }
2178
2179 if g, w := deviceBin.OrderOnly.Strings(), deviceRuntime.Output.String(); !android.InList(w, g) {
2180 t.Errorf("expected device bin dependency %q, got %q", w, g)
2181 }
2182
2183 if g, w := deviceBin.OrderOnly.Strings(), hostTool.Output.String(); android.InList(w, g) {
2184 t.Errorf("expected no device bin dependency %q, got %q", w, g)
2185 }
2186
2187}
Jiyong Park1ad8e162020-12-01 23:40:09 +09002188
2189func TestStubsLibReexportsHeaders(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002190 t.Parallel()
Jiyong Park1ad8e162020-12-01 23:40:09 +09002191 ctx := testCc(t, `
2192 cc_library_shared {
2193 name: "libclient",
2194 srcs: ["foo.c"],
2195 shared_libs: ["libfoo#1"],
2196 }
2197
2198 cc_library_shared {
2199 name: "libfoo",
2200 srcs: ["foo.c"],
2201 shared_libs: ["libbar"],
2202 export_shared_lib_headers: ["libbar"],
2203 stubs: {
2204 symbol_file: "foo.map.txt",
2205 versions: ["1", "2", "3"],
2206 },
2207 }
2208
2209 cc_library_shared {
2210 name: "libbar",
2211 export_include_dirs: ["include/libbar"],
2212 srcs: ["foo.c"],
2213 }`)
2214
2215 cFlags := ctx.ModuleForTests("libclient", "android_arm64_armv8-a_shared").Rule("cc").Args["cFlags"]
2216
2217 if !strings.Contains(cFlags, "-Iinclude/libbar") {
2218 t.Errorf("expected %q in cflags, got %q", "-Iinclude/libbar", cFlags)
2219 }
2220}
Jooyung Hane197d8b2021-01-05 10:33:16 +09002221
Vinh Tran09581952023-05-16 16:03:20 -04002222func TestAidlLibraryWithHeaders(t *testing.T) {
Vinh Tran367d89d2023-04-28 11:21:25 -04002223 t.Parallel()
2224 ctx := android.GroupFixturePreparers(
2225 prepareForCcTest,
2226 aidl_library.PrepareForTestWithAidlLibrary,
2227 android.MockFS{
2228 "package_bar/Android.bp": []byte(`
2229 aidl_library {
2230 name: "bar",
2231 srcs: ["x/y/Bar.aidl"],
Vinh Tran09581952023-05-16 16:03:20 -04002232 hdrs: ["x/HeaderBar.aidl"],
Vinh Tran367d89d2023-04-28 11:21:25 -04002233 strip_import_prefix: "x",
2234 }
2235 `)}.AddToFixture(),
2236 android.MockFS{
2237 "package_foo/Android.bp": []byte(`
2238 aidl_library {
2239 name: "foo",
2240 srcs: ["a/b/Foo.aidl"],
Vinh Tran09581952023-05-16 16:03:20 -04002241 hdrs: ["a/HeaderFoo.aidl"],
Vinh Tran367d89d2023-04-28 11:21:25 -04002242 strip_import_prefix: "a",
2243 deps: ["bar"],
2244 }
2245 cc_library {
2246 name: "libfoo",
2247 aidl: {
2248 libs: ["foo"],
2249 }
2250 }
2251 `),
2252 }.AddToFixture(),
2253 ).RunTest(t).TestContext
2254
2255 libfoo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_static")
Vinh Tran09581952023-05-16 16:03:20 -04002256
2257 android.AssertPathsRelativeToTopEquals(
2258 t,
2259 "aidl headers",
2260 []string{
2261 "package_bar/x/HeaderBar.aidl",
2262 "package_foo/a/HeaderFoo.aidl",
2263 "package_foo/a/b/Foo.aidl",
2264 "out/soong/.intermediates/package_foo/libfoo/android_arm64_armv8-a_static/gen/aidl_library.sbox.textproto",
2265 },
2266 libfoo.Rule("aidl_library").Implicits,
2267 )
2268
Colin Crossf61d03d2023-11-02 16:56:39 -07002269 manifest := android.RuleBuilderSboxProtoForTests(t, ctx, libfoo.Output("aidl_library.sbox.textproto"))
Vinh Tran367d89d2023-04-28 11:21:25 -04002270 aidlCommand := manifest.Commands[0].GetCommand()
2271
2272 expectedAidlFlags := "-Ipackage_foo/a -Ipackage_bar/x"
2273 if !strings.Contains(aidlCommand, expectedAidlFlags) {
2274 t.Errorf("aidl command %q does not contain %q", aidlCommand, expectedAidlFlags)
2275 }
2276
2277 outputs := strings.Join(libfoo.AllOutputs(), " ")
2278
Vinh Tran09581952023-05-16 16:03:20 -04002279 android.AssertStringDoesContain(t, "aidl-generated header", outputs, "gen/aidl_library/b/BpFoo.h")
2280 android.AssertStringDoesContain(t, "aidl-generated header", outputs, "gen/aidl_library/b/BnFoo.h")
2281 android.AssertStringDoesContain(t, "aidl-generated header", outputs, "gen/aidl_library/b/Foo.h")
Vinh Tran367d89d2023-04-28 11:21:25 -04002282 android.AssertStringDoesContain(t, "aidl-generated cpp", outputs, "b/Foo.cpp")
2283 // Confirm that the aidl header doesn't get compiled to cpp and h files
Vinh Tran09581952023-05-16 16:03:20 -04002284 android.AssertStringDoesNotContain(t, "aidl-generated header", outputs, "gen/aidl_library/y/BpBar.h")
2285 android.AssertStringDoesNotContain(t, "aidl-generated header", outputs, "gen/aidl_library/y/BnBar.h")
2286 android.AssertStringDoesNotContain(t, "aidl-generated header", outputs, "gen/aidl_library/y/Bar.h")
Vinh Tran367d89d2023-04-28 11:21:25 -04002287 android.AssertStringDoesNotContain(t, "aidl-generated cpp", outputs, "y/Bar.cpp")
2288}
2289
Jooyung Hane197d8b2021-01-05 10:33:16 +09002290func TestAidlFlagsPassedToTheAidlCompiler(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002291 t.Parallel()
Vinh Tran367d89d2023-04-28 11:21:25 -04002292 ctx := android.GroupFixturePreparers(
2293 prepareForCcTest,
2294 aidl_library.PrepareForTestWithAidlLibrary,
2295 ).RunTestWithBp(t, `
Jooyung Hane197d8b2021-01-05 10:33:16 +09002296 cc_library {
2297 name: "libfoo",
2298 srcs: ["a/Foo.aidl"],
2299 aidl: { flags: ["-Werror"], },
2300 }
2301 `)
2302
2303 libfoo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_static")
Colin Crossf61d03d2023-11-02 16:56:39 -07002304 manifest := android.RuleBuilderSboxProtoForTests(t, ctx.TestContext, libfoo.Output("aidl.sbox.textproto"))
Jooyung Hane197d8b2021-01-05 10:33:16 +09002305 aidlCommand := manifest.Commands[0].GetCommand()
2306 expectedAidlFlag := "-Werror"
2307 if !strings.Contains(aidlCommand, expectedAidlFlag) {
2308 t.Errorf("aidl command %q does not contain %q", aidlCommand, expectedAidlFlag)
2309 }
2310}
Evgenii Stepanov193ac2e2020-04-28 15:09:12 -07002311
Jooyung Han07f70c02021-11-06 07:08:45 +09002312func TestAidlFlagsWithMinSdkVersion(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002313 t.Parallel()
Jooyung Han07f70c02021-11-06 07:08:45 +09002314 for _, tc := range []struct {
2315 name string
2316 sdkVersion string
2317 variant string
2318 expected string
2319 }{
2320 {
2321 name: "default is current",
2322 sdkVersion: "",
2323 variant: "android_arm64_armv8-a_static",
2324 expected: "platform_apis",
2325 },
2326 {
2327 name: "use sdk_version",
2328 sdkVersion: `sdk_version: "29"`,
2329 variant: "android_arm64_armv8-a_static",
2330 expected: "platform_apis",
2331 },
2332 {
2333 name: "use sdk_version(sdk variant)",
2334 sdkVersion: `sdk_version: "29"`,
2335 variant: "android_arm64_armv8-a_sdk_static",
2336 expected: "29",
2337 },
2338 {
2339 name: "use min_sdk_version",
2340 sdkVersion: `min_sdk_version: "29"`,
2341 variant: "android_arm64_armv8-a_static",
2342 expected: "29",
2343 },
2344 } {
2345 t.Run(tc.name, func(t *testing.T) {
2346 ctx := testCc(t, `
2347 cc_library {
2348 name: "libfoo",
2349 stl: "none",
2350 srcs: ["a/Foo.aidl"],
2351 `+tc.sdkVersion+`
2352 }
2353 `)
2354 libfoo := ctx.ModuleForTests("libfoo", tc.variant)
Colin Crossf61d03d2023-11-02 16:56:39 -07002355 manifest := android.RuleBuilderSboxProtoForTests(t, ctx, libfoo.Output("aidl.sbox.textproto"))
Jooyung Han07f70c02021-11-06 07:08:45 +09002356 aidlCommand := manifest.Commands[0].GetCommand()
2357 expectedAidlFlag := "--min_sdk_version=" + tc.expected
2358 if !strings.Contains(aidlCommand, expectedAidlFlag) {
2359 t.Errorf("aidl command %q does not contain %q", aidlCommand, expectedAidlFlag)
2360 }
2361 })
2362 }
2363}
2364
Vinh Tran09581952023-05-16 16:03:20 -04002365func TestInvalidAidlProp(t *testing.T) {
2366 t.Parallel()
2367
2368 testCases := []struct {
2369 description string
2370 bp string
2371 }{
2372 {
2373 description: "Invalid use of aidl.libs and aidl.include_dirs",
2374 bp: `
2375 cc_library {
2376 name: "foo",
2377 aidl: {
2378 libs: ["foo_aidl"],
2379 include_dirs: ["bar/include"],
2380 }
2381 }
2382 `,
2383 },
2384 {
2385 description: "Invalid use of aidl.libs and aidl.local_include_dirs",
2386 bp: `
2387 cc_library {
2388 name: "foo",
2389 aidl: {
2390 libs: ["foo_aidl"],
2391 local_include_dirs: ["include"],
2392 }
2393 }
2394 `,
2395 },
2396 }
2397
2398 for _, testCase := range testCases {
2399 t.Run(testCase.description, func(t *testing.T) {
2400 bp := `
2401 aidl_library {
2402 name: "foo_aidl",
2403 srcs: ["Foo.aidl"],
2404 } ` + testCase.bp
2405 android.GroupFixturePreparers(
2406 prepareForCcTest,
2407 aidl_library.PrepareForTestWithAidlLibrary.
2408 ExtendWithErrorHandler(android.FixtureExpectsOneErrorPattern("For aidl headers, please only use aidl.libs prop")),
2409 ).RunTestWithBp(t, bp)
2410 })
2411 }
2412}
2413
Jiyong Parka008fb02021-03-16 17:15:53 +09002414func TestMinSdkVersionInClangTriple(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002415 t.Parallel()
Jiyong Parka008fb02021-03-16 17:15:53 +09002416 ctx := testCc(t, `
2417 cc_library_shared {
2418 name: "libfoo",
2419 srcs: ["foo.c"],
2420 min_sdk_version: "29",
2421 }`)
2422
2423 cFlags := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Rule("cc").Args["cFlags"]
2424 android.AssertStringDoesContain(t, "min sdk version", cFlags, "-target aarch64-linux-android29")
2425}
2426
Vinh Tranf1924742022-06-24 16:40:11 -04002427func TestNonDigitMinSdkVersionInClangTriple(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002428 t.Parallel()
Vinh Tranf1924742022-06-24 16:40:11 -04002429 bp := `
2430 cc_library_shared {
2431 name: "libfoo",
2432 srcs: ["foo.c"],
2433 min_sdk_version: "S",
2434 }
2435 `
2436 result := android.GroupFixturePreparers(
2437 prepareForCcTest,
2438 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
2439 variables.Platform_version_active_codenames = []string{"UpsideDownCake", "Tiramisu"}
2440 }),
2441 ).RunTestWithBp(t, bp)
2442 ctx := result.TestContext
2443 cFlags := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Rule("cc").Args["cFlags"]
2444 android.AssertStringDoesContain(t, "min sdk version", cFlags, "-target aarch64-linux-android31")
2445}
2446
Paul Duffin3cb603e2021-02-19 13:57:10 +00002447func TestIncludeDirsExporting(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002448 t.Parallel()
Paul Duffin3cb603e2021-02-19 13:57:10 +00002449
2450 // Trim spaces from the beginning, end and immediately after any newline characters. Leaves
2451 // embedded newline characters alone.
2452 trimIndentingSpaces := func(s string) string {
2453 return strings.TrimSpace(regexp.MustCompile("(^|\n)\\s+").ReplaceAllString(s, "$1"))
2454 }
2455
2456 checkPaths := func(t *testing.T, message string, expected string, paths android.Paths) {
2457 t.Helper()
2458 expected = trimIndentingSpaces(expected)
2459 actual := trimIndentingSpaces(strings.Join(android.FirstUniqueStrings(android.NormalizePathsForTesting(paths)), "\n"))
2460 if expected != actual {
2461 t.Errorf("%s: expected:\n%s\n actual:\n%s\n", message, expected, actual)
2462 }
2463 }
2464
2465 type exportedChecker func(t *testing.T, name string, exported FlagExporterInfo)
2466
2467 checkIncludeDirs := func(t *testing.T, ctx *android.TestContext, module android.Module, checkers ...exportedChecker) {
2468 t.Helper()
Yu Liu663e4502024-08-12 18:23:59 +00002469 exported, _ := android.OtherModuleProvider(ctx, module, FlagExporterInfoProvider)
Paul Duffin3cb603e2021-02-19 13:57:10 +00002470 name := module.Name()
2471
2472 for _, checker := range checkers {
2473 checker(t, name, exported)
2474 }
2475 }
2476
2477 expectedIncludeDirs := func(expectedPaths string) exportedChecker {
2478 return func(t *testing.T, name string, exported FlagExporterInfo) {
2479 t.Helper()
2480 checkPaths(t, fmt.Sprintf("%s: include dirs", name), expectedPaths, exported.IncludeDirs)
2481 }
2482 }
2483
2484 expectedSystemIncludeDirs := func(expectedPaths string) exportedChecker {
2485 return func(t *testing.T, name string, exported FlagExporterInfo) {
2486 t.Helper()
2487 checkPaths(t, fmt.Sprintf("%s: system include dirs", name), expectedPaths, exported.SystemIncludeDirs)
2488 }
2489 }
2490
2491 expectedGeneratedHeaders := func(expectedPaths string) exportedChecker {
2492 return func(t *testing.T, name string, exported FlagExporterInfo) {
2493 t.Helper()
2494 checkPaths(t, fmt.Sprintf("%s: generated headers", name), expectedPaths, exported.GeneratedHeaders)
2495 }
2496 }
2497
2498 expectedOrderOnlyDeps := func(expectedPaths string) exportedChecker {
2499 return func(t *testing.T, name string, exported FlagExporterInfo) {
2500 t.Helper()
2501 checkPaths(t, fmt.Sprintf("%s: order only deps", name), expectedPaths, exported.Deps)
2502 }
2503 }
2504
2505 genRuleModules := `
2506 genrule {
2507 name: "genrule_foo",
2508 cmd: "generate-foo",
2509 out: [
2510 "generated_headers/foo/generated_header.h",
2511 ],
2512 export_include_dirs: [
2513 "generated_headers",
2514 ],
2515 }
2516
2517 genrule {
2518 name: "genrule_bar",
2519 cmd: "generate-bar",
2520 out: [
2521 "generated_headers/bar/generated_header.h",
2522 ],
2523 export_include_dirs: [
2524 "generated_headers",
2525 ],
2526 }
2527 `
2528
2529 t.Run("ensure exported include dirs are not automatically re-exported from shared_libs", func(t *testing.T) {
2530 ctx := testCc(t, genRuleModules+`
2531 cc_library {
2532 name: "libfoo",
2533 srcs: ["foo.c"],
2534 export_include_dirs: ["foo/standard"],
2535 export_system_include_dirs: ["foo/system"],
2536 generated_headers: ["genrule_foo"],
2537 export_generated_headers: ["genrule_foo"],
2538 }
2539
2540 cc_library {
2541 name: "libbar",
2542 srcs: ["bar.c"],
2543 shared_libs: ["libfoo"],
2544 export_include_dirs: ["bar/standard"],
2545 export_system_include_dirs: ["bar/system"],
2546 generated_headers: ["genrule_bar"],
2547 export_generated_headers: ["genrule_bar"],
2548 }
2549 `)
2550 foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Module()
2551 checkIncludeDirs(t, ctx, foo,
2552 expectedIncludeDirs(`
2553 foo/standard
2554 .intermediates/genrule_foo/gen/generated_headers
2555 `),
2556 expectedSystemIncludeDirs(`foo/system`),
2557 expectedGeneratedHeaders(`.intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h`),
2558 expectedOrderOnlyDeps(`.intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h`),
2559 )
2560
2561 bar := ctx.ModuleForTests("libbar", "android_arm64_armv8-a_shared").Module()
2562 checkIncludeDirs(t, ctx, bar,
2563 expectedIncludeDirs(`
2564 bar/standard
2565 .intermediates/genrule_bar/gen/generated_headers
2566 `),
2567 expectedSystemIncludeDirs(`bar/system`),
2568 expectedGeneratedHeaders(`.intermediates/genrule_bar/gen/generated_headers/bar/generated_header.h`),
2569 expectedOrderOnlyDeps(`.intermediates/genrule_bar/gen/generated_headers/bar/generated_header.h`),
2570 )
2571 })
2572
2573 t.Run("ensure exported include dirs are automatically re-exported from whole_static_libs", func(t *testing.T) {
2574 ctx := testCc(t, genRuleModules+`
2575 cc_library {
2576 name: "libfoo",
2577 srcs: ["foo.c"],
2578 export_include_dirs: ["foo/standard"],
2579 export_system_include_dirs: ["foo/system"],
2580 generated_headers: ["genrule_foo"],
2581 export_generated_headers: ["genrule_foo"],
2582 }
2583
2584 cc_library {
2585 name: "libbar",
2586 srcs: ["bar.c"],
2587 whole_static_libs: ["libfoo"],
2588 export_include_dirs: ["bar/standard"],
2589 export_system_include_dirs: ["bar/system"],
2590 generated_headers: ["genrule_bar"],
2591 export_generated_headers: ["genrule_bar"],
2592 }
2593 `)
2594 foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Module()
2595 checkIncludeDirs(t, ctx, foo,
2596 expectedIncludeDirs(`
2597 foo/standard
2598 .intermediates/genrule_foo/gen/generated_headers
2599 `),
2600 expectedSystemIncludeDirs(`foo/system`),
2601 expectedGeneratedHeaders(`.intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h`),
2602 expectedOrderOnlyDeps(`.intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h`),
2603 )
2604
2605 bar := ctx.ModuleForTests("libbar", "android_arm64_armv8-a_shared").Module()
2606 checkIncludeDirs(t, ctx, bar,
2607 expectedIncludeDirs(`
2608 bar/standard
2609 foo/standard
2610 .intermediates/genrule_foo/gen/generated_headers
2611 .intermediates/genrule_bar/gen/generated_headers
2612 `),
2613 expectedSystemIncludeDirs(`
2614 bar/system
2615 foo/system
2616 `),
2617 expectedGeneratedHeaders(`
2618 .intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h
2619 .intermediates/genrule_bar/gen/generated_headers/bar/generated_header.h
2620 `),
2621 expectedOrderOnlyDeps(`
2622 .intermediates/genrule_foo/gen/generated_headers/foo/generated_header.h
2623 .intermediates/genrule_bar/gen/generated_headers/bar/generated_header.h
2624 `),
2625 )
2626 })
2627
Paul Duffin3cb603e2021-02-19 13:57:10 +00002628 t.Run("ensure only aidl headers are exported", func(t *testing.T) {
Vinh Tran367d89d2023-04-28 11:21:25 -04002629 ctx := android.GroupFixturePreparers(
2630 prepareForCcTest,
2631 aidl_library.PrepareForTestWithAidlLibrary,
2632 ).RunTestWithBp(t, `
2633 aidl_library {
2634 name: "libfoo_aidl",
2635 srcs: ["x/y/Bar.aidl"],
2636 strip_import_prefix: "x",
2637 }
Paul Duffin3cb603e2021-02-19 13:57:10 +00002638 cc_library_shared {
2639 name: "libfoo",
2640 srcs: [
2641 "foo.c",
2642 "b.aidl",
2643 "a.proto",
2644 ],
2645 aidl: {
Vinh Tran367d89d2023-04-28 11:21:25 -04002646 libs: ["libfoo_aidl"],
Paul Duffin3cb603e2021-02-19 13:57:10 +00002647 export_aidl_headers: true,
2648 }
2649 }
Vinh Tran367d89d2023-04-28 11:21:25 -04002650 `).TestContext
Paul Duffin3cb603e2021-02-19 13:57:10 +00002651 foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Module()
2652 checkIncludeDirs(t, ctx, foo,
2653 expectedIncludeDirs(`
2654 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl
Vinh Tran09581952023-05-16 16:03:20 -04002655 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library
Paul Duffin3cb603e2021-02-19 13:57:10 +00002656 `),
2657 expectedSystemIncludeDirs(``),
2658 expectedGeneratedHeaders(`
2659 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/b.h
2660 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/Bnb.h
2661 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/Bpb.h
Vinh Tran09581952023-05-16 16:03:20 -04002662 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/Bar.h
2663 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/BnBar.h
2664 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/BpBar.h
Paul Duffin3cb603e2021-02-19 13:57:10 +00002665 `),
2666 expectedOrderOnlyDeps(`
2667 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/b.h
2668 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/Bnb.h
2669 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl/Bpb.h
Vinh Tran09581952023-05-16 16:03:20 -04002670 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/Bar.h
2671 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/BnBar.h
2672 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/aidl_library/y/BpBar.h
Paul Duffin3cb603e2021-02-19 13:57:10 +00002673 `),
2674 )
2675 })
2676
Paul Duffin3cb603e2021-02-19 13:57:10 +00002677 t.Run("ensure only proto headers are exported", func(t *testing.T) {
2678 ctx := testCc(t, genRuleModules+`
2679 cc_library_shared {
2680 name: "libfoo",
2681 srcs: [
2682 "foo.c",
2683 "b.aidl",
2684 "a.proto",
2685 ],
2686 proto: {
2687 export_proto_headers: true,
2688 }
2689 }
2690 `)
2691 foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Module()
2692 checkIncludeDirs(t, ctx, foo,
2693 expectedIncludeDirs(`
2694 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/proto
2695 `),
2696 expectedSystemIncludeDirs(``),
2697 expectedGeneratedHeaders(`
Paul Duffin3cb603e2021-02-19 13:57:10 +00002698 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/proto/a.pb.h
2699 `),
2700 expectedOrderOnlyDeps(`
Paul Duffin3cb603e2021-02-19 13:57:10 +00002701 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/proto/a.pb.h
2702 `),
2703 )
2704 })
2705
Paul Duffin33056e82021-02-19 13:49:08 +00002706 t.Run("ensure only sysprop headers are exported", func(t *testing.T) {
Paul Duffin3cb603e2021-02-19 13:57:10 +00002707 ctx := testCc(t, genRuleModules+`
2708 cc_library_shared {
2709 name: "libfoo",
2710 srcs: [
2711 "foo.c",
Trevor Radcliffe3092a8e2022-08-24 15:25:25 +00002712 "path/to/a.sysprop",
Paul Duffin3cb603e2021-02-19 13:57:10 +00002713 "b.aidl",
2714 "a.proto",
2715 ],
2716 }
2717 `)
2718 foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared").Module()
2719 checkIncludeDirs(t, ctx, foo,
2720 expectedIncludeDirs(`
2721 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/sysprop/include
2722 `),
2723 expectedSystemIncludeDirs(``),
2724 expectedGeneratedHeaders(`
Trevor Radcliffe3092a8e2022-08-24 15:25:25 +00002725 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/sysprop/include/path/to/a.sysprop.h
Paul Duffin3cb603e2021-02-19 13:57:10 +00002726 `),
2727 expectedOrderOnlyDeps(`
Trevor Radcliffe3092a8e2022-08-24 15:25:25 +00002728 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/sysprop/include/path/to/a.sysprop.h
2729 .intermediates/libfoo/android_arm64_armv8-a_shared/gen/sysprop/public/include/path/to/a.sysprop.h
Paul Duffin3cb603e2021-02-19 13:57:10 +00002730 `),
2731 )
2732 })
2733}
Colin Crossae628182021-06-14 16:52:28 -07002734
2735func TestIncludeDirectoryOrdering(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04002736 t.Parallel()
Colin Cross0e097dd2024-10-17 11:41:28 -07002737
2738 expectedPlatformFlags := []string{
2739 "-nostdlibinc",
2740 }
2741
Liz Kammer08572c62021-09-30 10:11:04 -04002742 baseExpectedFlags := []string{
2743 "${config.ArmThumbCflags}",
2744 "${config.ArmCflags}",
2745 "${config.CommonGlobalCflags}",
2746 "${config.DeviceGlobalCflags}",
2747 "${config.ExternalCflags}",
2748 "${config.ArmToolchainCflags}",
2749 "${config.ArmArmv7ANeonCflags}",
2750 "${config.ArmGenericCflags}",
Colin Crossdd81e672024-10-17 14:01:12 -07002751 }
2752
2753 expectedTargetNDKFlags := []string{
Liz Kammer08572c62021-09-30 10:11:04 -04002754 "-target",
Dan Albert6bfb6bb2022-08-17 20:11:57 +00002755 "armv7a-linux-androideabi21",
Liz Kammer08572c62021-09-30 10:11:04 -04002756 }
2757
Colin Crossdd81e672024-10-17 14:01:12 -07002758 expectedTargetPlatformFlags := []string{
2759 "-target",
2760 "armv7a-linux-androideabi10000",
2761 }
2762
Liz Kammer08572c62021-09-30 10:11:04 -04002763 expectedIncludes := []string{
2764 "external/foo/android_arm_export_include_dirs",
2765 "external/foo/lib32_export_include_dirs",
2766 "external/foo/arm_export_include_dirs",
2767 "external/foo/android_export_include_dirs",
2768 "external/foo/linux_export_include_dirs",
2769 "external/foo/export_include_dirs",
2770 "external/foo/android_arm_local_include_dirs",
2771 "external/foo/lib32_local_include_dirs",
2772 "external/foo/arm_local_include_dirs",
2773 "external/foo/android_local_include_dirs",
2774 "external/foo/linux_local_include_dirs",
2775 "external/foo/local_include_dirs",
2776 "external/foo",
2777 "external/foo/libheader1",
2778 "external/foo/libheader2",
2779 "external/foo/libwhole1",
2780 "external/foo/libwhole2",
2781 "external/foo/libstatic1",
2782 "external/foo/libstatic2",
2783 "external/foo/libshared1",
2784 "external/foo/libshared2",
2785 "external/foo/liblinux",
2786 "external/foo/libandroid",
2787 "external/foo/libarm",
2788 "external/foo/lib32",
2789 "external/foo/libandroid_arm",
Colin Crossdd81e672024-10-17 14:01:12 -07002790 }
2791
2792 expectedNDKSTLIncludes := []string{
Ryan Prichard2a69eb62024-07-30 01:58:54 +00002793 "defaults/cc/common/ndk_libc++_shared_include_dirs",
Liz Kammer08572c62021-09-30 10:11:04 -04002794 }
2795
2796 conly := []string{"-fPIC", "${config.CommonGlobalConlyflags}"}
2797 cppOnly := []string{"-fPIC", "${config.CommonGlobalCppflags}", "${config.DeviceGlobalCppflags}", "${config.ArmCppflags}"}
2798
Elliott Hughesed4a27b2022-05-18 13:15:00 -07002799 cflags := []string{"-Werror", "-std=candcpp"}
Elliott Hughesfb294e32023-06-14 10:42:45 -07002800 cstd := []string{"-std=gnu17", "-std=conly"}
Elliott Hughesc79d9e32022-01-13 14:56:02 -08002801 cppstd := []string{"-std=gnu++20", "-std=cpp", "-fno-rtti"}
Liz Kammer08572c62021-09-30 10:11:04 -04002802
Colin Cross0e097dd2024-10-17 11:41:28 -07002803 lastNDKFlags := []string{
2804 "--sysroot",
2805 "out/soong/ndk/sysroot",
Liz Kammer08572c62021-09-30 10:11:04 -04002806 }
2807
Colin Crossdd81e672024-10-17 14:01:12 -07002808 lastPlatformIncludes := []string{
2809 "${config.CommonGlobalIncludes}",
Liz Kammer08572c62021-09-30 10:11:04 -04002810 }
2811
2812 testCases := []struct {
Colin Crossdd81e672024-10-17 14:01:12 -07002813 name string
2814 src string
2815 expectedNDK []string
2816 expectedPlatform []string
Liz Kammer08572c62021-09-30 10:11:04 -04002817 }{
2818 {
Colin Crossdd81e672024-10-17 14:01:12 -07002819 name: "c",
2820 src: "foo.c",
2821 expectedNDK: slices.Concat(
2822 baseExpectedFlags,
2823 expectedTargetNDKFlags,
2824 conly,
2825 expectedIncludes,
2826 expectedNDKSTLIncludes,
2827 cflags,
2828 cstd,
Colin Cross0e097dd2024-10-17 11:41:28 -07002829 lastNDKFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002830 []string{"${config.NoOverrideGlobalCflags}", "${config.NoOverrideExternalGlobalCflags}"},
2831 ),
2832 expectedPlatform: slices.Concat(
Colin Cross0e097dd2024-10-17 11:41:28 -07002833 expectedPlatformFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002834 baseExpectedFlags,
2835 expectedTargetPlatformFlags,
2836 conly,
2837 expectedIncludes,
2838 cflags,
2839 cstd,
2840 lastPlatformIncludes,
2841 []string{"${config.NoOverrideGlobalCflags}", "${config.NoOverrideExternalGlobalCflags}"},
2842 ),
Liz Kammer08572c62021-09-30 10:11:04 -04002843 },
2844 {
Colin Crossdd81e672024-10-17 14:01:12 -07002845 name: "cc",
2846 src: "foo.cc",
2847 expectedNDK: slices.Concat(
2848 baseExpectedFlags,
2849 expectedTargetNDKFlags,
2850 cppOnly,
2851 expectedIncludes,
2852 expectedNDKSTLIncludes,
2853 cflags,
2854 cppstd,
Colin Cross0e097dd2024-10-17 11:41:28 -07002855 lastNDKFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002856 []string{"${config.NoOverrideGlobalCflags}", "${config.NoOverrideExternalGlobalCflags}"},
2857 ),
2858 expectedPlatform: slices.Concat(
Colin Cross0e097dd2024-10-17 11:41:28 -07002859 expectedPlatformFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002860 baseExpectedFlags,
2861 expectedTargetPlatformFlags,
2862 cppOnly,
2863 expectedIncludes,
2864 cflags,
2865 cppstd,
2866 lastPlatformIncludes,
2867 []string{"${config.NoOverrideGlobalCflags}", "${config.NoOverrideExternalGlobalCflags}"},
2868 ),
Liz Kammer08572c62021-09-30 10:11:04 -04002869 },
2870 {
Colin Crossdd81e672024-10-17 14:01:12 -07002871 name: "assemble",
2872 src: "foo.s",
2873 expectedNDK: slices.Concat(
2874 baseExpectedFlags,
2875 expectedTargetNDKFlags,
2876 []string{"${config.CommonGlobalAsflags}"},
2877 expectedIncludes,
2878 expectedNDKSTLIncludes,
Colin Cross0e097dd2024-10-17 11:41:28 -07002879 lastNDKFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002880 ),
2881 expectedPlatform: slices.Concat(
Colin Cross0e097dd2024-10-17 11:41:28 -07002882 expectedPlatformFlags,
Colin Crossdd81e672024-10-17 14:01:12 -07002883 baseExpectedFlags,
2884 expectedTargetPlatformFlags,
2885 []string{"${config.CommonGlobalAsflags}"},
2886 expectedIncludes,
2887 lastPlatformIncludes,
2888 ),
Liz Kammer08572c62021-09-30 10:11:04 -04002889 },
2890 }
2891
2892 for _, tc := range testCases {
2893 t.Run(tc.name, func(t *testing.T) {
2894 bp := fmt.Sprintf(`
Colin Crossae628182021-06-14 16:52:28 -07002895 cc_library {
2896 name: "libfoo",
Liz Kammer08572c62021-09-30 10:11:04 -04002897 srcs: ["%s"],
Liz Kammer9dc65772021-12-16 11:38:50 -05002898 cflags: ["-std=candcpp"],
2899 conlyflags: ["-std=conly"],
2900 cppflags: ["-std=cpp"],
Colin Crossae628182021-06-14 16:52:28 -07002901 local_include_dirs: ["local_include_dirs"],
2902 export_include_dirs: ["export_include_dirs"],
2903 export_system_include_dirs: ["export_system_include_dirs"],
2904 static_libs: ["libstatic1", "libstatic2"],
2905 whole_static_libs: ["libwhole1", "libwhole2"],
2906 shared_libs: ["libshared1", "libshared2"],
2907 header_libs: ["libheader1", "libheader2"],
2908 target: {
2909 android: {
2910 shared_libs: ["libandroid"],
2911 local_include_dirs: ["android_local_include_dirs"],
2912 export_include_dirs: ["android_export_include_dirs"],
2913 },
2914 android_arm: {
2915 shared_libs: ["libandroid_arm"],
2916 local_include_dirs: ["android_arm_local_include_dirs"],
2917 export_include_dirs: ["android_arm_export_include_dirs"],
2918 },
2919 linux: {
2920 shared_libs: ["liblinux"],
2921 local_include_dirs: ["linux_local_include_dirs"],
2922 export_include_dirs: ["linux_export_include_dirs"],
2923 },
2924 },
2925 multilib: {
2926 lib32: {
2927 shared_libs: ["lib32"],
2928 local_include_dirs: ["lib32_local_include_dirs"],
2929 export_include_dirs: ["lib32_export_include_dirs"],
2930 },
2931 },
2932 arch: {
2933 arm: {
2934 shared_libs: ["libarm"],
2935 local_include_dirs: ["arm_local_include_dirs"],
2936 export_include_dirs: ["arm_export_include_dirs"],
2937 },
2938 },
2939 stl: "libc++",
Dan Albert6bfb6bb2022-08-17 20:11:57 +00002940 sdk_version: "minimum",
Colin Crossae628182021-06-14 16:52:28 -07002941 }
2942
2943 cc_library_headers {
2944 name: "libheader1",
2945 export_include_dirs: ["libheader1"],
Dan Albert6bfb6bb2022-08-17 20:11:57 +00002946 sdk_version: "minimum",
Colin Crossae628182021-06-14 16:52:28 -07002947 stl: "none",
2948 }
2949
2950 cc_library_headers {
2951 name: "libheader2",
2952 export_include_dirs: ["libheader2"],
Dan Albert6bfb6bb2022-08-17 20:11:57 +00002953 sdk_version: "minimum",
Colin Crossae628182021-06-14 16:52:28 -07002954 stl: "none",
2955 }
Liz Kammer08572c62021-09-30 10:11:04 -04002956 `, tc.src)
Colin Crossae628182021-06-14 16:52:28 -07002957
Liz Kammer08572c62021-09-30 10:11:04 -04002958 libs := []string{
2959 "libstatic1",
2960 "libstatic2",
2961 "libwhole1",
2962 "libwhole2",
2963 "libshared1",
2964 "libshared2",
2965 "libandroid",
2966 "libandroid_arm",
2967 "liblinux",
2968 "lib32",
2969 "libarm",
2970 }
Colin Crossae628182021-06-14 16:52:28 -07002971
Liz Kammer08572c62021-09-30 10:11:04 -04002972 for _, lib := range libs {
2973 bp += fmt.Sprintf(`
Colin Crossae628182021-06-14 16:52:28 -07002974 cc_library {
2975 name: "%s",
2976 export_include_dirs: ["%s"],
Dan Albert6bfb6bb2022-08-17 20:11:57 +00002977 sdk_version: "minimum",
Colin Crossae628182021-06-14 16:52:28 -07002978 stl: "none",
2979 }
2980 `, lib, lib)
Liz Kammer08572c62021-09-30 10:11:04 -04002981 }
2982
Colin Crossdd81e672024-10-17 14:01:12 -07002983 runTest := func(t *testing.T, variant string, expected []string) {
2984 ctx := android.GroupFixturePreparers(
2985 PrepareForIntegrationTestWithCc,
2986 android.FixtureAddTextFile("external/foo/Android.bp", bp),
2987 ).RunTest(t)
2988 cflags := ctx.ModuleForTests("libfoo", variant).Output("obj/external/foo/foo.o").Args["cFlags"]
Liz Kammer08572c62021-09-30 10:11:04 -04002989
Colin Crossdd81e672024-10-17 14:01:12 -07002990 var includes []string
2991 flags := strings.Split(cflags, " ")
2992 for _, flag := range flags {
2993 if strings.HasPrefix(flag, "-I") {
2994 includes = append(includes, strings.TrimPrefix(flag, "-I"))
2995 } else if flag == "-isystem" {
2996 // skip isystem, include next
2997 } else if len(flag) > 0 {
2998 includes = append(includes, flag)
2999 }
Liz Kammer08572c62021-09-30 10:11:04 -04003000 }
Colin Crossdd81e672024-10-17 14:01:12 -07003001
3002 android.AssertArrayString(t, "includes", expected, includes)
Liz Kammer08572c62021-09-30 10:11:04 -04003003 }
3004
Colin Crossdd81e672024-10-17 14:01:12 -07003005 t.Run("platform", func(t *testing.T) {
3006 runTest(t, "android_arm_armv7-a-neon_static", tc.expectedPlatform)
3007 })
3008 t.Run("ndk", func(t *testing.T) {
3009 runTest(t, "android_arm_armv7-a-neon_sdk_static", tc.expectedNDK)
3010 })
Liz Kammer08572c62021-09-30 10:11:04 -04003011 })
Colin Crossae628182021-06-14 16:52:28 -07003012 }
3013
Colin Crossae628182021-06-14 16:52:28 -07003014}
Alixb5f6d9e2022-04-20 23:00:58 +00003015
zijunzhao933e3802023-01-12 07:26:20 +00003016func TestAddnoOverride64GlobalCflags(t *testing.T) {
3017 t.Parallel()
3018 ctx := testCc(t, `
3019 cc_library_shared {
3020 name: "libclient",
3021 srcs: ["foo.c"],
3022 shared_libs: ["libfoo#1"],
3023 }
3024
3025 cc_library_shared {
3026 name: "libfoo",
3027 srcs: ["foo.c"],
3028 shared_libs: ["libbar"],
3029 export_shared_lib_headers: ["libbar"],
3030 stubs: {
3031 symbol_file: "foo.map.txt",
3032 versions: ["1", "2", "3"],
3033 },
3034 }
3035
3036 cc_library_shared {
3037 name: "libbar",
3038 export_include_dirs: ["include/libbar"],
3039 srcs: ["foo.c"],
3040 }`)
3041
3042 cFlags := ctx.ModuleForTests("libclient", "android_arm64_armv8-a_shared").Rule("cc").Args["cFlags"]
3043
3044 if !strings.Contains(cFlags, "${config.NoOverride64GlobalCflags}") {
3045 t.Errorf("expected %q in cflags, got %q", "${config.NoOverride64GlobalCflags}", cFlags)
3046 }
3047}
3048
Alixb5f6d9e2022-04-20 23:00:58 +00003049func TestCcBuildBrokenClangProperty(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04003050 t.Parallel()
Alixb5f6d9e2022-04-20 23:00:58 +00003051 tests := []struct {
3052 name string
3053 clang bool
3054 BuildBrokenClangProperty bool
3055 err string
3056 }{
3057 {
3058 name: "error when clang is set to false",
3059 clang: false,
3060 err: "is no longer supported",
3061 },
3062 {
3063 name: "error when clang is set to true",
3064 clang: true,
3065 err: "property is deprecated, see Changes.md",
3066 },
3067 {
3068 name: "no error when BuildBrokenClangProperty is explicitly set to true",
3069 clang: true,
3070 BuildBrokenClangProperty: true,
3071 },
3072 }
3073
3074 for _, test := range tests {
3075 t.Run(test.name, func(t *testing.T) {
3076 bp := fmt.Sprintf(`
3077 cc_library {
3078 name: "foo",
3079 clang: %t,
3080 }`, test.clang)
3081
3082 if test.err == "" {
3083 android.GroupFixturePreparers(
3084 prepareForCcTest,
3085 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
3086 if test.BuildBrokenClangProperty {
3087 variables.BuildBrokenClangProperty = test.BuildBrokenClangProperty
3088 }
3089 }),
3090 ).RunTestWithBp(t, bp)
3091 } else {
3092 prepareForCcTest.
3093 ExtendWithErrorHandler(android.FixtureExpectsOneErrorPattern(test.err)).
3094 RunTestWithBp(t, bp)
3095 }
3096 })
3097 }
3098}
Alix Espinoef47e542022-09-14 19:10:51 +00003099
3100func TestCcBuildBrokenClangAsFlags(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04003101 t.Parallel()
Alix Espinoef47e542022-09-14 19:10:51 +00003102 tests := []struct {
3103 name string
3104 clangAsFlags []string
3105 BuildBrokenClangAsFlags bool
3106 err string
3107 }{
3108 {
3109 name: "error when clang_asflags is set",
3110 clangAsFlags: []string{"-a", "-b"},
3111 err: "clang_asflags: property is deprecated",
3112 },
3113 {
3114 name: "no error when BuildBrokenClangAsFlags is explicitly set to true",
3115 clangAsFlags: []string{"-a", "-b"},
3116 BuildBrokenClangAsFlags: true,
3117 },
3118 }
3119
3120 for _, test := range tests {
3121 t.Run(test.name, func(t *testing.T) {
3122 bp := fmt.Sprintf(`
3123 cc_library {
3124 name: "foo",
3125 clang_asflags: %s,
3126 }`, `["`+strings.Join(test.clangAsFlags, `","`)+`"]`)
3127
3128 if test.err == "" {
3129 android.GroupFixturePreparers(
3130 prepareForCcTest,
3131 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
3132 if test.BuildBrokenClangAsFlags {
3133 variables.BuildBrokenClangAsFlags = test.BuildBrokenClangAsFlags
3134 }
3135 }),
3136 ).RunTestWithBp(t, bp)
3137 } else {
3138 prepareForCcTest.
3139 ExtendWithErrorHandler(android.FixtureExpectsOneErrorPattern(test.err)).
3140 RunTestWithBp(t, bp)
3141 }
3142 })
3143 }
3144}
3145
3146func TestCcBuildBrokenClangCFlags(t *testing.T) {
Liz Kammer7c5d1592022-10-31 16:27:38 -04003147 t.Parallel()
Alix Espinoef47e542022-09-14 19:10:51 +00003148 tests := []struct {
3149 name string
3150 clangCFlags []string
3151 BuildBrokenClangCFlags bool
3152 err string
3153 }{
3154 {
3155 name: "error when clang_cflags is set",
3156 clangCFlags: []string{"-a", "-b"},
3157 err: "clang_cflags: property is deprecated",
3158 },
3159 {
3160 name: "no error when BuildBrokenClangCFlags is explicitly set to true",
3161 clangCFlags: []string{"-a", "-b"},
3162 BuildBrokenClangCFlags: true,
3163 },
3164 }
3165
3166 for _, test := range tests {
3167 t.Run(test.name, func(t *testing.T) {
3168 bp := fmt.Sprintf(`
3169 cc_library {
3170 name: "foo",
3171 clang_cflags: %s,
3172 }`, `["`+strings.Join(test.clangCFlags, `","`)+`"]`)
3173
3174 if test.err == "" {
3175 android.GroupFixturePreparers(
3176 prepareForCcTest,
3177 android.FixtureModifyProductVariables(func(variables android.FixtureProductVariables) {
3178 if test.BuildBrokenClangCFlags {
3179 variables.BuildBrokenClangCFlags = test.BuildBrokenClangCFlags
3180 }
3181 }),
3182 ).RunTestWithBp(t, bp)
3183 } else {
3184 prepareForCcTest.
3185 ExtendWithErrorHandler(android.FixtureExpectsOneErrorPattern(test.err)).
3186 RunTestWithBp(t, bp)
3187 }
3188 })
3189 }
3190}
Wei Li5f5d2712023-12-11 15:40:29 -08003191
3192func TestStrippedAllOutputFile(t *testing.T) {
3193 t.Parallel()
3194 bp := `
3195 cc_library {
3196 name: "test_lib",
3197 srcs: ["test_lib.cpp"],
3198 dist: {
3199 targets: [ "dist_target" ],
3200 tag: "stripped_all",
3201 }
3202 }
3203 `
3204 config := TestConfig(t.TempDir(), android.Android, nil, bp, nil)
3205 ctx := testCcWithConfig(t, config)
mrziwangabdb2932024-06-18 12:43:41 -07003206 testingModule := ctx.ModuleForTests("test_lib", "android_arm_armv7-a-neon_shared")
Yu Liu51c22312024-08-20 23:56:15 +00003207 outputFile := testingModule.OutputFiles(ctx, t, "stripped_all")
Wei Li5f5d2712023-12-11 15:40:29 -08003208 if !strings.HasSuffix(outputFile.Strings()[0], "/stripped_all/test_lib.so") {
3209 t.Errorf("Unexpected output file: %s", outputFile.Strings()[0])
3210 return
3211 }
3212}
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +09003213
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09003214func TestImageVariants(t *testing.T) {
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +09003215 t.Parallel()
3216
3217 bp := `
3218 cc_binary {
3219 name: "binfoo",
3220 srcs: ["binfoo.cc"],
3221 vendor_available: true,
3222 product_available: true,
3223 shared_libs: ["libbar"]
3224 }
3225 cc_library {
3226 name: "libbar",
3227 srcs: ["libbar.cc"],
3228 vendor_available: true,
3229 product_available: true,
3230 }
3231 `
3232
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09003233 ctx := prepareForCcTest.RunTestWithBp(t, bp)
Kiyoung Kimb5fdb2e2024-01-03 14:24:34 +09003234
3235 hasDep := func(m android.Module, wantDep android.Module) bool {
3236 t.Helper()
3237 var found bool
3238 ctx.VisitDirectDeps(m, func(dep blueprint.Module) {
3239 if dep == wantDep {
3240 found = true
3241 }
3242 })
3243 return found
3244 }
3245
3246 testDepWithVariant := func(imageVariant string) {
3247 imageVariantStr := ""
3248 if imageVariant != "core" {
3249 imageVariantStr = "_" + imageVariant
3250 }
3251 binFooModule := ctx.ModuleForTests("binfoo", "android"+imageVariantStr+"_arm64_armv8-a").Module()
3252 libBarModule := ctx.ModuleForTests("libbar", "android"+imageVariantStr+"_arm64_armv8-a_shared").Module()
3253 android.AssertBoolEquals(t, "binfoo should have dependency on libbar with image variant "+imageVariant, true, hasDep(binFooModule, libBarModule))
3254 }
3255
3256 testDepWithVariant("core")
3257 testDepWithVariant("vendor")
3258 testDepWithVariant("product")
3259}
Yi-Yo Chiang88960aa2024-01-19 15:02:29 +08003260
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09003261func TestVendorSdkVersion(t *testing.T) {
Yi-Yo Chiang88960aa2024-01-19 15:02:29 +08003262 t.Parallel()
3263
3264 bp := `
3265 cc_library {
3266 name: "libfoo",
3267 srcs: ["libfoo.cc"],
3268 vendor_available: true,
3269 }
3270
3271 cc_library {
3272 name: "libbar",
3273 srcs: ["libbar.cc"],
3274 vendor_available: true,
3275 min_sdk_version: "29",
3276 }
3277 `
3278
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09003279 ctx := prepareForCcTest.RunTestWithBp(t, bp)
Yi-Yo Chiang88960aa2024-01-19 15:02:29 +08003280 testSdkVersionFlag := func(module, version string) {
3281 flags := ctx.ModuleForTests(module, "android_vendor_arm64_armv8-a_static").Rule("cc").Args["cFlags"]
3282 android.AssertStringDoesContain(t, "min sdk version", flags, "-target aarch64-linux-android"+version)
3283 }
3284
3285 testSdkVersionFlag("libfoo", "10000")
3286 testSdkVersionFlag("libbar", "29")
3287
3288 ctx = android.GroupFixturePreparers(
Kiyoung Kim0d1c1e62024-03-26 16:33:58 +09003289 prepareForCcTest,
Colin Crossa66b4632024-08-08 15:50:47 -07003290 android.PrepareForTestWithBuildFlag("RELEASE_BOARD_API_LEVEL_FROZEN", "true"),
Yi-Yo Chiang88960aa2024-01-19 15:02:29 +08003291 ).RunTestWithBp(t, bp)
3292 testSdkVersionFlag("libfoo", "30")
3293 testSdkVersionFlag("libbar", "29")
3294}
kellyhungd62ea302024-05-19 21:16:07 +08003295
3296func TestClangVerify(t *testing.T) {
3297 t.Parallel()
3298
3299 ctx := testCc(t, `
3300 cc_library {
3301 name: "lib_no_clang_verify",
3302 srcs: ["libnocv.cc"],
3303 }
3304
3305 cc_library {
3306 name: "lib_clang_verify",
3307 srcs: ["libcv.cc"],
3308 clang_verify: true,
3309 }
3310 `)
3311
3312 module := ctx.ModuleForTests("lib_no_clang_verify", "android_arm64_armv8-a_shared")
3313
3314 cFlags_no_cv := module.Rule("cc").Args["cFlags"]
3315 if strings.Contains(cFlags_no_cv, "-Xclang") || strings.Contains(cFlags_no_cv, "-verify") {
3316 t.Errorf("expected %q not in cflags, got %q", "-Xclang -verify", cFlags_no_cv)
3317 }
3318
3319 cFlags_cv := ctx.ModuleForTests("lib_clang_verify", "android_arm64_armv8-a_shared").Rule("cc").Args["cFlags"]
3320 if strings.Contains(cFlags_cv, "-Xclang") && strings.Contains(cFlags_cv, "-verify") {
3321 t.Errorf("expected %q in cflags, got %q", "-Xclang -verify", cFlags_cv)
3322 }
3323}
Colin Cross516c5452024-10-28 13:45:21 -07003324
3325func TestCheckConflictingExplicitVersions(t *testing.T) {
3326 PrepareForIntegrationTestWithCc.
3327 ExtendWithErrorHandler(android.FixtureExpectsOneErrorPattern(
3328 `shared_libs: duplicate shared libraries with different explicit versions: "libbar" and "libbar#impl"`,
3329 )).
3330 RunTestWithBp(t, `
3331 cc_library {
3332 name: "libfoo",
3333 shared_libs: ["libbar", "libbar#impl"],
3334 }
3335
3336 cc_library {
3337 name: "libbar",
3338 }
3339 `)
3340}