Support sdk_version: "core_current"

core_current is a pseudo SDK version which is a core Java API subset of
the Android API. It is expected to be mainly used for external Java
projects which are agnostic to Android; such as junit, guava, etc.

A module built with this SDK version can only link to java modules of
the same kind. It can't depend on modules built with other sdk  (e.g.
current) or without sdk.

Bug: 72206056
Test: m -j
Change-Id: I778e7b4fcb9456a12b418ffd633ea78e29951e84
diff --git a/java/java.go b/java/java.go
index b2fbc42..8312ecc 100644
--- a/java/java.go
+++ b/java/java.go
@@ -315,7 +315,7 @@
 
 func sdkStringToNumber(ctx android.BaseContext, v string) int {
 	switch v {
-	case "", "current", "system_current", "test_current":
+	case "", "current", "system_current", "test_current", "core_current":
 		return android.FutureApiLevel
 	default:
 		if i, err := strconv.Atoi(android.GetNumericSdkVersion(v)); err != nil {
@@ -361,8 +361,15 @@
 	}
 
 	toFile := func(v string) sdkDep {
+		isCore := strings.HasPrefix(v, "core_")
+		if isCore {
+			v = strings.TrimPrefix(v, "core_")
+		}
 		dir := filepath.Join("prebuilts/sdk", v)
 		jar := filepath.Join(dir, "android.jar")
+		if isCore {
+			jar = filepath.Join(dir, "core.jar")
+		}
 		aidl := filepath.Join(dir, "framework.aidl")
 		jarPath := android.ExistentPathForSource(ctx, "sdkdir", jar)
 		aidlPath := android.ExistentPathForSource(ctx, "sdkdir", aidl)
@@ -557,6 +564,15 @@
 	}
 }
 
+func checkLinkType(ctx android.ModuleContext, from *Module, to *Library, tag dependencyTag) {
+	if strings.HasPrefix(String(from.deviceProperties.Sdk_version), "core_") {
+		if !strings.HasPrefix(String(to.deviceProperties.Sdk_version), "core_") {
+			ctx.ModuleErrorf("depends on other library %q using non-core Java APIs",
+				ctx.OtherModuleName(to))
+		}
+	}
+}
+
 func (j *Module) collectDeps(ctx android.ModuleContext) deps {
 	var deps deps
 
@@ -573,6 +589,9 @@
 		otherName := ctx.OtherModuleName(module)
 		tag := ctx.OtherModuleDependencyTag(module)
 
+		if to, ok := module.(*Library); ok {
+			checkLinkType(ctx, j, to, tag.(dependencyTag))
+		}
 		switch dep := module.(type) {
 		case Dependency:
 			switch tag {
@@ -989,7 +1008,7 @@
 // modules targeting an unreleased SDK (meaning it does not yet have a number) it returns "10000".
 func (j *Module) minSdkVersionNumber(ctx android.ModuleContext) string {
 	switch String(j.deviceProperties.Sdk_version) {
-	case "", "current", "test_current", "system_current":
+	case "", "current", "test_current", "system_current", "core_current":
 		return strconv.Itoa(ctx.Config().DefaultAppTargetSdkInt())
 	default:
 		return android.GetNumericSdkVersion(String(j.deviceProperties.Sdk_version))