1*333d2b36SAndroid Build Coastguard Worker// Copyright 2019 The Android Open Source Project 2*333d2b36SAndroid Build Coastguard Worker// 3*333d2b36SAndroid Build Coastguard Worker// Licensed under the Apache License, Version 2.0 (the "License"); 4*333d2b36SAndroid Build Coastguard Worker// you may not use this file except in compliance with the License. 5*333d2b36SAndroid Build Coastguard Worker// You may obtain a copy of the License at 6*333d2b36SAndroid Build Coastguard Worker// 7*333d2b36SAndroid Build Coastguard Worker// http://www.apache.org/licenses/LICENSE-2.0 8*333d2b36SAndroid Build Coastguard Worker// 9*333d2b36SAndroid Build Coastguard Worker// Unless required by applicable law or agreed to in writing, software 10*333d2b36SAndroid Build Coastguard Worker// distributed under the License is distributed on an "AS IS" BASIS, 11*333d2b36SAndroid Build Coastguard Worker// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12*333d2b36SAndroid Build Coastguard Worker// See the License for the specific language governing permissions and 13*333d2b36SAndroid Build Coastguard Worker// limitations under the License. 14*333d2b36SAndroid Build Coastguard Worker 15*333d2b36SAndroid Build Coastguard Workerpackage rust 16*333d2b36SAndroid Build Coastguard Worker 17*333d2b36SAndroid Build Coastguard Workerimport ( 18*333d2b36SAndroid Build Coastguard Worker "strings" 19*333d2b36SAndroid Build Coastguard Worker "testing" 20*333d2b36SAndroid Build Coastguard Worker 21*333d2b36SAndroid Build Coastguard Worker "android/soong/android" 22*333d2b36SAndroid Build Coastguard Worker) 23*333d2b36SAndroid Build Coastguard Worker 24*333d2b36SAndroid Build Coastguard Worker// Test that variants are being generated correctly, and that crate-types are correct. 25*333d2b36SAndroid Build Coastguard Workerfunc TestLibraryVariants(t *testing.T) { 26*333d2b36SAndroid Build Coastguard Worker 27*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 28*333d2b36SAndroid Build Coastguard Worker rust_library_host { 29*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 30*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 31*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 32*333d2b36SAndroid Build Coastguard Worker } 33*333d2b36SAndroid Build Coastguard Worker rust_ffi_host { 34*333d2b36SAndroid Build Coastguard Worker name: "libfoo.ffi", 35*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 36*333d2b36SAndroid Build Coastguard Worker crate_name: "foo" 37*333d2b36SAndroid Build Coastguard Worker } 38*333d2b36SAndroid Build Coastguard Worker rust_ffi_host_static { 39*333d2b36SAndroid Build Coastguard Worker name: "libfoo.ffi_static", 40*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 41*333d2b36SAndroid Build Coastguard Worker crate_name: "foo" 42*333d2b36SAndroid Build Coastguard Worker }`) 43*333d2b36SAndroid Build Coastguard Worker 44*333d2b36SAndroid Build Coastguard Worker // Test all variants are being built. 45*333d2b36SAndroid Build Coastguard Worker libfooRlib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_rlib_rlib-std").Rule("rustc") 46*333d2b36SAndroid Build Coastguard Worker libfooDylib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_dylib").Rule("rustc") 47*333d2b36SAndroid Build Coastguard Worker libfooFFIRlib := ctx.ModuleForTests("libfoo.ffi", "linux_glibc_x86_64_rlib_rlib-std").Rule("rustc") 48*333d2b36SAndroid Build Coastguard Worker libfooShared := ctx.ModuleForTests("libfoo.ffi", "linux_glibc_x86_64_shared").Rule("rustc") 49*333d2b36SAndroid Build Coastguard Worker 50*333d2b36SAndroid Build Coastguard Worker rlibCrateType := "rlib" 51*333d2b36SAndroid Build Coastguard Worker dylibCrateType := "dylib" 52*333d2b36SAndroid Build Coastguard Worker sharedCrateType := "cdylib" 53*333d2b36SAndroid Build Coastguard Worker 54*333d2b36SAndroid Build Coastguard Worker // Test crate type for rlib is correct. 55*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooRlib.Args["rustcFlags"], "crate-type="+rlibCrateType) { 56*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing crate-type for static variant, expecting %#v, rustcFlags: %#v", rlibCrateType, libfooRlib.Args["rustcFlags"]) 57*333d2b36SAndroid Build Coastguard Worker } 58*333d2b36SAndroid Build Coastguard Worker 59*333d2b36SAndroid Build Coastguard Worker // Test crate type for dylib is correct. 60*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooDylib.Args["rustcFlags"], "crate-type="+dylibCrateType) { 61*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing crate-type for static variant, expecting %#v, rustcFlags: %#v", dylibCrateType, libfooDylib.Args["rustcFlags"]) 62*333d2b36SAndroid Build Coastguard Worker } 63*333d2b36SAndroid Build Coastguard Worker 64*333d2b36SAndroid Build Coastguard Worker // Test crate type for FFI rlibs is correct 65*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooFFIRlib.Args["rustcFlags"], "crate-type="+rlibCrateType) { 66*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing crate-type for static variant, expecting %#v, rustcFlags: %#v", rlibCrateType, libfooFFIRlib.Args["rustcFlags"]) 67*333d2b36SAndroid Build Coastguard Worker } 68*333d2b36SAndroid Build Coastguard Worker 69*333d2b36SAndroid Build Coastguard Worker // Test crate type for C shared libraries is correct. 70*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooShared.Args["rustcFlags"], "crate-type="+sharedCrateType) { 71*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing crate-type for shared variant, expecting %#v, got rustcFlags: %#v", sharedCrateType, libfooShared.Args["rustcFlags"]) 72*333d2b36SAndroid Build Coastguard Worker } 73*333d2b36SAndroid Build Coastguard Worker 74*333d2b36SAndroid Build Coastguard Worker} 75*333d2b36SAndroid Build Coastguard Worker 76*333d2b36SAndroid Build Coastguard Worker// Test that dylibs are not statically linking the standard library. 77*333d2b36SAndroid Build Coastguard Workerfunc TestDylibPreferDynamic(t *testing.T) { 78*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 79*333d2b36SAndroid Build Coastguard Worker rust_library_host_dylib { 80*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 81*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 82*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 83*333d2b36SAndroid Build Coastguard Worker }`) 84*333d2b36SAndroid Build Coastguard Worker 85*333d2b36SAndroid Build Coastguard Worker libfooDylib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_dylib").Rule("rustc") 86*333d2b36SAndroid Build Coastguard Worker 87*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooDylib.Args["rustcFlags"], "prefer-dynamic") { 88*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing prefer-dynamic flag for libfoo dylib, rustcFlags: %#v", libfooDylib.Args["rustcFlags"]) 89*333d2b36SAndroid Build Coastguard Worker } 90*333d2b36SAndroid Build Coastguard Worker} 91*333d2b36SAndroid Build Coastguard Worker 92*333d2b36SAndroid Build Coastguard Worker// Check that we are passing the android_dylib config flag 93*333d2b36SAndroid Build Coastguard Workerfunc TestAndroidDylib(t *testing.T) { 94*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 95*333d2b36SAndroid Build Coastguard Worker rust_library_host_dylib { 96*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 97*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 98*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 99*333d2b36SAndroid Build Coastguard Worker }`) 100*333d2b36SAndroid Build Coastguard Worker 101*333d2b36SAndroid Build Coastguard Worker libfooDylib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_dylib").Rule("rustc") 102*333d2b36SAndroid Build Coastguard Worker 103*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooDylib.Args["rustcFlags"], "--cfg 'android_dylib'") { 104*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing android_dylib cfg flag for libfoo dylib, rustcFlags: %#v", libfooDylib.Args["rustcFlags"]) 105*333d2b36SAndroid Build Coastguard Worker } 106*333d2b36SAndroid Build Coastguard Worker} 107*333d2b36SAndroid Build Coastguard Worker 108*333d2b36SAndroid Build Coastguard Workerfunc TestValidateLibraryStem(t *testing.T) { 109*333d2b36SAndroid Build Coastguard Worker testRustError(t, "crate_name must be defined.", ` 110*333d2b36SAndroid Build Coastguard Worker rust_library_host { 111*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 112*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 113*333d2b36SAndroid Build Coastguard Worker }`) 114*333d2b36SAndroid Build Coastguard Worker 115*333d2b36SAndroid Build Coastguard Worker testRustError(t, "library crate_names must be alphanumeric with underscores allowed", ` 116*333d2b36SAndroid Build Coastguard Worker rust_library_host { 117*333d2b36SAndroid Build Coastguard Worker name: "libfoo-bar", 118*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 119*333d2b36SAndroid Build Coastguard Worker crate_name: "foo-bar" 120*333d2b36SAndroid Build Coastguard Worker }`) 121*333d2b36SAndroid Build Coastguard Worker 122*333d2b36SAndroid Build Coastguard Worker testRustError(t, "Invalid name or stem property; library filenames must start with lib<crate_name>", ` 123*333d2b36SAndroid Build Coastguard Worker rust_library_host { 124*333d2b36SAndroid Build Coastguard Worker name: "foobar", 125*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 126*333d2b36SAndroid Build Coastguard Worker crate_name: "foo_bar" 127*333d2b36SAndroid Build Coastguard Worker }`) 128*333d2b36SAndroid Build Coastguard Worker testRustError(t, "Invalid name or stem property; library filenames must start with lib<crate_name>", ` 129*333d2b36SAndroid Build Coastguard Worker rust_library_host { 130*333d2b36SAndroid Build Coastguard Worker name: "foobar", 131*333d2b36SAndroid Build Coastguard Worker stem: "libfoo", 132*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 133*333d2b36SAndroid Build Coastguard Worker crate_name: "foo_bar" 134*333d2b36SAndroid Build Coastguard Worker }`) 135*333d2b36SAndroid Build Coastguard Worker testRustError(t, "Invalid name or stem property; library filenames must start with lib<crate_name>", ` 136*333d2b36SAndroid Build Coastguard Worker rust_library_host { 137*333d2b36SAndroid Build Coastguard Worker name: "foobar", 138*333d2b36SAndroid Build Coastguard Worker stem: "foo_bar", 139*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 140*333d2b36SAndroid Build Coastguard Worker crate_name: "foo_bar" 141*333d2b36SAndroid Build Coastguard Worker }`) 142*333d2b36SAndroid Build Coastguard Worker 143*333d2b36SAndroid Build Coastguard Worker} 144*333d2b36SAndroid Build Coastguard Worker 145*333d2b36SAndroid Build Coastguard Workerfunc TestSharedLibrary(t *testing.T) { 146*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 147*333d2b36SAndroid Build Coastguard Worker rust_ffi_shared { 148*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 149*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 150*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 151*333d2b36SAndroid Build Coastguard Worker }`) 152*333d2b36SAndroid Build Coastguard Worker 153*333d2b36SAndroid Build Coastguard Worker libfoo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_shared") 154*333d2b36SAndroid Build Coastguard Worker 155*333d2b36SAndroid Build Coastguard Worker libfooOutput := libfoo.Rule("rustc") 156*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(libfooOutput.Args["linkFlags"], "-Wl,-soname=libfoo.so") { 157*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing expected -Wl,-soname linker flag for libfoo shared lib, linkFlags: %#v", 158*333d2b36SAndroid Build Coastguard Worker libfooOutput.Args["linkFlags"]) 159*333d2b36SAndroid Build Coastguard Worker } 160*333d2b36SAndroid Build Coastguard Worker 161*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libfoo.Module().(*Module).Properties.AndroidMkDylibs) { 162*333d2b36SAndroid Build Coastguard Worker t.Errorf("Non-static libstd dylib expected to be a dependency of Rust shared libraries. Dylib deps are: %#v", 163*333d2b36SAndroid Build Coastguard Worker libfoo.Module().(*Module).Properties.AndroidMkDylibs) 164*333d2b36SAndroid Build Coastguard Worker } 165*333d2b36SAndroid Build Coastguard Worker} 166*333d2b36SAndroid Build Coastguard Worker 167*333d2b36SAndroid Build Coastguard Workerfunc TestSharedLibraryToc(t *testing.T) { 168*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 169*333d2b36SAndroid Build Coastguard Worker rust_ffi_shared { 170*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 171*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 172*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 173*333d2b36SAndroid Build Coastguard Worker } 174*333d2b36SAndroid Build Coastguard Worker cc_binary { 175*333d2b36SAndroid Build Coastguard Worker name: "fizzbuzz", 176*333d2b36SAndroid Build Coastguard Worker shared_libs: ["libfoo"], 177*333d2b36SAndroid Build Coastguard Worker }`) 178*333d2b36SAndroid Build Coastguard Worker 179*333d2b36SAndroid Build Coastguard Worker fizzbuzz := ctx.ModuleForTests("fizzbuzz", "android_arm64_armv8-a").Rule("ld") 180*333d2b36SAndroid Build Coastguard Worker 181*333d2b36SAndroid Build Coastguard Worker if !android.SuffixInList(fizzbuzz.Implicits.Strings(), "libfoo.so.toc") { 182*333d2b36SAndroid Build Coastguard Worker t.Errorf("missing expected libfoo.so.toc implicit dependency, instead found: %#v", 183*333d2b36SAndroid Build Coastguard Worker fizzbuzz.Implicits.Strings()) 184*333d2b36SAndroid Build Coastguard Worker } 185*333d2b36SAndroid Build Coastguard Worker} 186*333d2b36SAndroid Build Coastguard Worker 187*333d2b36SAndroid Build Coastguard Workerfunc TestStaticLibraryLinkage(t *testing.T) { 188*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 189*333d2b36SAndroid Build Coastguard Worker rust_ffi_static { 190*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 191*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 192*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 193*333d2b36SAndroid Build Coastguard Worker }`) 194*333d2b36SAndroid Build Coastguard Worker 195*333d2b36SAndroid Build Coastguard Worker libfoo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_rlib_rlib-std") 196*333d2b36SAndroid Build Coastguard Worker 197*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libfoo.Module().(*Module).Properties.AndroidMkRlibs) { 198*333d2b36SAndroid Build Coastguard Worker t.Errorf("Static libstd rlib expected to be a dependency of Rust rlib libraries. Rlib deps are: %#v", 199*333d2b36SAndroid Build Coastguard Worker libfoo.Module().(*Module).Properties.AndroidMkDylibs) 200*333d2b36SAndroid Build Coastguard Worker } 201*333d2b36SAndroid Build Coastguard Worker} 202*333d2b36SAndroid Build Coastguard Worker 203*333d2b36SAndroid Build Coastguard Workerfunc TestNativeDependencyOfRlib(t *testing.T) { 204*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 205*333d2b36SAndroid Build Coastguard Worker rust_ffi_rlib { 206*333d2b36SAndroid Build Coastguard Worker name: "libffi_rlib", 207*333d2b36SAndroid Build Coastguard Worker crate_name: "ffi_rlib", 208*333d2b36SAndroid Build Coastguard Worker rlibs: ["librust_rlib"], 209*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 210*333d2b36SAndroid Build Coastguard Worker } 211*333d2b36SAndroid Build Coastguard Worker rust_library_rlib { 212*333d2b36SAndroid Build Coastguard Worker name: "librust_rlib", 213*333d2b36SAndroid Build Coastguard Worker crate_name: "rust_rlib", 214*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 215*333d2b36SAndroid Build Coastguard Worker shared_libs: ["libshared_cc_dep"], 216*333d2b36SAndroid Build Coastguard Worker static_libs: ["libstatic_cc_dep"], 217*333d2b36SAndroid Build Coastguard Worker } 218*333d2b36SAndroid Build Coastguard Worker cc_library_shared { 219*333d2b36SAndroid Build Coastguard Worker name: "libshared_cc_dep", 220*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.cpp"], 221*333d2b36SAndroid Build Coastguard Worker } 222*333d2b36SAndroid Build Coastguard Worker cc_library_static { 223*333d2b36SAndroid Build Coastguard Worker name: "libstatic_cc_dep", 224*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.cpp"], 225*333d2b36SAndroid Build Coastguard Worker } 226*333d2b36SAndroid Build Coastguard Worker `) 227*333d2b36SAndroid Build Coastguard Worker 228*333d2b36SAndroid Build Coastguard Worker rustRlibRlibStd := ctx.ModuleForTests("librust_rlib", "android_arm64_armv8-a_rlib_rlib-std") 229*333d2b36SAndroid Build Coastguard Worker rustRlibDylibStd := ctx.ModuleForTests("librust_rlib", "android_arm64_armv8-a_rlib_dylib-std") 230*333d2b36SAndroid Build Coastguard Worker ffiRlib := ctx.ModuleForTests("libffi_rlib", "android_arm64_armv8-a_rlib_rlib-std") 231*333d2b36SAndroid Build Coastguard Worker 232*333d2b36SAndroid Build Coastguard Worker modules := []android.TestingModule{ 233*333d2b36SAndroid Build Coastguard Worker rustRlibRlibStd, 234*333d2b36SAndroid Build Coastguard Worker rustRlibDylibStd, 235*333d2b36SAndroid Build Coastguard Worker ffiRlib, 236*333d2b36SAndroid Build Coastguard Worker } 237*333d2b36SAndroid Build Coastguard Worker 238*333d2b36SAndroid Build Coastguard Worker // librust_rlib specifies -L flag to cc deps output directory on rustc command 239*333d2b36SAndroid Build Coastguard Worker // and re-export the cc deps to rdep libffi_static 240*333d2b36SAndroid Build Coastguard Worker // When building rlib crate, rustc doesn't link the native libraries 241*333d2b36SAndroid Build Coastguard Worker // The build system assumes the cc deps will be at the final linkage (either a shared library or binary) 242*333d2b36SAndroid Build Coastguard Worker // Hence, these flags are no-op 243*333d2b36SAndroid Build Coastguard Worker // TODO: We could consider removing these flags 244*333d2b36SAndroid Build Coastguard Worker for _, module := range modules { 245*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(module.Rule("rustc").Args["libFlags"], 246*333d2b36SAndroid Build Coastguard Worker "-L out/soong/.intermediates/libshared_cc_dep/android_arm64_armv8-a_shared/") { 247*333d2b36SAndroid Build Coastguard Worker t.Errorf( 248*333d2b36SAndroid Build Coastguard Worker "missing -L flag for libshared_cc_dep of %s, rustcFlags: %#v", 249*333d2b36SAndroid Build Coastguard Worker module.Module().Name(), rustRlibRlibStd.Rule("rustc").Args["libFlags"], 250*333d2b36SAndroid Build Coastguard Worker ) 251*333d2b36SAndroid Build Coastguard Worker } 252*333d2b36SAndroid Build Coastguard Worker if !strings.Contains(module.Rule("rustc").Args["libFlags"], 253*333d2b36SAndroid Build Coastguard Worker "-L out/soong/.intermediates/libstatic_cc_dep/android_arm64_armv8-a_static/") { 254*333d2b36SAndroid Build Coastguard Worker t.Errorf( 255*333d2b36SAndroid Build Coastguard Worker "missing -L flag for libstatic_cc_dep of %s, rustcFlags: %#v", 256*333d2b36SAndroid Build Coastguard Worker module.Module().Name(), rustRlibRlibStd.Rule("rustc").Args["libFlags"], 257*333d2b36SAndroid Build Coastguard Worker ) 258*333d2b36SAndroid Build Coastguard Worker } 259*333d2b36SAndroid Build Coastguard Worker } 260*333d2b36SAndroid Build Coastguard Worker} 261*333d2b36SAndroid Build Coastguard Worker 262*333d2b36SAndroid Build Coastguard Worker// Test that variants pull in the right type of rustlib autodep 263*333d2b36SAndroid Build Coastguard Workerfunc TestAutoDeps(t *testing.T) { 264*333d2b36SAndroid Build Coastguard Worker 265*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 266*333d2b36SAndroid Build Coastguard Worker rust_library_host { 267*333d2b36SAndroid Build Coastguard Worker name: "libbar", 268*333d2b36SAndroid Build Coastguard Worker srcs: ["bar.rs"], 269*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 270*333d2b36SAndroid Build Coastguard Worker } 271*333d2b36SAndroid Build Coastguard Worker rust_library_host_rlib { 272*333d2b36SAndroid Build Coastguard Worker name: "librlib_only", 273*333d2b36SAndroid Build Coastguard Worker srcs: ["bar.rs"], 274*333d2b36SAndroid Build Coastguard Worker crate_name: "rlib_only", 275*333d2b36SAndroid Build Coastguard Worker } 276*333d2b36SAndroid Build Coastguard Worker rust_library_host { 277*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 278*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 279*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 280*333d2b36SAndroid Build Coastguard Worker rustlibs: [ 281*333d2b36SAndroid Build Coastguard Worker "libbar", 282*333d2b36SAndroid Build Coastguard Worker "librlib_only", 283*333d2b36SAndroid Build Coastguard Worker ], 284*333d2b36SAndroid Build Coastguard Worker } 285*333d2b36SAndroid Build Coastguard Worker rust_ffi_host { 286*333d2b36SAndroid Build Coastguard Worker name: "libfoo.ffi", 287*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 288*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 289*333d2b36SAndroid Build Coastguard Worker rustlibs: [ 290*333d2b36SAndroid Build Coastguard Worker "libbar", 291*333d2b36SAndroid Build Coastguard Worker "librlib_only", 292*333d2b36SAndroid Build Coastguard Worker ], 293*333d2b36SAndroid Build Coastguard Worker } 294*333d2b36SAndroid Build Coastguard Worker rust_ffi_host_static { 295*333d2b36SAndroid Build Coastguard Worker name: "libfoo.ffi.static", 296*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 297*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 298*333d2b36SAndroid Build Coastguard Worker rustlibs: [ 299*333d2b36SAndroid Build Coastguard Worker "libbar", 300*333d2b36SAndroid Build Coastguard Worker "librlib_only", 301*333d2b36SAndroid Build Coastguard Worker ], 302*333d2b36SAndroid Build Coastguard Worker }`) 303*333d2b36SAndroid Build Coastguard Worker 304*333d2b36SAndroid Build Coastguard Worker libfooRlib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_rlib_rlib-std") 305*333d2b36SAndroid Build Coastguard Worker libfooDylib := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_dylib") 306*333d2b36SAndroid Build Coastguard Worker libfooFFIRlib := ctx.ModuleForTests("libfoo.ffi", "linux_glibc_x86_64_rlib_rlib-std") 307*333d2b36SAndroid Build Coastguard Worker libfooShared := ctx.ModuleForTests("libfoo.ffi", "linux_glibc_x86_64_shared") 308*333d2b36SAndroid Build Coastguard Worker 309*333d2b36SAndroid Build Coastguard Worker for _, static := range []android.TestingModule{libfooRlib, libfooFFIRlib} { 310*333d2b36SAndroid Build Coastguard Worker if !android.InList("libbar.rlib-std", static.Module().(*Module).Properties.AndroidMkRlibs) { 311*333d2b36SAndroid Build Coastguard Worker t.Errorf("libbar not present as rlib dependency in static lib: %s", static.Module().Name()) 312*333d2b36SAndroid Build Coastguard Worker } 313*333d2b36SAndroid Build Coastguard Worker if android.InList("libbar", static.Module().(*Module).Properties.AndroidMkDylibs) { 314*333d2b36SAndroid Build Coastguard Worker t.Errorf("libbar present as dynamic dependency in static lib: %s", static.Module().Name()) 315*333d2b36SAndroid Build Coastguard Worker } 316*333d2b36SAndroid Build Coastguard Worker } 317*333d2b36SAndroid Build Coastguard Worker 318*333d2b36SAndroid Build Coastguard Worker for _, dyn := range []android.TestingModule{libfooDylib, libfooShared} { 319*333d2b36SAndroid Build Coastguard Worker if !android.InList("libbar", dyn.Module().(*Module).Properties.AndroidMkDylibs) { 320*333d2b36SAndroid Build Coastguard Worker t.Errorf("libbar not present as dynamic dependency in dynamic lib: %s", dyn.Module().Name()) 321*333d2b36SAndroid Build Coastguard Worker } 322*333d2b36SAndroid Build Coastguard Worker if android.InList("libbar", dyn.Module().(*Module).Properties.AndroidMkRlibs) { 323*333d2b36SAndroid Build Coastguard Worker t.Errorf("libbar present as rlib dependency in dynamic lib: %s", dyn.Module().Name()) 324*333d2b36SAndroid Build Coastguard Worker } 325*333d2b36SAndroid Build Coastguard Worker if !android.InList("librlib_only", dyn.Module().(*Module).Properties.AndroidMkRlibs) { 326*333d2b36SAndroid Build Coastguard Worker t.Errorf("librlib_only should be selected by rustlibs as an rlib: %s.", dyn.Module().Name()) 327*333d2b36SAndroid Build Coastguard Worker } 328*333d2b36SAndroid Build Coastguard Worker } 329*333d2b36SAndroid Build Coastguard Worker} 330*333d2b36SAndroid Build Coastguard Worker 331*333d2b36SAndroid Build Coastguard Worker// Test that stripped versions are correctly generated and used. 332*333d2b36SAndroid Build Coastguard Workerfunc TestStrippedLibrary(t *testing.T) { 333*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 334*333d2b36SAndroid Build Coastguard Worker rust_library_dylib { 335*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 336*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 337*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 338*333d2b36SAndroid Build Coastguard Worker } 339*333d2b36SAndroid Build Coastguard Worker rust_library_dylib { 340*333d2b36SAndroid Build Coastguard Worker name: "libbar", 341*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 342*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 343*333d2b36SAndroid Build Coastguard Worker strip: { 344*333d2b36SAndroid Build Coastguard Worker none: true 345*333d2b36SAndroid Build Coastguard Worker } 346*333d2b36SAndroid Build Coastguard Worker } 347*333d2b36SAndroid Build Coastguard Worker `) 348*333d2b36SAndroid Build Coastguard Worker 349*333d2b36SAndroid Build Coastguard Worker foo := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_dylib") 350*333d2b36SAndroid Build Coastguard Worker foo.Output("libfoo.dylib.so") 351*333d2b36SAndroid Build Coastguard Worker foo.Output("unstripped/libfoo.dylib.so") 352*333d2b36SAndroid Build Coastguard Worker // Check that the `cp` rule is using the stripped version as input. 353*333d2b36SAndroid Build Coastguard Worker cp := foo.Rule("android.Cp") 354*333d2b36SAndroid Build Coastguard Worker if strings.HasSuffix(cp.Input.String(), "unstripped/libfoo.dylib.so") { 355*333d2b36SAndroid Build Coastguard Worker t.Errorf("installed library not based on stripped version: %v", cp.Input) 356*333d2b36SAndroid Build Coastguard Worker } 357*333d2b36SAndroid Build Coastguard Worker 358*333d2b36SAndroid Build Coastguard Worker fizzBar := ctx.ModuleForTests("libbar", "android_arm64_armv8-a_dylib").MaybeOutput("unstripped/libbar.dylib.so") 359*333d2b36SAndroid Build Coastguard Worker if fizzBar.Rule != nil { 360*333d2b36SAndroid Build Coastguard Worker t.Errorf("unstripped library exists, so stripped library has incorrectly been generated") 361*333d2b36SAndroid Build Coastguard Worker } 362*333d2b36SAndroid Build Coastguard Worker} 363*333d2b36SAndroid Build Coastguard Worker 364*333d2b36SAndroid Build Coastguard Workerfunc TestLibstdLinkage(t *testing.T) { 365*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 366*333d2b36SAndroid Build Coastguard Worker rust_library { 367*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 368*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 369*333d2b36SAndroid Build Coastguard Worker crate_name: "foo", 370*333d2b36SAndroid Build Coastguard Worker } 371*333d2b36SAndroid Build Coastguard Worker rust_ffi { 372*333d2b36SAndroid Build Coastguard Worker name: "libbar", 373*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 374*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 375*333d2b36SAndroid Build Coastguard Worker rustlibs: ["libfoo"], 376*333d2b36SAndroid Build Coastguard Worker } 377*333d2b36SAndroid Build Coastguard Worker rust_ffi_static { 378*333d2b36SAndroid Build Coastguard Worker name: "libbar_static", 379*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 380*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 381*333d2b36SAndroid Build Coastguard Worker rustlibs: ["libfoo"], 382*333d2b36SAndroid Build Coastguard Worker } 383*333d2b36SAndroid Build Coastguard Worker rust_ffi { 384*333d2b36SAndroid Build Coastguard Worker name: "libbar.prefer_rlib", 385*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 386*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 387*333d2b36SAndroid Build Coastguard Worker rustlibs: ["libfoo"], 388*333d2b36SAndroid Build Coastguard Worker prefer_rlib: true, 389*333d2b36SAndroid Build Coastguard Worker }`) 390*333d2b36SAndroid Build Coastguard Worker 391*333d2b36SAndroid Build Coastguard Worker libfooDylib := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_dylib").Module().(*Module) 392*333d2b36SAndroid Build Coastguard Worker libfooRlibStatic := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_rlib_rlib-std").Module().(*Module) 393*333d2b36SAndroid Build Coastguard Worker libfooRlibDynamic := ctx.ModuleForTests("libfoo", "android_arm64_armv8-a_rlib_dylib-std").Module().(*Module) 394*333d2b36SAndroid Build Coastguard Worker 395*333d2b36SAndroid Build Coastguard Worker libbarShared := ctx.ModuleForTests("libbar", "android_arm64_armv8-a_shared").Module().(*Module) 396*333d2b36SAndroid Build Coastguard Worker libbarFFIRlib := ctx.ModuleForTests("libbar", "android_arm64_armv8-a_rlib_rlib-std").Module().(*Module) 397*333d2b36SAndroid Build Coastguard Worker 398*333d2b36SAndroid Build Coastguard Worker // prefer_rlib works the same for both rust_library and rust_ffi, so a single check is sufficient here. 399*333d2b36SAndroid Build Coastguard Worker libbarRlibStd := ctx.ModuleForTests("libbar.prefer_rlib", "android_arm64_armv8-a_shared").Module().(*Module) 400*333d2b36SAndroid Build Coastguard Worker 401*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libfooRlibStatic.Properties.AndroidMkRlibs) { 402*333d2b36SAndroid Build Coastguard Worker t.Errorf("rlib-std variant for device rust_library_rlib does not link libstd as an rlib") 403*333d2b36SAndroid Build Coastguard Worker } 404*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libfooRlibDynamic.Properties.AndroidMkDylibs) { 405*333d2b36SAndroid Build Coastguard Worker t.Errorf("dylib-std variant for device rust_library_rlib does not link libstd as an dylib") 406*333d2b36SAndroid Build Coastguard Worker } 407*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libfooDylib.Properties.AndroidMkDylibs) { 408*333d2b36SAndroid Build Coastguard Worker t.Errorf("Device rust_library_dylib does not link libstd as an dylib") 409*333d2b36SAndroid Build Coastguard Worker } 410*333d2b36SAndroid Build Coastguard Worker 411*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libbarShared.Properties.AndroidMkDylibs) { 412*333d2b36SAndroid Build Coastguard Worker t.Errorf("Device rust_ffi_shared does not link libstd as an dylib") 413*333d2b36SAndroid Build Coastguard Worker } 414*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libbarFFIRlib.Properties.AndroidMkRlibs) { 415*333d2b36SAndroid Build Coastguard Worker t.Errorf("Device rust_ffi_rlib does not link libstd as an rlib") 416*333d2b36SAndroid Build Coastguard Worker } 417*333d2b36SAndroid Build Coastguard Worker if !android.InList("libfoo.rlib-std", libbarFFIRlib.Properties.AndroidMkRlibs) { 418*333d2b36SAndroid Build Coastguard Worker t.Errorf("Device rust_ffi_rlib does not link dependent rustlib rlib-std variant") 419*333d2b36SAndroid Build Coastguard Worker } 420*333d2b36SAndroid Build Coastguard Worker if !android.InList("libstd", libbarRlibStd.Properties.AndroidMkRlibs) { 421*333d2b36SAndroid Build Coastguard Worker t.Errorf("rust_ffi with prefer_rlib does not link libstd as an rlib") 422*333d2b36SAndroid Build Coastguard Worker } 423*333d2b36SAndroid Build Coastguard Worker 424*333d2b36SAndroid Build Coastguard Worker} 425*333d2b36SAndroid Build Coastguard Worker 426*333d2b36SAndroid Build Coastguard Workerfunc TestRustFFIExportedIncludes(t *testing.T) { 427*333d2b36SAndroid Build Coastguard Worker ctx := testRust(t, ` 428*333d2b36SAndroid Build Coastguard Worker rust_ffi { 429*333d2b36SAndroid Build Coastguard Worker name: "libbar", 430*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.rs"], 431*333d2b36SAndroid Build Coastguard Worker crate_name: "bar", 432*333d2b36SAndroid Build Coastguard Worker export_include_dirs: ["rust_includes"], 433*333d2b36SAndroid Build Coastguard Worker host_supported: true, 434*333d2b36SAndroid Build Coastguard Worker } 435*333d2b36SAndroid Build Coastguard Worker cc_library_static { 436*333d2b36SAndroid Build Coastguard Worker name: "libfoo", 437*333d2b36SAndroid Build Coastguard Worker srcs: ["foo.cpp"], 438*333d2b36SAndroid Build Coastguard Worker shared_libs: ["libbar"], 439*333d2b36SAndroid Build Coastguard Worker host_supported: true, 440*333d2b36SAndroid Build Coastguard Worker }`) 441*333d2b36SAndroid Build Coastguard Worker libfooStatic := ctx.ModuleForTests("libfoo", "linux_glibc_x86_64_static").Rule("cc") 442*333d2b36SAndroid Build Coastguard Worker android.AssertStringDoesContain(t, "cFlags for lib module", libfooStatic.Args["cFlags"], " -Irust_includes ") 443*333d2b36SAndroid Build Coastguard Worker} 444