Split out sdk.go from java.go
Split out SDK handling functions from java.go to sdk.go and tests from java_test.go to sdk.go. Test: sdk_test.go Change-Id: I83ef48cbe5230572c1d4ecc0e89021d2f7c71b76
This commit is contained in:
@@ -249,6 +249,7 @@ bootstrap_go_package {
|
|||||||
"java/java_resources.go",
|
"java/java_resources.go",
|
||||||
"java/prebuilt_apis.go",
|
"java/prebuilt_apis.go",
|
||||||
"java/proto.go",
|
"java/proto.go",
|
||||||
|
"java/sdk.go",
|
||||||
"java/sdk_library.go",
|
"java/sdk_library.go",
|
||||||
"java/support_libraries.go",
|
"java/support_libraries.go",
|
||||||
"java/system_modules.go",
|
"java/system_modules.go",
|
||||||
@@ -258,6 +259,7 @@ bootstrap_go_package {
|
|||||||
"java/dexpreopt_test.go",
|
"java/dexpreopt_test.go",
|
||||||
"java/java_test.go",
|
"java/java_test.go",
|
||||||
"java/jdeps_test.go",
|
"java/jdeps_test.go",
|
||||||
|
"java/sdk_test.go",
|
||||||
],
|
],
|
||||||
pluginFor: ["soong_build"],
|
pluginFor: ["soong_build"],
|
||||||
}
|
}
|
||||||
|
148
java/java.go
148
java/java.go
@@ -430,154 +430,6 @@ func (j *Module) targetSdkVersion() string {
|
|||||||
return j.sdkVersion()
|
return j.sdkVersion()
|
||||||
}
|
}
|
||||||
|
|
||||||
type sdkContext interface {
|
|
||||||
// sdkVersion eturns the sdk_version property of the current module, or an empty string if it is not set.
|
|
||||||
sdkVersion() string
|
|
||||||
// minSdkVersion returns the min_sdk_version property of the current module, or sdkVersion() if it is not set.
|
|
||||||
minSdkVersion() string
|
|
||||||
// targetSdkVersion returns the target_sdk_version property of the current module, or sdkVersion() if it is not set.
|
|
||||||
targetSdkVersion() string
|
|
||||||
}
|
|
||||||
|
|
||||||
func sdkVersionOrDefault(ctx android.BaseContext, v string) string {
|
|
||||||
switch v {
|
|
||||||
case "", "current", "system_current", "test_current", "core_current":
|
|
||||||
return ctx.Config().DefaultAppTargetSdk()
|
|
||||||
default:
|
|
||||||
return v
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns a sdk version as a number. For modules targeting an unreleased SDK (meaning it does not yet have a number)
|
|
||||||
// it returns android.FutureApiLevel (10000).
|
|
||||||
func sdkVersionToNumber(ctx android.BaseContext, v string) (int, error) {
|
|
||||||
switch v {
|
|
||||||
case "", "current", "test_current", "system_current", "core_current":
|
|
||||||
return ctx.Config().DefaultAppTargetSdkInt(), nil
|
|
||||||
default:
|
|
||||||
n := android.GetNumericSdkVersion(v)
|
|
||||||
if i, err := strconv.Atoi(n); err != nil {
|
|
||||||
return -1, fmt.Errorf("invalid sdk version %q", n)
|
|
||||||
} else {
|
|
||||||
return i, nil
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func sdkVersionToNumberAsString(ctx android.BaseContext, v string) (string, error) {
|
|
||||||
n, err := sdkVersionToNumber(ctx, v)
|
|
||||||
if err != nil {
|
|
||||||
return "", err
|
|
||||||
}
|
|
||||||
return strconv.Itoa(n), nil
|
|
||||||
}
|
|
||||||
|
|
||||||
func decodeSdkDep(ctx android.BaseContext, sdkContext sdkContext) sdkDep {
|
|
||||||
v := sdkContext.sdkVersion()
|
|
||||||
i, err := sdkVersionToNumber(ctx, v)
|
|
||||||
if err != nil {
|
|
||||||
ctx.PropertyErrorf("sdk_version", "%s", err)
|
|
||||||
return sdkDep{}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Ensures that the specificed system SDK version is one of BOARD_SYSTEMSDK_VERSIONS (for vendor apks)
|
|
||||||
// or PRODUCT_SYSTEMSDK_VERSIONS (for other apks or when BOARD_SYSTEMSDK_VERSIONS is not set)
|
|
||||||
if strings.HasPrefix(v, "system_") && i != android.FutureApiLevel {
|
|
||||||
allowed_versions := ctx.DeviceConfig().PlatformSystemSdkVersions()
|
|
||||||
if ctx.DeviceSpecific() || ctx.SocSpecific() {
|
|
||||||
if len(ctx.DeviceConfig().SystemSdkVersions()) > 0 {
|
|
||||||
allowed_versions = ctx.DeviceConfig().SystemSdkVersions()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
version := strings.TrimPrefix(v, "system_")
|
|
||||||
if len(allowed_versions) > 0 && !android.InList(version, allowed_versions) {
|
|
||||||
ctx.PropertyErrorf("sdk_version", "incompatible sdk version %q. System SDK version should be one of %q",
|
|
||||||
v, allowed_versions)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
toPrebuilt := func(sdk string) sdkDep {
|
|
||||||
var api, v string
|
|
||||||
if strings.Contains(sdk, "_") {
|
|
||||||
t := strings.Split(sdk, "_")
|
|
||||||
api = t[0]
|
|
||||||
v = t[1]
|
|
||||||
} else {
|
|
||||||
api = "public"
|
|
||||||
v = sdk
|
|
||||||
}
|
|
||||||
dir := filepath.Join("prebuilts", "sdk", v, api)
|
|
||||||
jar := filepath.Join(dir, "android.jar")
|
|
||||||
// There's no aidl for other SDKs yet.
|
|
||||||
// TODO(77525052): Add aidl files for other SDKs too.
|
|
||||||
public_dir := filepath.Join("prebuilts", "sdk", v, "public")
|
|
||||||
aidl := filepath.Join(public_dir, "framework.aidl")
|
|
||||||
jarPath := android.ExistentPathForSource(ctx, jar)
|
|
||||||
aidlPath := android.ExistentPathForSource(ctx, aidl)
|
|
||||||
lambdaStubsPath := android.PathForSource(ctx, config.SdkLambdaStubsPath)
|
|
||||||
|
|
||||||
if (!jarPath.Valid() || !aidlPath.Valid()) && ctx.Config().AllowMissingDependencies() {
|
|
||||||
return sdkDep{
|
|
||||||
invalidVersion: true,
|
|
||||||
modules: []string{fmt.Sprintf("sdk_%s_%s_android", api, v)},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if !jarPath.Valid() {
|
|
||||||
ctx.PropertyErrorf("sdk_version", "invalid sdk version %q, %q does not exist", v, jar)
|
|
||||||
return sdkDep{}
|
|
||||||
}
|
|
||||||
|
|
||||||
if !aidlPath.Valid() {
|
|
||||||
ctx.PropertyErrorf("sdk_version", "invalid sdk version %q, %q does not exist", v, aidl)
|
|
||||||
return sdkDep{}
|
|
||||||
}
|
|
||||||
|
|
||||||
return sdkDep{
|
|
||||||
useFiles: true,
|
|
||||||
jars: android.Paths{jarPath.Path(), lambdaStubsPath},
|
|
||||||
aidl: aidlPath.Path(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
toModule := func(m, r string) sdkDep {
|
|
||||||
ret := sdkDep{
|
|
||||||
useModule: true,
|
|
||||||
modules: []string{m, config.DefaultLambdaStubsLibrary},
|
|
||||||
systemModules: m + "_system_modules",
|
|
||||||
frameworkResModule: r,
|
|
||||||
}
|
|
||||||
if m == "core.current.stubs" {
|
|
||||||
ret.systemModules = "core-system-modules"
|
|
||||||
} else if m == "core.platform.api.stubs" {
|
|
||||||
ret.systemModules = "core-platform-api-stubs-system-modules"
|
|
||||||
}
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
if ctx.Config().UnbundledBuildPrebuiltSdks() && v != "" {
|
|
||||||
return toPrebuilt(v)
|
|
||||||
}
|
|
||||||
|
|
||||||
switch v {
|
|
||||||
case "":
|
|
||||||
return sdkDep{
|
|
||||||
useDefaultLibs: true,
|
|
||||||
frameworkResModule: "framework-res",
|
|
||||||
}
|
|
||||||
case "current":
|
|
||||||
return toModule("android_stubs_current", "framework-res")
|
|
||||||
case "system_current":
|
|
||||||
return toModule("android_system_stubs_current", "framework-res")
|
|
||||||
case "test_current":
|
|
||||||
return toModule("android_test_stubs_current", "framework-res")
|
|
||||||
case "core_current":
|
|
||||||
return toModule("core.current.stubs", "")
|
|
||||||
default:
|
|
||||||
return toPrebuilt(v)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func (j *Module) deps(ctx android.BottomUpMutatorContext) {
|
func (j *Module) deps(ctx android.BottomUpMutatorContext) {
|
||||||
if ctx.Device() {
|
if ctx.Device() {
|
||||||
if !Bool(j.properties.No_standard_libs) {
|
if !Bool(j.properties.No_standard_libs) {
|
||||||
|
@@ -19,13 +19,10 @@ import (
|
|||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"os"
|
"os"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
"reflect"
|
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/google/blueprint/proptools"
|
|
||||||
|
|
||||||
"android/soong/android"
|
"android/soong/android"
|
||||||
"android/soong/cc"
|
"android/soong/cc"
|
||||||
"android/soong/genrule"
|
"android/soong/genrule"
|
||||||
@@ -354,241 +351,6 @@ func TestBinary(t *testing.T) {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
var classpathTestcases = []struct {
|
|
||||||
name string
|
|
||||||
unbundled bool
|
|
||||||
moduleType string
|
|
||||||
host android.OsClass
|
|
||||||
properties string
|
|
||||||
bootclasspath []string
|
|
||||||
system string
|
|
||||||
classpath []string
|
|
||||||
}{
|
|
||||||
{
|
|
||||||
name: "default",
|
|
||||||
bootclasspath: []string{"core.platform.api.stubs", "core-lambda-stubs"},
|
|
||||||
system: "core-platform-api-stubs-system-modules",
|
|
||||||
classpath: []string{"ext", "framework"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "blank sdk version",
|
|
||||||
properties: `sdk_version: "",`,
|
|
||||||
bootclasspath: []string{"core.platform.api.stubs", "core-lambda-stubs"},
|
|
||||||
system: "core-platform-api-stubs-system-modules",
|
|
||||||
classpath: []string{"ext", "framework"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "sdk v14",
|
|
||||||
properties: `sdk_version: "14",`,
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
classpath: []string{"prebuilts/sdk/14/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "current",
|
|
||||||
properties: `sdk_version: "current",`,
|
|
||||||
bootclasspath: []string{"android_stubs_current", "core-lambda-stubs"},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "system_current",
|
|
||||||
properties: `sdk_version: "system_current",`,
|
|
||||||
bootclasspath: []string{"android_system_stubs_current", "core-lambda-stubs"},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "system_14",
|
|
||||||
properties: `sdk_version: "system_14",`,
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
classpath: []string{"prebuilts/sdk/14/system/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "test_current",
|
|
||||||
properties: `sdk_version: "test_current",`,
|
|
||||||
bootclasspath: []string{"android_test_stubs_current", "core-lambda-stubs"},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "core_current",
|
|
||||||
properties: `sdk_version: "core_current",`,
|
|
||||||
bootclasspath: []string{"core.current.stubs", "core-lambda-stubs"},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "nostdlib",
|
|
||||||
properties: `no_standard_libs: true, system_modules: "none"`,
|
|
||||||
system: "none",
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
classpath: []string{},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "nostdlib system_modules",
|
|
||||||
properties: `no_standard_libs: true, system_modules: "core-platform-api-stubs-system-modules"`,
|
|
||||||
system: "core-platform-api-stubs-system-modules",
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
classpath: []string{},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "host default",
|
|
||||||
moduleType: "java_library_host",
|
|
||||||
properties: ``,
|
|
||||||
host: android.Host,
|
|
||||||
bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
|
|
||||||
classpath: []string{},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "host nostdlib",
|
|
||||||
moduleType: "java_library_host",
|
|
||||||
host: android.Host,
|
|
||||||
properties: `no_standard_libs: true`,
|
|
||||||
classpath: []string{},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "host supported default",
|
|
||||||
host: android.Host,
|
|
||||||
properties: `host_supported: true,`,
|
|
||||||
classpath: []string{},
|
|
||||||
bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "host supported nostdlib",
|
|
||||||
host: android.Host,
|
|
||||||
properties: `host_supported: true, no_standard_libs: true, system_modules: "none"`,
|
|
||||||
classpath: []string{},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "unbundled sdk v14",
|
|
||||||
unbundled: true,
|
|
||||||
properties: `sdk_version: "14",`,
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
classpath: []string{"prebuilts/sdk/14/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
|
||||||
},
|
|
||||||
{
|
|
||||||
|
|
||||||
name: "unbundled current",
|
|
||||||
unbundled: true,
|
|
||||||
properties: `sdk_version: "current",`,
|
|
||||||
bootclasspath: []string{`""`},
|
|
||||||
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
|
||||||
classpath: []string{"prebuilts/sdk/current/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestClasspath(t *testing.T) {
|
|
||||||
for _, testcase := range classpathTestcases {
|
|
||||||
t.Run(testcase.name, func(t *testing.T) {
|
|
||||||
moduleType := "java_library"
|
|
||||||
if testcase.moduleType != "" {
|
|
||||||
moduleType = testcase.moduleType
|
|
||||||
}
|
|
||||||
|
|
||||||
bp := moduleType + ` {
|
|
||||||
name: "foo",
|
|
||||||
srcs: ["a.java"],
|
|
||||||
` + testcase.properties + `
|
|
||||||
}`
|
|
||||||
|
|
||||||
variant := "android_common"
|
|
||||||
if testcase.host == android.Host {
|
|
||||||
variant = android.BuildOs.String() + "_common"
|
|
||||||
}
|
|
||||||
|
|
||||||
convertModulesToPaths := func(cp []string) []string {
|
|
||||||
ret := make([]string, len(cp))
|
|
||||||
for i, e := range cp {
|
|
||||||
ret[i] = moduleToPath(e)
|
|
||||||
}
|
|
||||||
return ret
|
|
||||||
}
|
|
||||||
|
|
||||||
bootclasspath := convertModulesToPaths(testcase.bootclasspath)
|
|
||||||
classpath := convertModulesToPaths(testcase.classpath)
|
|
||||||
|
|
||||||
bc := strings.Join(bootclasspath, ":")
|
|
||||||
if bc != "" {
|
|
||||||
bc = "-bootclasspath " + bc
|
|
||||||
}
|
|
||||||
|
|
||||||
c := strings.Join(classpath, ":")
|
|
||||||
if c != "" {
|
|
||||||
c = "-classpath " + c
|
|
||||||
}
|
|
||||||
system := ""
|
|
||||||
if testcase.system == "none" {
|
|
||||||
system = "--system=none"
|
|
||||||
} else if testcase.system != "" {
|
|
||||||
system = "--system=" + filepath.Join(buildDir, ".intermediates", testcase.system, "android_common", "system") + "/"
|
|
||||||
}
|
|
||||||
|
|
||||||
t.Run("1.8", func(t *testing.T) {
|
|
||||||
// Test default javac 1.8
|
|
||||||
config := testConfig(nil)
|
|
||||||
if testcase.unbundled {
|
|
||||||
config.TestProductVariables.Unbundled_build = proptools.BoolPtr(true)
|
|
||||||
}
|
|
||||||
ctx := testContext(config, bp, nil)
|
|
||||||
run(t, ctx, config)
|
|
||||||
|
|
||||||
javac := ctx.ModuleForTests("foo", variant).Rule("javac")
|
|
||||||
|
|
||||||
got := javac.Args["bootClasspath"]
|
|
||||||
if got != bc {
|
|
||||||
t.Errorf("bootclasspath expected %q != got %q", bc, got)
|
|
||||||
}
|
|
||||||
|
|
||||||
got = javac.Args["classpath"]
|
|
||||||
if got != c {
|
|
||||||
t.Errorf("classpath expected %q != got %q", c, got)
|
|
||||||
}
|
|
||||||
|
|
||||||
var deps []string
|
|
||||||
if len(bootclasspath) > 0 && bootclasspath[0] != `""` {
|
|
||||||
deps = append(deps, bootclasspath...)
|
|
||||||
}
|
|
||||||
deps = append(deps, classpath...)
|
|
||||||
|
|
||||||
if !reflect.DeepEqual(javac.Implicits.Strings(), deps) {
|
|
||||||
t.Errorf("implicits expected %q != got %q", deps, javac.Implicits.Strings())
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
// Test again with javac 1.9
|
|
||||||
t.Run("1.9", func(t *testing.T) {
|
|
||||||
config := testConfig(map[string]string{"EXPERIMENTAL_USE_OPENJDK9": "true"})
|
|
||||||
if testcase.unbundled {
|
|
||||||
config.TestProductVariables.Unbundled_build = proptools.BoolPtr(true)
|
|
||||||
}
|
|
||||||
ctx := testContext(config, bp, nil)
|
|
||||||
run(t, ctx, config)
|
|
||||||
|
|
||||||
javac := ctx.ModuleForTests("foo", variant).Rule("javac")
|
|
||||||
got := javac.Args["bootClasspath"]
|
|
||||||
expected := system
|
|
||||||
if testcase.system == "bootclasspath" {
|
|
||||||
expected = bc
|
|
||||||
}
|
|
||||||
if got != expected {
|
|
||||||
t.Errorf("bootclasspath expected %q != got %q", expected, got)
|
|
||||||
}
|
|
||||||
})
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestPrebuilts(t *testing.T) {
|
func TestPrebuilts(t *testing.T) {
|
||||||
ctx := testJava(t, `
|
ctx := testJava(t, `
|
||||||
java_library {
|
java_library {
|
||||||
|
172
java/sdk.go
Normal file
172
java/sdk.go
Normal file
@@ -0,0 +1,172 @@
|
|||||||
|
// Copyright 2019 Google Inc. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
package java
|
||||||
|
|
||||||
|
import (
|
||||||
|
"android/soong/android"
|
||||||
|
"android/soong/java/config"
|
||||||
|
"fmt"
|
||||||
|
"path/filepath"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
type sdkContext interface {
|
||||||
|
// sdkVersion eturns the sdk_version property of the current module, or an empty string if it is not set.
|
||||||
|
sdkVersion() string
|
||||||
|
// minSdkVersion returns the min_sdk_version property of the current module, or sdkVersion() if it is not set.
|
||||||
|
minSdkVersion() string
|
||||||
|
// targetSdkVersion returns the target_sdk_version property of the current module, or sdkVersion() if it is not set.
|
||||||
|
targetSdkVersion() string
|
||||||
|
}
|
||||||
|
|
||||||
|
func sdkVersionOrDefault(ctx android.BaseContext, v string) string {
|
||||||
|
switch v {
|
||||||
|
case "", "current", "system_current", "test_current", "core_current":
|
||||||
|
return ctx.Config().DefaultAppTargetSdk()
|
||||||
|
default:
|
||||||
|
return v
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Returns a sdk version as a number. For modules targeting an unreleased SDK (meaning it does not yet have a number)
|
||||||
|
// it returns android.FutureApiLevel (10000).
|
||||||
|
func sdkVersionToNumber(ctx android.BaseContext, v string) (int, error) {
|
||||||
|
switch v {
|
||||||
|
case "", "current", "test_current", "system_current", "core_current":
|
||||||
|
return ctx.Config().DefaultAppTargetSdkInt(), nil
|
||||||
|
default:
|
||||||
|
n := android.GetNumericSdkVersion(v)
|
||||||
|
if i, err := strconv.Atoi(n); err != nil {
|
||||||
|
return -1, fmt.Errorf("invalid sdk version %q", n)
|
||||||
|
} else {
|
||||||
|
return i, nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func sdkVersionToNumberAsString(ctx android.BaseContext, v string) (string, error) {
|
||||||
|
n, err := sdkVersionToNumber(ctx, v)
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
return strconv.Itoa(n), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func decodeSdkDep(ctx android.BaseContext, sdkContext sdkContext) sdkDep {
|
||||||
|
v := sdkContext.sdkVersion()
|
||||||
|
i, err := sdkVersionToNumber(ctx, v)
|
||||||
|
if err != nil {
|
||||||
|
ctx.PropertyErrorf("sdk_version", "%s", err)
|
||||||
|
return sdkDep{}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ensures that the specificed system SDK version is one of BOARD_SYSTEMSDK_VERSIONS (for vendor apks)
|
||||||
|
// or PRODUCT_SYSTEMSDK_VERSIONS (for other apks or when BOARD_SYSTEMSDK_VERSIONS is not set)
|
||||||
|
if strings.HasPrefix(v, "system_") && i != android.FutureApiLevel {
|
||||||
|
allowed_versions := ctx.DeviceConfig().PlatformSystemSdkVersions()
|
||||||
|
if ctx.DeviceSpecific() || ctx.SocSpecific() {
|
||||||
|
if len(ctx.DeviceConfig().SystemSdkVersions()) > 0 {
|
||||||
|
allowed_versions = ctx.DeviceConfig().SystemSdkVersions()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
version := strings.TrimPrefix(v, "system_")
|
||||||
|
if len(allowed_versions) > 0 && !android.InList(version, allowed_versions) {
|
||||||
|
ctx.PropertyErrorf("sdk_version", "incompatible sdk version %q. System SDK version should be one of %q",
|
||||||
|
v, allowed_versions)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
toPrebuilt := func(sdk string) sdkDep {
|
||||||
|
var api, v string
|
||||||
|
if strings.Contains(sdk, "_") {
|
||||||
|
t := strings.Split(sdk, "_")
|
||||||
|
api = t[0]
|
||||||
|
v = t[1]
|
||||||
|
} else {
|
||||||
|
api = "public"
|
||||||
|
v = sdk
|
||||||
|
}
|
||||||
|
dir := filepath.Join("prebuilts", "sdk", v, api)
|
||||||
|
jar := filepath.Join(dir, "android.jar")
|
||||||
|
// There's no aidl for other SDKs yet.
|
||||||
|
// TODO(77525052): Add aidl files for other SDKs too.
|
||||||
|
public_dir := filepath.Join("prebuilts", "sdk", v, "public")
|
||||||
|
aidl := filepath.Join(public_dir, "framework.aidl")
|
||||||
|
jarPath := android.ExistentPathForSource(ctx, jar)
|
||||||
|
aidlPath := android.ExistentPathForSource(ctx, aidl)
|
||||||
|
lambdaStubsPath := android.PathForSource(ctx, config.SdkLambdaStubsPath)
|
||||||
|
|
||||||
|
if (!jarPath.Valid() || !aidlPath.Valid()) && ctx.Config().AllowMissingDependencies() {
|
||||||
|
return sdkDep{
|
||||||
|
invalidVersion: true,
|
||||||
|
modules: []string{fmt.Sprintf("sdk_%s_%s_android", api, v)},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !jarPath.Valid() {
|
||||||
|
ctx.PropertyErrorf("sdk_version", "invalid sdk version %q, %q does not exist", v, jar)
|
||||||
|
return sdkDep{}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !aidlPath.Valid() {
|
||||||
|
ctx.PropertyErrorf("sdk_version", "invalid sdk version %q, %q does not exist", v, aidl)
|
||||||
|
return sdkDep{}
|
||||||
|
}
|
||||||
|
|
||||||
|
return sdkDep{
|
||||||
|
useFiles: true,
|
||||||
|
jars: android.Paths{jarPath.Path(), lambdaStubsPath},
|
||||||
|
aidl: aidlPath.Path(),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
toModule := func(m, r string) sdkDep {
|
||||||
|
ret := sdkDep{
|
||||||
|
useModule: true,
|
||||||
|
modules: []string{m, config.DefaultLambdaStubsLibrary},
|
||||||
|
systemModules: m + "_system_modules",
|
||||||
|
frameworkResModule: r,
|
||||||
|
}
|
||||||
|
if m == "core.current.stubs" {
|
||||||
|
ret.systemModules = "core-system-modules"
|
||||||
|
} else if m == "core.platform.api.stubs" {
|
||||||
|
ret.systemModules = "core-platform-api-stubs-system-modules"
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
if ctx.Config().UnbundledBuildPrebuiltSdks() && v != "" {
|
||||||
|
return toPrebuilt(v)
|
||||||
|
}
|
||||||
|
|
||||||
|
switch v {
|
||||||
|
case "":
|
||||||
|
return sdkDep{
|
||||||
|
useDefaultLibs: true,
|
||||||
|
frameworkResModule: "framework-res",
|
||||||
|
}
|
||||||
|
case "current":
|
||||||
|
return toModule("android_stubs_current", "framework-res")
|
||||||
|
case "system_current":
|
||||||
|
return toModule("android_system_stubs_current", "framework-res")
|
||||||
|
case "test_current":
|
||||||
|
return toModule("android_test_stubs_current", "framework-res")
|
||||||
|
case "core_current":
|
||||||
|
return toModule("core.current.stubs", "")
|
||||||
|
default:
|
||||||
|
return toPrebuilt(v)
|
||||||
|
}
|
||||||
|
}
|
260
java/sdk_test.go
Normal file
260
java/sdk_test.go
Normal file
@@ -0,0 +1,260 @@
|
|||||||
|
// Copyright 2019 Google Inc. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
package java
|
||||||
|
|
||||||
|
import (
|
||||||
|
"android/soong/android"
|
||||||
|
"path/filepath"
|
||||||
|
"reflect"
|
||||||
|
"strings"
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/google/blueprint/proptools"
|
||||||
|
)
|
||||||
|
|
||||||
|
var classpathTestcases = []struct {
|
||||||
|
name string
|
||||||
|
unbundled bool
|
||||||
|
moduleType string
|
||||||
|
host android.OsClass
|
||||||
|
properties string
|
||||||
|
bootclasspath []string
|
||||||
|
system string
|
||||||
|
classpath []string
|
||||||
|
}{
|
||||||
|
{
|
||||||
|
name: "default",
|
||||||
|
bootclasspath: []string{"core.platform.api.stubs", "core-lambda-stubs"},
|
||||||
|
system: "core-platform-api-stubs-system-modules",
|
||||||
|
classpath: []string{"ext", "framework"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "blank sdk version",
|
||||||
|
properties: `sdk_version: "",`,
|
||||||
|
bootclasspath: []string{"core.platform.api.stubs", "core-lambda-stubs"},
|
||||||
|
system: "core-platform-api-stubs-system-modules",
|
||||||
|
classpath: []string{"ext", "framework"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "sdk v14",
|
||||||
|
properties: `sdk_version: "14",`,
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
classpath: []string{"prebuilts/sdk/14/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "current",
|
||||||
|
properties: `sdk_version: "current",`,
|
||||||
|
bootclasspath: []string{"android_stubs_current", "core-lambda-stubs"},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "system_current",
|
||||||
|
properties: `sdk_version: "system_current",`,
|
||||||
|
bootclasspath: []string{"android_system_stubs_current", "core-lambda-stubs"},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "system_14",
|
||||||
|
properties: `sdk_version: "system_14",`,
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
classpath: []string{"prebuilts/sdk/14/system/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "test_current",
|
||||||
|
properties: `sdk_version: "test_current",`,
|
||||||
|
bootclasspath: []string{"android_test_stubs_current", "core-lambda-stubs"},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "core_current",
|
||||||
|
properties: `sdk_version: "core_current",`,
|
||||||
|
bootclasspath: []string{"core.current.stubs", "core-lambda-stubs"},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "nostdlib",
|
||||||
|
properties: `no_standard_libs: true, system_modules: "none"`,
|
||||||
|
system: "none",
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
classpath: []string{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "nostdlib system_modules",
|
||||||
|
properties: `no_standard_libs: true, system_modules: "core-platform-api-stubs-system-modules"`,
|
||||||
|
system: "core-platform-api-stubs-system-modules",
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
classpath: []string{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "host default",
|
||||||
|
moduleType: "java_library_host",
|
||||||
|
properties: ``,
|
||||||
|
host: android.Host,
|
||||||
|
bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
|
||||||
|
classpath: []string{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "host nostdlib",
|
||||||
|
moduleType: "java_library_host",
|
||||||
|
host: android.Host,
|
||||||
|
properties: `no_standard_libs: true`,
|
||||||
|
classpath: []string{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "host supported default",
|
||||||
|
host: android.Host,
|
||||||
|
properties: `host_supported: true,`,
|
||||||
|
classpath: []string{},
|
||||||
|
bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "host supported nostdlib",
|
||||||
|
host: android.Host,
|
||||||
|
properties: `host_supported: true, no_standard_libs: true, system_modules: "none"`,
|
||||||
|
classpath: []string{},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "unbundled sdk v14",
|
||||||
|
unbundled: true,
|
||||||
|
properties: `sdk_version: "14",`,
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
classpath: []string{"prebuilts/sdk/14/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
|
||||||
|
name: "unbundled current",
|
||||||
|
unbundled: true,
|
||||||
|
properties: `sdk_version: "current",`,
|
||||||
|
bootclasspath: []string{`""`},
|
||||||
|
system: "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
|
||||||
|
classpath: []string{"prebuilts/sdk/current/public/android.jar", "prebuilts/sdk/tools/core-lambda-stubs.jar"},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestClasspath(t *testing.T) {
|
||||||
|
for _, testcase := range classpathTestcases {
|
||||||
|
t.Run(testcase.name, func(t *testing.T) {
|
||||||
|
moduleType := "java_library"
|
||||||
|
if testcase.moduleType != "" {
|
||||||
|
moduleType = testcase.moduleType
|
||||||
|
}
|
||||||
|
|
||||||
|
bp := moduleType + ` {
|
||||||
|
name: "foo",
|
||||||
|
srcs: ["a.java"],
|
||||||
|
` + testcase.properties + `
|
||||||
|
}`
|
||||||
|
|
||||||
|
variant := "android_common"
|
||||||
|
if testcase.host == android.Host {
|
||||||
|
variant = android.BuildOs.String() + "_common"
|
||||||
|
}
|
||||||
|
|
||||||
|
convertModulesToPaths := func(cp []string) []string {
|
||||||
|
ret := make([]string, len(cp))
|
||||||
|
for i, e := range cp {
|
||||||
|
ret[i] = moduleToPath(e)
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
bootclasspath := convertModulesToPaths(testcase.bootclasspath)
|
||||||
|
classpath := convertModulesToPaths(testcase.classpath)
|
||||||
|
|
||||||
|
bc := strings.Join(bootclasspath, ":")
|
||||||
|
if bc != "" {
|
||||||
|
bc = "-bootclasspath " + bc
|
||||||
|
}
|
||||||
|
|
||||||
|
c := strings.Join(classpath, ":")
|
||||||
|
if c != "" {
|
||||||
|
c = "-classpath " + c
|
||||||
|
}
|
||||||
|
system := ""
|
||||||
|
if testcase.system == "none" {
|
||||||
|
system = "--system=none"
|
||||||
|
} else if testcase.system != "" {
|
||||||
|
system = "--system=" + filepath.Join(buildDir, ".intermediates", testcase.system, "android_common", "system") + "/"
|
||||||
|
}
|
||||||
|
|
||||||
|
t.Run("1.8", func(t *testing.T) {
|
||||||
|
// Test default javac 1.8
|
||||||
|
config := testConfig(nil)
|
||||||
|
if testcase.unbundled {
|
||||||
|
config.TestProductVariables.Unbundled_build = proptools.BoolPtr(true)
|
||||||
|
}
|
||||||
|
ctx := testContext(config, bp, nil)
|
||||||
|
run(t, ctx, config)
|
||||||
|
|
||||||
|
javac := ctx.ModuleForTests("foo", variant).Rule("javac")
|
||||||
|
|
||||||
|
got := javac.Args["bootClasspath"]
|
||||||
|
if got != bc {
|
||||||
|
t.Errorf("bootclasspath expected %q != got %q", bc, got)
|
||||||
|
}
|
||||||
|
|
||||||
|
got = javac.Args["classpath"]
|
||||||
|
if got != c {
|
||||||
|
t.Errorf("classpath expected %q != got %q", c, got)
|
||||||
|
}
|
||||||
|
|
||||||
|
var deps []string
|
||||||
|
if len(bootclasspath) > 0 && bootclasspath[0] != `""` {
|
||||||
|
deps = append(deps, bootclasspath...)
|
||||||
|
}
|
||||||
|
deps = append(deps, classpath...)
|
||||||
|
|
||||||
|
if !reflect.DeepEqual(javac.Implicits.Strings(), deps) {
|
||||||
|
t.Errorf("implicits expected %q != got %q", deps, javac.Implicits.Strings())
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
// Test again with javac 1.9
|
||||||
|
t.Run("1.9", func(t *testing.T) {
|
||||||
|
config := testConfig(map[string]string{"EXPERIMENTAL_USE_OPENJDK9": "true"})
|
||||||
|
if testcase.unbundled {
|
||||||
|
config.TestProductVariables.Unbundled_build = proptools.BoolPtr(true)
|
||||||
|
}
|
||||||
|
ctx := testContext(config, bp, nil)
|
||||||
|
run(t, ctx, config)
|
||||||
|
|
||||||
|
javac := ctx.ModuleForTests("foo", variant).Rule("javac")
|
||||||
|
got := javac.Args["bootClasspath"]
|
||||||
|
expected := system
|
||||||
|
if testcase.system == "bootclasspath" {
|
||||||
|
expected = bc
|
||||||
|
}
|
||||||
|
if got != expected {
|
||||||
|
t.Errorf("bootclasspath expected %q != got %q", expected, got)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
Reference in New Issue
Block a user