github.com/westcoastroms/westcoastroms-build@v0.0.0-20190928114312-2350e5a73030/build/soong/java/java_test.go (about)

     1  // 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  
    15  package java
    16  
    17  import (
    18  	"android/soong/android"
    19  	"android/soong/genrule"
    20  	"fmt"
    21  	"io/ioutil"
    22  	"os"
    23  	"path/filepath"
    24  	"reflect"
    25  	"strconv"
    26  	"strings"
    27  	"testing"
    28  )
    29  
    30  var buildDir string
    31  
    32  func setUp() {
    33  	var err error
    34  	buildDir, err = ioutil.TempDir("", "soong_java_test")
    35  	if err != nil {
    36  		panic(err)
    37  	}
    38  }
    39  
    40  func tearDown() {
    41  	os.RemoveAll(buildDir)
    42  }
    43  
    44  func TestMain(m *testing.M) {
    45  	run := func() int {
    46  		setUp()
    47  		defer tearDown()
    48  
    49  		return m.Run()
    50  	}
    51  
    52  	os.Exit(run())
    53  }
    54  
    55  func testConfig(env map[string]string) android.Config {
    56  	if env == nil {
    57  		env = make(map[string]string)
    58  	}
    59  	if env["ANDROID_JAVA8_HOME"] == "" {
    60  		env["ANDROID_JAVA8_HOME"] = "jdk8"
    61  	}
    62  	config := android.TestArchConfig(buildDir, env)
    63  	config.TestProductVariables.DeviceSystemSdkVersions = &[]string{"14", "15"}
    64  	return config
    65  
    66  }
    67  
    68  func testContext(config android.Config, bp string,
    69  	fs map[string][]byte) *android.TestContext {
    70  
    71  	ctx := android.NewTestArchContext()
    72  	ctx.RegisterModuleType("android_app", android.ModuleFactoryAdaptor(AndroidAppFactory))
    73  	ctx.RegisterModuleType("android_library", android.ModuleFactoryAdaptor(AndroidLibraryFactory))
    74  	ctx.RegisterModuleType("java_binary_host", android.ModuleFactoryAdaptor(BinaryHostFactory))
    75  	ctx.RegisterModuleType("java_library", android.ModuleFactoryAdaptor(LibraryFactory(true)))
    76  	ctx.RegisterModuleType("java_library_host", android.ModuleFactoryAdaptor(LibraryHostFactory))
    77  	ctx.RegisterModuleType("java_import", android.ModuleFactoryAdaptor(ImportFactory))
    78  	ctx.RegisterModuleType("java_defaults", android.ModuleFactoryAdaptor(defaultsFactory))
    79  	ctx.RegisterModuleType("java_system_modules", android.ModuleFactoryAdaptor(SystemModulesFactory))
    80  	ctx.RegisterModuleType("java_genrule", android.ModuleFactoryAdaptor(genRuleFactory))
    81  	ctx.RegisterModuleType("filegroup", android.ModuleFactoryAdaptor(genrule.FileGroupFactory))
    82  	ctx.RegisterModuleType("genrule", android.ModuleFactoryAdaptor(genrule.GenRuleFactory))
    83  	ctx.RegisterModuleType("droiddoc", android.ModuleFactoryAdaptor(DroiddocFactory))
    84  	ctx.RegisterModuleType("droiddoc_host", android.ModuleFactoryAdaptor(DroiddocHostFactory))
    85  	ctx.RegisterModuleType("droiddoc_template", android.ModuleFactoryAdaptor(DroiddocTemplateFactory))
    86  	ctx.PreArchMutators(android.RegisterPrebuiltsPreArchMutators)
    87  	ctx.PreArchMutators(android.RegisterPrebuiltsPostDepsMutators)
    88  	ctx.PreArchMutators(android.RegisterDefaultsPreArchMutators)
    89  	ctx.RegisterPreSingletonType("overlay", android.SingletonFactoryAdaptor(OverlaySingletonFactory))
    90  	ctx.Register()
    91  
    92  	extraModules := []string{
    93  		"core-oj",
    94  		"core-libart",
    95  		"framework",
    96  		"ext",
    97  		"okhttp",
    98  		"android_stubs_current",
    99  		"android_system_stubs_current",
   100  		"android_test_stubs_current",
   101  		"kotlin-stdlib",
   102  	}
   103  
   104  	for _, extra := range extraModules {
   105  		bp += fmt.Sprintf(`
   106  			java_library {
   107  				name: "%s",
   108  				srcs: ["a.java"],
   109  				no_standard_libs: true,
   110  				system_modules: "core-system-modules",
   111  			}
   112  		`, extra)
   113  	}
   114  
   115  	bp += `
   116  		android_app {
   117  			name: "framework-res",
   118  			no_framework_libs: true,
   119  		}
   120  	`
   121  
   122  	systemModules := []string{
   123  		"core-system-modules",
   124  		"android_stubs_current_system_modules",
   125  		"android_system_stubs_current_system_modules",
   126  		"android_test_stubs_current_system_modules",
   127  	}
   128  
   129  	for _, extra := range systemModules {
   130  		bp += fmt.Sprintf(`
   131  			java_system_modules {
   132  				name: "%s",
   133  			}
   134  		`, extra)
   135  	}
   136  
   137  	mockFS := map[string][]byte{
   138  		"Android.bp":     []byte(bp),
   139  		"a.java":         nil,
   140  		"b.java":         nil,
   141  		"c.java":         nil,
   142  		"b.kt":           nil,
   143  		"a.jar":          nil,
   144  		"b.jar":          nil,
   145  		"java-res/a":     nil,
   146  		"java-res/b":     nil,
   147  		"java-res2/a":    nil,
   148  		"java-fg/a.java": nil,
   149  		"java-fg/b.java": nil,
   150  		"java-fg/c.java": nil,
   151  
   152  		"prebuilts/sdk/14/android.jar":                nil,
   153  		"prebuilts/sdk/14/framework.aidl":             nil,
   154  		"prebuilts/sdk/current/android.jar":           nil,
   155  		"prebuilts/sdk/current/framework.aidl":        nil,
   156  		"prebuilts/sdk/current/core.jar":              nil,
   157  		"prebuilts/sdk/system_current/android.jar":    nil,
   158  		"prebuilts/sdk/system_current/framework.aidl": nil,
   159  		"prebuilts/sdk/system_14/android.jar":         nil,
   160  		"prebuilts/sdk/system_14/framework.aidl":      nil,
   161  		"prebuilts/sdk/test_current/android.jar":      nil,
   162  		"prebuilts/sdk/test_current/framework.aidl":   nil,
   163  
   164  		// For framework-res, which is an implicit dependency for framework
   165  		"AndroidManifest.xml":                   nil,
   166  		"build/target/product/security/testkey": nil,
   167  
   168  		"build/soong/scripts/jar-wrapper.sh": nil,
   169  
   170  		"build/make/core/proguard.flags":             nil,
   171  		"build/make/core/proguard_basic_keeps.flags": nil,
   172  
   173  		"jdk8/jre/lib/jce.jar": nil,
   174  		"jdk8/jre/lib/rt.jar":  nil,
   175  
   176  		"bar-doc/a.java":                 nil,
   177  		"bar-doc/b.java":                 nil,
   178  		"bar-doc/known_oj_tags.txt":      nil,
   179  		"external/doclava/templates-sdk": nil,
   180  	}
   181  
   182  	for k, v := range fs {
   183  		mockFS[k] = v
   184  	}
   185  
   186  	ctx.MockFileSystem(mockFS)
   187  
   188  	return ctx
   189  }
   190  
   191  func run(t *testing.T, ctx *android.TestContext, config android.Config) {
   192  	t.Helper()
   193  	_, errs := ctx.ParseFileList(".", []string{"Android.bp"})
   194  	android.FailIfErrored(t, errs)
   195  	_, errs = ctx.PrepareBuildActions(config)
   196  	android.FailIfErrored(t, errs)
   197  }
   198  
   199  func testJava(t *testing.T, bp string) *android.TestContext {
   200  	t.Helper()
   201  	config := testConfig(nil)
   202  	ctx := testContext(config, bp, nil)
   203  	run(t, ctx, config)
   204  
   205  	return ctx
   206  }
   207  
   208  func moduleToPath(name string) string {
   209  	switch {
   210  	case name == `""`:
   211  		return name
   212  	case strings.HasSuffix(name, ".jar"):
   213  		return name
   214  	case name == "android_stubs_current" || name == "android_system_stubs_current" ||
   215  		name == "android_test_stubs_current":
   216  		return filepath.Join(buildDir, ".intermediates", name, "android_common", "javac", name+".jar")
   217  	default:
   218  		return filepath.Join(buildDir, ".intermediates", name, "android_common", "turbine-combined", name+".jar")
   219  	}
   220  }
   221  
   222  func TestSimple(t *testing.T) {
   223  	ctx := testJava(t, `
   224  		java_library {
   225  			name: "foo",
   226  			srcs: ["a.java"],
   227  			libs: ["bar"],
   228  			static_libs: ["baz"],
   229  		}
   230  
   231  		java_library {
   232  			name: "bar",
   233  			srcs: ["b.java"],
   234  		}
   235  
   236  		java_library {
   237  			name: "baz",
   238  			srcs: ["c.java"],
   239  		}
   240  	`)
   241  
   242  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   243  	combineJar := ctx.ModuleForTests("foo", "android_common").Description("for javac")
   244  
   245  	if len(javac.Inputs) != 1 || javac.Inputs[0].String() != "a.java" {
   246  		t.Errorf(`foo inputs %v != ["a.java"]`, javac.Inputs)
   247  	}
   248  
   249  	baz := ctx.ModuleForTests("baz", "android_common").Rule("javac").Output.String()
   250  	barTurbine := filepath.Join(buildDir, ".intermediates", "bar", "android_common", "turbine-combined", "bar.jar")
   251  	bazTurbine := filepath.Join(buildDir, ".intermediates", "baz", "android_common", "turbine-combined", "baz.jar")
   252  
   253  	if !strings.Contains(javac.Args["classpath"], barTurbine) {
   254  		t.Errorf("foo classpath %v does not contain %q", javac.Args["classpath"], barTurbine)
   255  	}
   256  
   257  	if !strings.Contains(javac.Args["classpath"], bazTurbine) {
   258  		t.Errorf("foo classpath %v does not contain %q", javac.Args["classpath"], bazTurbine)
   259  	}
   260  
   261  	if len(combineJar.Inputs) != 2 || combineJar.Inputs[1].String() != baz {
   262  		t.Errorf("foo combineJar inputs %v does not contain %q", combineJar.Inputs, baz)
   263  	}
   264  }
   265  
   266  func TestArchSpecific(t *testing.T) {
   267  	ctx := testJava(t, `
   268  		java_library {
   269  			name: "foo",
   270  			srcs: ["a.java"],
   271  			target: {
   272  				android: {
   273  					srcs: ["b.java"],
   274  				},
   275  			},
   276  		}
   277  	`)
   278  
   279  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   280  	if len(javac.Inputs) != 2 || javac.Inputs[0].String() != "a.java" || javac.Inputs[1].String() != "b.java" {
   281  		t.Errorf(`foo inputs %v != ["a.java", "b.java"]`, javac.Inputs)
   282  	}
   283  }
   284  
   285  func TestBinary(t *testing.T) {
   286  	ctx := testJava(t, `
   287  		java_library_host {
   288  			name: "foo",
   289  			srcs: ["a.java"],
   290  		}
   291  
   292  		java_binary_host {
   293  			name: "bar",
   294  			srcs: ["b.java"],
   295  			static_libs: ["foo"],
   296  		}
   297  	`)
   298  
   299  	buildOS := android.BuildOs.String()
   300  
   301  	bar := ctx.ModuleForTests("bar", buildOS+"_common")
   302  	barJar := bar.Output("bar.jar").Output.String()
   303  	barWrapper := ctx.ModuleForTests("bar", buildOS+"_x86_64")
   304  	barWrapperDeps := barWrapper.Output("bar").Implicits.Strings()
   305  
   306  	// Test that the install binary wrapper depends on the installed jar file
   307  	if len(barWrapperDeps) != 1 || barWrapperDeps[0] != barJar {
   308  		t.Errorf("expected binary wrapper implicits [%q], got %v",
   309  			barJar, barWrapperDeps)
   310  	}
   311  
   312  }
   313  
   314  var classpathTestcases = []struct {
   315  	name          string
   316  	moduleType    string
   317  	host          android.OsClass
   318  	properties    string
   319  	bootclasspath []string
   320  	system        string
   321  	classpath     []string
   322  }{
   323  	{
   324  		name:          "default",
   325  		bootclasspath: []string{"core-oj", "core-libart"},
   326  		system:        "core-system-modules",
   327  		classpath:     []string{"ext", "framework", "okhttp"},
   328  	},
   329  	{
   330  		name:          "blank sdk version",
   331  		properties:    `sdk_version: "",`,
   332  		bootclasspath: []string{"core-oj", "core-libart"},
   333  		system:        "core-system-modules",
   334  		classpath:     []string{"ext", "framework", "okhttp"},
   335  	},
   336  	{
   337  
   338  		name:          "sdk v14",
   339  		properties:    `sdk_version: "14",`,
   340  		bootclasspath: []string{`""`},
   341  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   342  		classpath:     []string{"prebuilts/sdk/14/android.jar"},
   343  	},
   344  	{
   345  
   346  		name:          "current",
   347  		properties:    `sdk_version: "current",`,
   348  		bootclasspath: []string{`""`},
   349  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   350  		classpath:     []string{"prebuilts/sdk/current/android.jar"},
   351  	},
   352  	{
   353  
   354  		name:          "system_current",
   355  		properties:    `sdk_version: "system_current",`,
   356  		bootclasspath: []string{`""`},
   357  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   358  		classpath:     []string{"prebuilts/sdk/system_current/android.jar"},
   359  	},
   360  	{
   361  
   362  		name:          "system_14",
   363  		properties:    `sdk_version: "system_14",`,
   364  		bootclasspath: []string{`""`},
   365  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   366  		classpath:     []string{"prebuilts/sdk/system_14/android.jar"},
   367  	},
   368  	{
   369  
   370  		name:          "test_current",
   371  		properties:    `sdk_version: "test_current",`,
   372  		bootclasspath: []string{`""`},
   373  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   374  		classpath:     []string{"prebuilts/sdk/test_current/android.jar"},
   375  	},
   376  	{
   377  
   378  		name:          "core_current",
   379  		properties:    `sdk_version: "core_current",`,
   380  		bootclasspath: []string{`""`},
   381  		system:        "bootclasspath", // special value to tell 1.9 test to expect bootclasspath
   382  		classpath:     []string{"prebuilts/sdk/current/core.jar"},
   383  	},
   384  	{
   385  
   386  		name:          "nostdlib",
   387  		properties:    `no_standard_libs: true, system_modules: "none"`,
   388  		system:        "none",
   389  		bootclasspath: []string{`""`},
   390  		classpath:     []string{},
   391  	},
   392  	{
   393  
   394  		name:          "nostdlib system_modules",
   395  		properties:    `no_standard_libs: true, system_modules: "core-system-modules"`,
   396  		system:        "core-system-modules",
   397  		bootclasspath: []string{`""`},
   398  		classpath:     []string{},
   399  	},
   400  	{
   401  
   402  		name:          "host default",
   403  		moduleType:    "java_library_host",
   404  		properties:    ``,
   405  		host:          android.Host,
   406  		bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
   407  		classpath:     []string{},
   408  	},
   409  	{
   410  		name:       "host nostdlib",
   411  		moduleType: "java_library_host",
   412  		host:       android.Host,
   413  		properties: `no_standard_libs: true`,
   414  		classpath:  []string{},
   415  	},
   416  	{
   417  
   418  		name:          "host supported default",
   419  		host:          android.Host,
   420  		properties:    `host_supported: true,`,
   421  		classpath:     []string{},
   422  		bootclasspath: []string{"jdk8/jre/lib/jce.jar", "jdk8/jre/lib/rt.jar"},
   423  	},
   424  	{
   425  		name:       "host supported nostdlib",
   426  		host:       android.Host,
   427  		properties: `host_supported: true, no_standard_libs: true, system_modules: "none"`,
   428  		classpath:  []string{},
   429  	},
   430  }
   431  
   432  func TestClasspath(t *testing.T) {
   433  	for _, testcase := range classpathTestcases {
   434  		t.Run(testcase.name, func(t *testing.T) {
   435  			moduleType := "java_library"
   436  			if testcase.moduleType != "" {
   437  				moduleType = testcase.moduleType
   438  			}
   439  
   440  			bp := moduleType + ` {
   441  				name: "foo",
   442  				srcs: ["a.java"],
   443  				` + testcase.properties + `
   444  			}`
   445  
   446  			variant := "android_common"
   447  			if testcase.host == android.Host {
   448  				variant = android.BuildOs.String() + "_common"
   449  			}
   450  
   451  			convertModulesToPaths := func(cp []string) []string {
   452  				ret := make([]string, len(cp))
   453  				for i, e := range cp {
   454  					ret[i] = moduleToPath(e)
   455  				}
   456  				return ret
   457  			}
   458  
   459  			bootclasspath := convertModulesToPaths(testcase.bootclasspath)
   460  			classpath := convertModulesToPaths(testcase.classpath)
   461  
   462  			bc := strings.Join(bootclasspath, ":")
   463  			if bc != "" {
   464  				bc = "-bootclasspath " + bc
   465  			}
   466  
   467  			c := strings.Join(classpath, ":")
   468  			if c != "" {
   469  				c = "-classpath " + c
   470  			}
   471  			system := ""
   472  			if testcase.system == "none" {
   473  				system = "--system=none"
   474  			} else if testcase.system != "" {
   475  				system = "--system=" + filepath.Join(buildDir, ".intermediates", testcase.system, "android_common", "system") + "/"
   476  			}
   477  
   478  			t.Run("1.8", func(t *testing.T) {
   479  				// Test default javac 1.8
   480  				ctx := testJava(t, bp)
   481  
   482  				javac := ctx.ModuleForTests("foo", variant).Rule("javac")
   483  
   484  				got := javac.Args["bootClasspath"]
   485  				if got != bc {
   486  					t.Errorf("bootclasspath expected %q != got %q", bc, got)
   487  				}
   488  
   489  				got = javac.Args["classpath"]
   490  				if got != c {
   491  					t.Errorf("classpath expected %q != got %q", c, got)
   492  				}
   493  
   494  				var deps []string
   495  				if len(bootclasspath) > 0 && bootclasspath[0] != `""` {
   496  					deps = append(deps, bootclasspath...)
   497  				}
   498  				deps = append(deps, classpath...)
   499  
   500  				if !reflect.DeepEqual(javac.Implicits.Strings(), deps) {
   501  					t.Errorf("implicits expected %q != got %q", deps, javac.Implicits.Strings())
   502  				}
   503  			})
   504  
   505  			// Test again with javac 1.9
   506  			t.Run("1.9", func(t *testing.T) {
   507  				config := testConfig(map[string]string{"EXPERIMENTAL_USE_OPENJDK9": "true"})
   508  				ctx := testContext(config, bp, nil)
   509  				run(t, ctx, config)
   510  
   511  				javac := ctx.ModuleForTests("foo", variant).Rule("javac")
   512  				got := javac.Args["bootClasspath"]
   513  				expected := system
   514  				if testcase.system == "bootclasspath" {
   515  					expected = bc
   516  				}
   517  				if got != expected {
   518  					t.Errorf("bootclasspath expected %q != got %q", expected, got)
   519  				}
   520  			})
   521  		})
   522  	}
   523  
   524  }
   525  
   526  func TestPrebuilts(t *testing.T) {
   527  	ctx := testJava(t, `
   528  		java_library {
   529  			name: "foo",
   530  			srcs: ["a.java"],
   531  			libs: ["bar"],
   532  			static_libs: ["baz"],
   533  		}
   534  
   535  		java_import {
   536  			name: "bar",
   537  			jars: ["a.jar"],
   538  		}
   539  
   540  		java_import {
   541  			name: "baz",
   542  			jars: ["b.jar"],
   543  		}
   544  		`)
   545  
   546  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   547  	combineJar := ctx.ModuleForTests("foo", "android_common").Description("for javac")
   548  
   549  	bar := "a.jar"
   550  	if !strings.Contains(javac.Args["classpath"], bar) {
   551  		t.Errorf("foo classpath %v does not contain %q", javac.Args["classpath"], bar)
   552  	}
   553  
   554  	if len(combineJar.Inputs) != 2 || combineJar.Inputs[1].String() != "b.jar" {
   555  		t.Errorf("foo combineJar inputs %v does not contain %q", combineJar.Inputs, "b.jar")
   556  	}
   557  }
   558  
   559  func TestDefaults(t *testing.T) {
   560  	ctx := testJava(t, `
   561  		java_defaults {
   562  			name: "defaults",
   563  			srcs: ["a.java"],
   564  			libs: ["bar"],
   565  			static_libs: ["baz"],
   566  		}
   567  
   568  		java_library {
   569  			name: "foo",
   570  			defaults: ["defaults"],
   571  		}
   572  
   573  		java_library {
   574  			name: "bar",
   575  			srcs: ["b.java"],
   576  		}
   577  
   578  		java_library {
   579  			name: "baz",
   580  			srcs: ["c.java"],
   581  		}
   582  		`)
   583  
   584  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   585  	combineJar := ctx.ModuleForTests("foo", "android_common").Description("for javac")
   586  
   587  	if len(javac.Inputs) != 1 || javac.Inputs[0].String() != "a.java" {
   588  		t.Errorf(`foo inputs %v != ["a.java"]`, javac.Inputs)
   589  	}
   590  
   591  	barTurbine := filepath.Join(buildDir, ".intermediates", "bar", "android_common", "turbine-combined", "bar.jar")
   592  	if !strings.Contains(javac.Args["classpath"], barTurbine) {
   593  		t.Errorf("foo classpath %v does not contain %q", javac.Args["classpath"], barTurbine)
   594  	}
   595  
   596  	baz := ctx.ModuleForTests("baz", "android_common").Rule("javac").Output.String()
   597  	if len(combineJar.Inputs) != 2 || combineJar.Inputs[1].String() != baz {
   598  		t.Errorf("foo combineJar inputs %v does not contain %q", combineJar.Inputs, baz)
   599  	}
   600  }
   601  
   602  func TestResources(t *testing.T) {
   603  	var table = []struct {
   604  		name  string
   605  		prop  string
   606  		extra string
   607  		args  string
   608  	}{
   609  		{
   610  			// Test that a module with java_resource_dirs includes the files
   611  			name: "resource dirs",
   612  			prop: `java_resource_dirs: ["java-res"]`,
   613  			args: "-C java-res -f java-res/a -f java-res/b",
   614  		},
   615  		{
   616  			// Test that a module with java_resources includes the files
   617  			name: "resource files",
   618  			prop: `java_resources: ["java-res/a", "java-res/b"]`,
   619  			args: "-C . -f java-res/a -f java-res/b",
   620  		},
   621  		{
   622  			// Test that a module with a filegroup in java_resources includes the files with the
   623  			// path prefix
   624  			name: "resource filegroup",
   625  			prop: `java_resources: [":foo-res"]`,
   626  			extra: `
   627  				filegroup {
   628  					name: "foo-res",
   629  					path: "java-res",
   630  					srcs: ["java-res/a", "java-res/b"],
   631  				}`,
   632  			args: "-C java-res -f java-res/a -f java-res/b",
   633  		},
   634  		{
   635  			// Test that a module with "include_srcs: true" includes its source files in the resources jar
   636  			name: "include sources",
   637  			prop: `include_srcs: true`,
   638  			args: "-C . -f a.java -f b.java -f c.java",
   639  		},
   640  	}
   641  
   642  	for _, test := range table {
   643  		t.Run(test.name, func(t *testing.T) {
   644  			ctx := testJava(t, `
   645  				java_library {
   646  					name: "foo",
   647  					srcs: [
   648  						"a.java",
   649  						"b.java",
   650  						"c.java",
   651  					],
   652  					`+test.prop+`,
   653  				}
   654  			`+test.extra)
   655  
   656  			foo := ctx.ModuleForTests("foo", "android_common").Output("combined/foo.jar")
   657  			fooRes := ctx.ModuleForTests("foo", "android_common").Output("res/foo.jar")
   658  
   659  			if !inList(fooRes.Output.String(), foo.Inputs.Strings()) {
   660  				t.Errorf("foo combined jars %v does not contain %q",
   661  					foo.Inputs.Strings(), fooRes.Output.String())
   662  			}
   663  
   664  			if fooRes.Args["jarArgs"] != test.args {
   665  				t.Errorf("foo resource jar args %q is not %q",
   666  					fooRes.Args["jarArgs"], test.args)
   667  			}
   668  		})
   669  	}
   670  }
   671  
   672  func TestExcludeResources(t *testing.T) {
   673  	ctx := testJava(t, `
   674  		java_library {
   675  			name: "foo",
   676  			srcs: ["a.java"],
   677  			java_resource_dirs: ["java-res", "java-res2"],
   678  			exclude_java_resource_dirs: ["java-res2"],
   679  		}
   680  
   681  		java_library {
   682  			name: "bar",
   683  			srcs: ["a.java"],
   684  			java_resources: ["java-res/*"],
   685  			exclude_java_resources: ["java-res/b"],
   686  		}
   687  	`)
   688  
   689  	fooRes := ctx.ModuleForTests("foo", "android_common").Output("res/foo.jar")
   690  
   691  	expected := "-C java-res -f java-res/a -f java-res/b"
   692  	if fooRes.Args["jarArgs"] != expected {
   693  		t.Errorf("foo resource jar args %q is not %q",
   694  			fooRes.Args["jarArgs"], expected)
   695  
   696  	}
   697  
   698  	barRes := ctx.ModuleForTests("bar", "android_common").Output("res/bar.jar")
   699  
   700  	expected = "-C . -f java-res/a"
   701  	if barRes.Args["jarArgs"] != expected {
   702  		t.Errorf("bar resource jar args %q is not %q",
   703  			barRes.Args["jarArgs"], expected)
   704  
   705  	}
   706  }
   707  
   708  func TestGeneratedSources(t *testing.T) {
   709  	ctx := testJava(t, `
   710  		java_library {
   711  			name: "foo",
   712  			srcs: [
   713  				"a*.java",
   714  				":gen",
   715  				"b*.java",
   716  			],
   717  		}
   718  
   719  		genrule {
   720  			name: "gen",
   721  			tool_files: ["java-res/a"],
   722  			out: ["gen.java"],
   723  		}
   724  	`)
   725  
   726  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   727  	genrule := ctx.ModuleForTests("gen", "").Rule("generator")
   728  
   729  	if filepath.Base(genrule.Output.String()) != "gen.java" {
   730  		t.Fatalf(`gen output file %v is not ".../gen.java"`, genrule.Output.String())
   731  	}
   732  
   733  	if len(javac.Inputs) != 3 ||
   734  		javac.Inputs[0].String() != "a.java" ||
   735  		javac.Inputs[1].String() != genrule.Output.String() ||
   736  		javac.Inputs[2].String() != "b.java" {
   737  		t.Errorf(`foo inputs %v != ["a.java", ".../gen.java", "b.java"]`, javac.Inputs)
   738  	}
   739  }
   740  
   741  func TestKotlin(t *testing.T) {
   742  	ctx := testJava(t, `
   743  		java_library {
   744  			name: "foo",
   745  			srcs: ["a.java", "b.kt"],
   746  		}
   747  
   748  		java_library {
   749  			name: "bar",
   750  			srcs: ["b.kt"],
   751  			libs: ["foo"],
   752  			static_libs: ["baz"],
   753  		}
   754  
   755  		java_library {
   756  			name: "baz",
   757  			srcs: ["c.java"],
   758  		}
   759  		`)
   760  
   761  	fooKotlinc := ctx.ModuleForTests("foo", "android_common").Rule("kotlinc")
   762  	fooJavac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   763  	fooJar := ctx.ModuleForTests("foo", "android_common").Output("combined/foo.jar")
   764  
   765  	if len(fooKotlinc.Inputs) != 2 || fooKotlinc.Inputs[0].String() != "a.java" ||
   766  		fooKotlinc.Inputs[1].String() != "b.kt" {
   767  		t.Errorf(`foo kotlinc inputs %v != ["a.java", "b.kt"]`, fooKotlinc.Inputs)
   768  	}
   769  
   770  	if len(fooJavac.Inputs) != 1 || fooJavac.Inputs[0].String() != "a.java" {
   771  		t.Errorf(`foo inputs %v != ["a.java"]`, fooJavac.Inputs)
   772  	}
   773  
   774  	if !strings.Contains(fooJavac.Args["classpath"], fooKotlinc.Output.String()) {
   775  		t.Errorf("foo classpath %v does not contain %q",
   776  			fooJavac.Args["classpath"], fooKotlinc.Output.String())
   777  	}
   778  
   779  	if !inList(fooKotlinc.Output.String(), fooJar.Inputs.Strings()) {
   780  		t.Errorf("foo jar inputs %v does not contain %q",
   781  			fooJar.Inputs.Strings(), fooKotlinc.Output.String())
   782  	}
   783  
   784  	fooHeaderJar := ctx.ModuleForTests("foo", "android_common").Output("turbine-combined/foo.jar")
   785  	bazHeaderJar := ctx.ModuleForTests("baz", "android_common").Output("turbine-combined/baz.jar")
   786  	barKotlinc := ctx.ModuleForTests("bar", "android_common").Rule("kotlinc")
   787  
   788  	if len(barKotlinc.Inputs) != 1 || barKotlinc.Inputs[0].String() != "b.kt" {
   789  		t.Errorf(`bar kotlinc inputs %v != ["b.kt"]`, barKotlinc.Inputs)
   790  	}
   791  
   792  	if !inList(fooHeaderJar.Output.String(), barKotlinc.Implicits.Strings()) {
   793  		t.Errorf(`expected %q in bar implicits %v`,
   794  			fooHeaderJar.Output.String(), barKotlinc.Implicits.Strings())
   795  	}
   796  
   797  	if !inList(bazHeaderJar.Output.String(), barKotlinc.Implicits.Strings()) {
   798  		t.Errorf(`expected %q in bar implicits %v`,
   799  			bazHeaderJar.Output.String(), barKotlinc.Implicits.Strings())
   800  	}
   801  }
   802  
   803  func TestTurbine(t *testing.T) {
   804  	ctx := testJava(t, `
   805  		java_library {
   806  			name: "foo",
   807  			srcs: ["a.java"],
   808  		}
   809  
   810  		java_library {
   811  			name: "bar",
   812  			srcs: ["b.java"],
   813  			static_libs: ["foo"],
   814  		}
   815  
   816  		java_library {
   817  			name: "baz",
   818  			srcs: ["c.java"],
   819  			libs: ["bar"],
   820  			sdk_version: "14",
   821  		}
   822  		`)
   823  
   824  	fooTurbine := ctx.ModuleForTests("foo", "android_common").Rule("turbine")
   825  	barTurbine := ctx.ModuleForTests("bar", "android_common").Rule("turbine")
   826  	barJavac := ctx.ModuleForTests("bar", "android_common").Rule("javac")
   827  	barTurbineCombined := ctx.ModuleForTests("bar", "android_common").Description("for turbine")
   828  	bazJavac := ctx.ModuleForTests("baz", "android_common").Rule("javac")
   829  
   830  	if len(fooTurbine.Inputs) != 1 || fooTurbine.Inputs[0].String() != "a.java" {
   831  		t.Errorf(`foo inputs %v != ["a.java"]`, fooTurbine.Inputs)
   832  	}
   833  
   834  	fooHeaderJar := filepath.Join(buildDir, ".intermediates", "foo", "android_common", "turbine-combined", "foo.jar")
   835  	if !strings.Contains(barTurbine.Args["classpath"], fooHeaderJar) {
   836  		t.Errorf("bar turbine classpath %v does not contain %q", barTurbine.Args["classpath"], fooHeaderJar)
   837  	}
   838  	if !strings.Contains(barJavac.Args["classpath"], fooHeaderJar) {
   839  		t.Errorf("bar javac classpath %v does not contain %q", barJavac.Args["classpath"], fooHeaderJar)
   840  	}
   841  	if len(barTurbineCombined.Inputs) != 2 || barTurbineCombined.Inputs[1].String() != fooHeaderJar {
   842  		t.Errorf("bar turbine combineJar inputs %v does not contain %q", barTurbineCombined.Inputs, fooHeaderJar)
   843  	}
   844  	if !strings.Contains(bazJavac.Args["classpath"], "prebuilts/sdk/14/android.jar") {
   845  		t.Errorf("baz javac classpath %v does not contain %q", bazJavac.Args["classpath"],
   846  			"prebuilts/sdk/14/android.jar")
   847  	}
   848  }
   849  
   850  func TestSharding(t *testing.T) {
   851  	ctx := testJava(t, `
   852  		java_library {
   853  			name: "bar",
   854  			srcs: ["a.java","b.java","c.java"],
   855  			javac_shard_size: 1
   856  		}
   857  		`)
   858  
   859  	barHeaderJar := filepath.Join(buildDir, ".intermediates", "bar", "android_common", "turbine-combined", "bar.jar")
   860  	for i := 0; i < 3; i++ {
   861  		barJavac := ctx.ModuleForTests("bar", "android_common").Description("javac" + strconv.Itoa(i))
   862  		if !strings.Contains(barJavac.Args["classpath"], barHeaderJar) {
   863  			t.Errorf("bar javac classpath %v does not contain %q", barJavac.Args["classpath"], barHeaderJar)
   864  		}
   865  	}
   866  }
   867  
   868  func TestDroiddoc(t *testing.T) {
   869  	ctx := testJava(t, `
   870  		droiddoc_template {
   871  		    name: "droiddoc-templates-sdk",
   872  		    path: ".",
   873  		}
   874  		droiddoc {
   875  		    name: "bar-doc",
   876  		    srcs: [
   877  		        "bar-doc/*.java",
   878  		    ],
   879  		    exclude_srcs: [
   880  		        "bar-doc/b.java"
   881  		    ],
   882  		    custom_template: "droiddoc-templates-sdk",
   883  		    hdf: [
   884  		        "android.whichdoc offline",
   885  		    ],
   886  		    knowntags: [
   887  		        "bar-doc/known_oj_tags.txt",
   888  		    ],
   889  		    proofread_file: "libcore-proofread.txt",
   890  		    todo_file: "libcore-docs-todo.html",
   891  		    args: "-offlinemode -title \"libcore\"",
   892  		}
   893  		`)
   894  
   895  	stubsJar := filepath.Join(buildDir, ".intermediates", "bar-doc", "android_common", "bar-doc-stubs.srcjar")
   896  	barDoc := ctx.ModuleForTests("bar-doc", "android_common").Output("bar-doc-stubs.srcjar")
   897  	if stubsJar != barDoc.Output.String() {
   898  		t.Errorf("expected stubs Jar [%q], got %q", stubsJar, barDoc.Output.String())
   899  	}
   900  }
   901  
   902  func TestJarGenrules(t *testing.T) {
   903  	ctx := testJava(t, `
   904  		java_library {
   905  			name: "foo",
   906  			srcs: ["a.java"],
   907  		}
   908  
   909  		java_genrule {
   910  			name: "jargen",
   911  			tool_files: ["b.java"],
   912  			cmd: "$(location b.java) $(in) $(out)",
   913  			out: ["jargen.jar"],
   914  			srcs: [":foo"],
   915  		}
   916  
   917  		java_library {
   918  			name: "bar",
   919  			static_libs: ["jargen"],
   920  			srcs: ["c.java"],
   921  		}
   922  
   923  		java_library {
   924  			name: "baz",
   925  			libs: ["jargen"],
   926  			srcs: ["c.java"],
   927  		}
   928  	`)
   929  
   930  	foo := ctx.ModuleForTests("foo", "android_common").Output("javac/foo.jar")
   931  	jargen := ctx.ModuleForTests("jargen", "android_common").Output("jargen.jar")
   932  	bar := ctx.ModuleForTests("bar", "android_common").Output("javac/bar.jar")
   933  	baz := ctx.ModuleForTests("baz", "android_common").Output("javac/baz.jar")
   934  	barCombined := ctx.ModuleForTests("bar", "android_common").Output("combined/bar.jar")
   935  
   936  	if len(jargen.Inputs) != 1 || jargen.Inputs[0].String() != foo.Output.String() {
   937  		t.Errorf("expected jargen inputs [%q], got %q", foo.Output.String(), jargen.Inputs.Strings())
   938  	}
   939  
   940  	if !strings.Contains(bar.Args["classpath"], jargen.Output.String()) {
   941  		t.Errorf("bar classpath %v does not contain %q", bar.Args["classpath"], jargen.Output.String())
   942  	}
   943  
   944  	if !strings.Contains(baz.Args["classpath"], jargen.Output.String()) {
   945  		t.Errorf("baz classpath %v does not contain %q", baz.Args["classpath"], jargen.Output.String())
   946  	}
   947  
   948  	if len(barCombined.Inputs) != 2 ||
   949  		barCombined.Inputs[0].String() != bar.Output.String() ||
   950  		barCombined.Inputs[1].String() != jargen.Output.String() {
   951  		t.Errorf("bar combined jar inputs %v is not [%q, %q]",
   952  			barCombined.Inputs.Strings(), bar.Output.String(), jargen.Output.String())
   953  	}
   954  }
   955  
   956  func TestExcludeFileGroupInSrcs(t *testing.T) {
   957  	ctx := testJava(t, `
   958  		java_library {
   959  			name: "foo",
   960  			srcs: ["a.java", ":foo-srcs"],
   961  			exclude_srcs: ["a.java", ":foo-excludes"],
   962  		}
   963  
   964  		filegroup {
   965  			name: "foo-srcs",
   966  			srcs: ["java-fg/a.java", "java-fg/b.java", "java-fg/c.java"],
   967  		}
   968  
   969  		filegroup {
   970  			name: "foo-excludes",
   971  			srcs: ["java-fg/a.java", "java-fg/b.java"],
   972  		}
   973  	`)
   974  
   975  	javac := ctx.ModuleForTests("foo", "android_common").Rule("javac")
   976  
   977  	if len(javac.Inputs) != 1 || javac.Inputs[0].String() != "java-fg/c.java" {
   978  		t.Errorf(`foo inputs %v != ["java-fg/c.java"]`, javac.Inputs)
   979  	}
   980  }