platform_build_soong/sh/sh_binary_test.go
Lukacs T. Berki 7690c09953 cd to / before running soong_build .
This lets one avoid any decisions as to when to chdir there during its
execution and leads to better sandboxing because the pwd doesn't leak to
init() functions anymore.

Test: Manual.
Change-Id: I1560da8ed3a621249426f9e8908aa890c21e13ba
2021-03-03 09:14:22 +01:00

243 lines
5.9 KiB
Go

package sh
import (
"io/ioutil"
"os"
"path"
"path/filepath"
"reflect"
"testing"
"android/soong/android"
"android/soong/cc"
)
var buildDir string
func setUp() {
var err error
buildDir, err = ioutil.TempDir("", "soong_sh_test")
if err != nil {
panic(err)
}
}
func tearDown() {
os.RemoveAll(buildDir)
}
func TestMain(m *testing.M) {
run := func() int {
setUp()
defer tearDown()
return m.Run()
}
os.Exit(run())
}
func testShBinary(t *testing.T, bp string) (*android.TestContext, android.Config) {
fs := map[string][]byte{
"test.sh": nil,
"testdata/data1": nil,
"testdata/sub/data2": nil,
}
config := android.TestArchConfig(buildDir, nil, bp, fs)
ctx := android.NewTestArchContext(config)
ctx.RegisterModuleType("sh_test", ShTestFactory)
ctx.RegisterModuleType("sh_test_host", ShTestHostFactory)
cc.RegisterRequiredBuildComponentsForTest(ctx)
ctx.Register()
_, errs := ctx.ParseFileList(".", []string{"Android.bp"})
android.FailIfErrored(t, errs)
_, errs = ctx.PrepareBuildActions(config)
android.FailIfErrored(t, errs)
return ctx, config
}
func TestShTestSubDir(t *testing.T) {
ctx, _ := testShBinary(t, `
sh_test {
name: "foo",
src: "test.sh",
sub_dir: "foo_test"
}
`)
mod := ctx.ModuleForTests("foo", "android_arm64_armv8-a").Module().(*ShTest)
entries := android.AndroidMkEntriesForTest(t, ctx, mod)[0]
expectedPath := path.Join(buildDir,
"../target/product/test_device/data/nativetest64/foo_test")
actualPath := entries.EntryMap["LOCAL_MODULE_PATH"][0]
if expectedPath != actualPath {
t.Errorf("Unexpected LOCAL_MODULE_PATH expected: %q, actual: %q", expectedPath, actualPath)
}
}
func TestShTest(t *testing.T) {
ctx, _ := testShBinary(t, `
sh_test {
name: "foo",
src: "test.sh",
filename: "test.sh",
data: [
"testdata/data1",
"testdata/sub/data2",
],
}
`)
mod := ctx.ModuleForTests("foo", "android_arm64_armv8-a").Module().(*ShTest)
entries := android.AndroidMkEntriesForTest(t, ctx, mod)[0]
expectedPath := path.Join(buildDir,
"../target/product/test_device/data/nativetest64/foo")
actualPath := entries.EntryMap["LOCAL_MODULE_PATH"][0]
if expectedPath != actualPath {
t.Errorf("Unexpected LOCAL_MODULE_PATH expected: %q, actual: %q", expectedPath, actualPath)
}
expectedData := []string{":testdata/data1", ":testdata/sub/data2"}
actualData := entries.EntryMap["LOCAL_TEST_DATA"]
if !reflect.DeepEqual(expectedData, actualData) {
t.Errorf("Unexpected test data expected: %q, actual: %q", expectedData, actualData)
}
}
func TestShTest_dataModules(t *testing.T) {
ctx, _ := testShBinary(t, `
sh_test {
name: "foo",
src: "test.sh",
host_supported: true,
data_bins: ["bar"],
data_libs: ["libbar"],
}
cc_binary {
name: "bar",
host_supported: true,
shared_libs: ["libbar"],
no_libcrt: true,
nocrt: true,
system_shared_libs: [],
stl: "none",
}
cc_library {
name: "libbar",
host_supported: true,
no_libcrt: true,
nocrt: true,
system_shared_libs: [],
stl: "none",
}
`)
buildOS := android.BuildOs.String()
arches := []string{"android_arm64_armv8-a", buildOS + "_x86_64"}
for _, arch := range arches {
variant := ctx.ModuleForTests("foo", arch)
libExt := ".so"
if arch == "darwin_x86_64" {
libExt = ".dylib"
}
relocated := variant.Output("relocated/lib64/libbar" + libExt)
expectedInput := filepath.Join(buildDir, ".intermediates/libbar/"+arch+"_shared/libbar"+libExt)
if relocated.Input.String() != expectedInput {
t.Errorf("Unexpected relocation input, expected: %q, actual: %q",
expectedInput, relocated.Input.String())
}
mod := variant.Module().(*ShTest)
entries := android.AndroidMkEntriesForTest(t, ctx, mod)[0]
expectedData := []string{
filepath.Join(buildDir, ".intermediates/bar", arch, ":bar"),
filepath.Join(buildDir, ".intermediates/foo", arch, "relocated/:lib64/libbar"+libExt),
}
actualData := entries.EntryMap["LOCAL_TEST_DATA"]
if !reflect.DeepEqual(expectedData, actualData) {
t.Errorf("Unexpected test data, expected: %q, actual: %q", expectedData, actualData)
}
}
}
func TestShTestHost(t *testing.T) {
ctx, _ := testShBinary(t, `
sh_test_host {
name: "foo",
src: "test.sh",
filename: "test.sh",
data: [
"testdata/data1",
"testdata/sub/data2",
],
}
`)
buildOS := android.BuildOs.String()
mod := ctx.ModuleForTests("foo", buildOS+"_x86_64").Module().(*ShTest)
if !mod.Host() {
t.Errorf("host bit is not set for a sh_test_host module.")
}
}
func TestShTestHost_dataDeviceModules(t *testing.T) {
ctx, _ := testShBinary(t, `
sh_test_host {
name: "foo",
src: "test.sh",
data_device_bins: ["bar"],
data_device_libs: ["libbar"],
}
cc_binary {
name: "bar",
shared_libs: ["libbar"],
no_libcrt: true,
nocrt: true,
system_shared_libs: [],
stl: "none",
}
cc_library {
name: "libbar",
no_libcrt: true,
nocrt: true,
system_shared_libs: [],
stl: "none",
}
`)
buildOS := android.BuildOs.String()
variant := ctx.ModuleForTests("foo", buildOS+"_x86_64")
relocated := variant.Output("relocated/lib64/libbar.so")
expectedInput := filepath.Join(buildDir, ".intermediates/libbar/android_arm64_armv8-a_shared/libbar.so")
if relocated.Input.String() != expectedInput {
t.Errorf("Unexpected relocation input, expected: %q, actual: %q",
expectedInput, relocated.Input.String())
}
mod := variant.Module().(*ShTest)
entries := android.AndroidMkEntriesForTest(t, ctx, mod)[0]
expectedData := []string{
filepath.Join(buildDir, ".intermediates/bar/android_arm64_armv8-a/:bar"),
// libbar has been relocated, and so has a variant that matches the host arch.
filepath.Join(buildDir, ".intermediates/foo/"+buildOS+"_x86_64/relocated/:lib64/libbar.so"),
}
actualData := entries.EntryMap["LOCAL_TEST_DATA"]
if !reflect.DeepEqual(expectedData, actualData) {
t.Errorf("Unexpected test data, expected: %q, actual: %q", expectedData, actualData)
}
}