Merge "Check in BUILD files in prebuilts/rust and external/bazelbuild-rules_rust" into main
diff --git a/aconfig/aconfig_declarations.go b/aconfig/aconfig_declarations.go
index d1d1578..4e199dd 100644
--- a/aconfig/aconfig_declarations.go
+++ b/aconfig/aconfig_declarations.go
@@ -97,6 +97,15 @@
 	return sb.String()
 }
 
+func optionalVariable(prefix string, value string) string {
+	var sb strings.Builder
+	if value != "" {
+		sb.WriteString(prefix)
+		sb.WriteString(value)
+	}
+	return sb.String()
+}
+
 // Provider published by aconfig_value_set
 type declarationsProviderData struct {
 	Package          string
@@ -124,15 +133,17 @@
 	// Intermediate format
 	inputFiles := android.PathsForModuleSrc(ctx, module.properties.Srcs)
 	intermediatePath := android.PathForModuleOut(ctx, "intermediate.pb")
+	defaultPermission := ctx.Config().ReleaseAconfigFlagDefaultPermission()
 	ctx.Build(pctx, android.BuildParams{
 		Rule:        aconfigRule,
 		Output:      intermediatePath,
 		Description: "aconfig_declarations",
 		Args: map[string]string{
-			"release_version": ctx.Config().ReleaseVersion(),
-			"package":         module.properties.Package,
-			"declarations":    android.JoinPathsWithPrefix(inputFiles, "--declarations "),
-			"values":          joinAndPrefix(" --values ", module.properties.Values),
+			"release_version":    ctx.Config().ReleaseVersion(),
+			"package":            module.properties.Package,
+			"declarations":       android.JoinPathsWithPrefix(inputFiles, "--declarations "),
+			"values":             joinAndPrefix(" --values ", module.properties.Values),
+			"default-permission": optionalVariable(" --default-permission ", defaultPermission),
 		},
 	})
 
diff --git a/aconfig/init.go b/aconfig/init.go
index cfbd79d..797388d 100644
--- a/aconfig/init.go
+++ b/aconfig/init.go
@@ -30,6 +30,7 @@
 				` --package ${package}` +
 				` ${declarations}` +
 				` ${values}` +
+				` ${default-permission}` +
 				` --cache ${out}.tmp` +
 				` && ( if cmp -s ${out}.tmp ${out} ; then rm ${out}.tmp ; else mv ${out}.tmp ${out} ; fi )`,
 			//				` --build-id ${release_version}` +
@@ -37,7 +38,7 @@
 				"${aconfig}",
 			},
 			Restat: true,
-		}, "release_version", "package", "declarations", "values")
+		}, "release_version", "package", "declarations", "values", "default-permission")
 
 	// For java_aconfig_library: Generate java file
 	javaRule = pctx.AndroidStaticRule("java_aconfig_library",
diff --git a/android/config.go b/android/config.go
index 5c8b20b..3e7bb14 100644
--- a/android/config.go
+++ b/android/config.go
@@ -206,6 +206,12 @@
 	return c.config.productVariables.ReleaseAconfigValueSets
 }
 
+// The flag default permission value passed to aconfig
+// derived from RELEASE_ACONFIG_FLAG_DEFAULT_PERMISSION
+func (c Config) ReleaseAconfigFlagDefaultPermission() string {
+	return c.config.productVariables.ReleaseAconfigFlagDefaultPermission
+}
+
 // A DeviceConfig object represents the configuration for a particular device
 // being built. For now there will only be one of these, but in the future there
 // may be multiple devices being built.
diff --git a/android/variable.go b/android/variable.go
index 664ead7..bae2adc 100644
--- a/android/variable.go
+++ b/android/variable.go
@@ -482,6 +482,8 @@
 	ReleaseVersion          string   `json:",omitempty"`
 	ReleaseAconfigValueSets []string `json:",omitempty"`
 
+	ReleaseAconfigFlagDefaultPermission string `json:",omitempty"`
+
 	KeepVndk *bool `json:",omitempty"`
 }
 
diff --git a/cc/config/global.go b/cc/config/global.go
index e547c3f..ff5ab05 100644
--- a/cc/config/global.go
+++ b/cc/config/global.go
@@ -68,6 +68,10 @@
 		// not emit the table by default on Android since NDK still uses GNU binutils.
 		"-faddrsig",
 
+		// Turn on -fcommon explicitly, since Clang now defaults to -fno-common. The cleanup bug
+		// tracking this is http://b/151457797.
+		"-fcommon",
+
 		// Help catch common 32/64-bit errors.
 		"-Werror=int-conversion",
 
diff --git a/cc/orderfile.go b/cc/orderfile.go
index cc1ab29..b64c1c7 100644
--- a/cc/orderfile.go
+++ b/cc/orderfile.go
@@ -121,9 +121,9 @@
 }
 
 func (props *OrderfileProperties) addInstrumentationProfileGatherFlags(ctx ModuleContext, flags Flags) Flags {
-	flags.Local.CFlags = append(flags.Local.CFlags, props.Orderfile.Cflags...)
 	flags.Local.CFlags = append(flags.Local.CFlags, orderfileProfileFlag)
 	flags.Local.CFlags = append(flags.Local.CFlags, "-mllvm -enable-order-file-instrumentation")
+	flags.Local.CFlags = append(flags.Local.CFlags, props.Orderfile.Cflags...)
 	flags.Local.LdFlags = append(flags.Local.LdFlags, orderfileProfileFlag)
 	return flags
 }
@@ -140,7 +140,6 @@
 	orderFilePath := orderFile.Path()
 	loadFlags := props.loadOrderfileFlags(ctx, orderFilePath.String())
 
-	flags.Local.CFlags = append(flags.Local.CFlags, loadFlags...)
 	flags.Local.LdFlags = append(flags.Local.LdFlags, loadFlags...)
 
 	// Update CFlagsDeps and LdFlagsDeps so the module is rebuilt
diff --git a/cc/orderfile_test.go b/cc/orderfile_test.go
index 9e30bd2..f68457d 100644
--- a/cc/orderfile_test.go
+++ b/cc/orderfile_test.go
@@ -79,12 +79,6 @@
 
 	libTest := result.ModuleForTests("libTest", "android_arm64_armv8-a_shared")
 
-	// Check cFlags of orderfile-enabled module
-	cFlags := libTest.Rule("cc").Args["cFlags"]
-	if !strings.Contains(cFlags, expectedCFlag) {
-		t.Errorf("Expected 'libTest' to load orderfile, but did not find %q in cflags %q", expectedCFlag, cFlags)
-	}
-
 	// Check ldFlags of orderfile-enabled module
 	ldFlags := libTest.Rule("ld").Args["ldFlags"]
 	if !strings.Contains(ldFlags, expectedCFlag) {
@@ -150,12 +144,6 @@
 
 	test := result.ModuleForTests("test", "android_arm64_armv8-a")
 
-	// Check cFlags of orderfile-enabled module
-	cFlags := test.Rule("cc").Args["cFlags"]
-	if !strings.Contains(cFlags, expectedCFlag) {
-		t.Errorf("Expected 'test' to load orderfile, but did not find %q in cflags %q", expectedCFlag, cFlags)
-	}
-
 	// Check ldFlags of orderfile-enabled module
 	ldFlags := test.Rule("ld").Args["ldFlags"]
 	if !strings.Contains(ldFlags, expectedCFlag) {
@@ -285,28 +273,17 @@
 
 	expectedCFlag := "-Wl,--symbol-ordering-file=toolchain/pgo-profiles/orderfiles/test.orderfile"
 
-	// Check cFlags of orderfile-enabled module
+	// Check ldFlags of orderfile-enabled module
 	libTest := result.ModuleForTests("libTest", "android_arm64_armv8-a_shared")
 
-	cFlags := libTest.Rule("cc").Args["cFlags"]
-	if !strings.Contains(cFlags, expectedCFlag) {
-		t.Errorf("Expected 'libTest' to load orderfile, but did not find %q in cflags %q", expectedCFlag, cFlags)
+	ldFlags := libTest.Rule("ld").Args["ldFlags"]
+	if !strings.Contains(ldFlags, expectedCFlag) {
+		t.Errorf("Expected 'libTest' to load orderfile, but did not find %q in ldFlags %q", expectedCFlag, ldFlags)
 	}
 
-	// Check cFlags of the non-orderfile variant static libraries
 	libFoo  := result.ModuleForTests("libFoo", "android_arm64_armv8-a_static")
 	libBar  := result.ModuleForTests("libBar", "android_arm64_armv8-a_static")
 
-	cFlags = libFoo.Rule("cc").Args["cFlags"]
-	if strings.Contains(cFlags, expectedCFlag) {
-		t.Errorf("Expected 'libFoo' not load orderfile, but did find %q in cflags %q", expectedCFlag, cFlags)
-	}
-
-	cFlags = libBar.Rule("cc").Args["cFlags"]
-	if strings.Contains(cFlags, expectedCFlag) {
-		t.Errorf("Expected 'libBar' not load orderfile, but did find %q in cflags %q", expectedCFlag, cFlags)
-	}
-
 	// Check dependency edge from orderfile-enabled module to non-orderfile variant static libraries
 	if !hasDirectDep(result, libTest.Module(), libFoo.Module()) {
 		t.Errorf("libTest missing dependency on non-orderfile variant of libFoo")
diff --git a/java/droidstubs.go b/java/droidstubs.go
index 51d36e4..f05ef1f 100644
--- a/java/droidstubs.go
+++ b/java/droidstubs.go
@@ -694,6 +694,13 @@
 		cmd.FlagWithArg("--error-message:compatibility:released ", msg)
 	}
 
+	if apiCheckEnabled(ctx, d.properties.Check_api.Current, "current") {
+		// Pass the current API file into metalava so it can use it as the basis for determining how to
+		// generate the output signature files (both api and removed).
+		currentApiFile := android.PathForModuleSrc(ctx, String(d.properties.Check_api.Current.Api_file))
+		cmd.FlagWithInput("--use-same-format-as ", currentApiFile)
+	}
+
 	if generateStubs {
 		rule.Command().
 			BuiltTool("soong_zip").
diff --git a/java/java.go b/java/java.go
index 0d39a6a..6667a52 100644
--- a/java/java.go
+++ b/java/java.go
@@ -1812,6 +1812,28 @@
 	}
 }
 
+// API signature file names sorted from
+// the narrowest api scope to the widest api scope
+var scopeOrderedSourceFileNames = allApiScopes.Strings(
+	func(s *apiScope) string { return s.apiFilePrefix + "current.txt" })
+
+func (al *ApiLibrary) sortApiFilesByApiScope(ctx android.ModuleContext, srcFiles android.Paths) android.Paths {
+	sortedSrcFiles := android.Paths{}
+
+	for _, scopeSourceFileName := range scopeOrderedSourceFileNames {
+		for _, sourceFileName := range srcFiles {
+			if sourceFileName.Base() == scopeSourceFileName {
+				sortedSrcFiles = append(sortedSrcFiles, sourceFileName)
+			}
+		}
+	}
+	if len(srcFiles) != len(sortedSrcFiles) {
+		ctx.ModuleErrorf("Unrecognizable source file found within %s", srcFiles)
+	}
+
+	return sortedSrcFiles
+}
+
 func (al *ApiLibrary) GenerateAndroidBuildActions(ctx android.ModuleContext) {
 
 	rule := android.NewRuleBuilder(pctx, ctx)
@@ -1862,6 +1884,8 @@
 		ctx.ModuleErrorf("Error: %s has an empty api file.", ctx.ModuleName())
 	}
 
+	srcFiles = al.sortApiFilesByApiScope(ctx, srcFiles)
+
 	cmd := metalavaStubCmd(ctx, rule, srcFiles, homeDir)
 
 	al.stubsFlags(ctx, cmd, stubsDir)
diff --git a/java/java_test.go b/java/java_test.go
index dd98677..6110e21 100644
--- a/java/java_test.go
+++ b/java/java_test.go
@@ -1864,12 +1864,12 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	ctx, _ := testJavaWithFS(t, `
@@ -1897,11 +1897,11 @@
 	}{
 		{
 			moduleName:         "bar1",
-			sourceTextFileDirs: []string{"a/foo1.txt"},
+			sourceTextFileDirs: []string{"a/current.txt"},
 		},
 		{
 			moduleName:         "bar2",
-			sourceTextFileDirs: []string{"a/foo1.txt", "b/foo2.txt", "api1/current.txt", "api2/current.txt"},
+			sourceTextFileDirs: []string{"a/current.txt", "b/current.txt", "api1/current.txt", "api2/current.txt"},
 		},
 	}
 	for _, c := range testcases {
@@ -1918,25 +1918,25 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `
 	java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_c := `
 	java_api_contribution {
 		name: "foo3",
-		api_file: "foo3.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_d := `
 	java_api_contribution {
 		name: "foo4",
-		api_file: "foo4.txt",
+		api_file: "current.txt",
 	}
 	`
 	ctx, _ := testJavaWithFS(t, `
@@ -1985,15 +1985,15 @@
 	}{
 		{
 			moduleName:         "bar1",
-			sourceTextFileDirs: []string{"a/foo1.txt"},
+			sourceTextFileDirs: []string{"a/current.txt"},
 		},
 		{
 			moduleName:         "bar2",
-			sourceTextFileDirs: []string{"a/foo1.txt", "b/foo2.txt"},
+			sourceTextFileDirs: []string{"a/current.txt", "b/current.txt"},
 		},
 		{
 			moduleName:         "bar3",
-			sourceTextFileDirs: []string{"c/foo3.txt", "a/foo1.txt", "b/foo2.txt", "d/foo4.txt", "api1/current.txt", "api2/current.txt"},
+			sourceTextFileDirs: []string{"c/current.txt", "a/current.txt", "b/current.txt", "d/current.txt", "api1/current.txt", "api2/current.txt"},
 		},
 	}
 	for _, c := range testcases {
@@ -2010,13 +2010,13 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `
 	java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	ctx, _ := testJavaWithFS(t, `
@@ -2063,13 +2063,13 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `
 	java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	lib_bp_a := `
@@ -2138,13 +2138,13 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `
 	java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	lib_bp_a := `
@@ -2212,13 +2212,13 @@
 	provider_bp_a := `
 	java_api_contribution {
 		name: "foo1",
-		api_file: "foo1.txt",
+		api_file: "current.txt",
 	}
 	`
 	provider_bp_b := `
 	java_api_contribution {
 		name: "foo2",
-		api_file: "foo2.txt",
+		api_file: "current.txt",
 	}
 	`
 	lib_bp_a := `
diff --git a/rust/builder.go b/rust/builder.go
index fbceecc..b1f049d 100644
--- a/rust/builder.go
+++ b/rust/builder.go
@@ -45,9 +45,9 @@
 		"rustcFlags", "libFlags", "envVars")
 	rustLink = pctx.AndroidStaticRule("rustLink",
 		blueprint.RuleParams{
-			Command: "${config.RustLinker} -o $out ${crtBegin} ${config.RustLinkerArgs} @$in ${linkFlags} ${crtEnd}",
+			Command: "${config.RustLinker} -o $out ${crtBegin} ${earlyLinkFlags} @$in ${linkFlags} ${crtEnd}",
 		},
-		"linkFlags", "crtBegin", "crtEnd")
+		"earlyLinkFlags", "linkFlags", "crtBegin", "crtEnd")
 
 	_       = pctx.SourcePathVariable("rustdocCmd", "${config.RustBin}/rustdoc")
 	rustdoc = pctx.AndroidStaticRule("rustdoc",
@@ -244,6 +244,10 @@
 
 	envVars = append(envVars, "AR=${cc_config.ClangBin}/llvm-ar")
 
+	if ctx.Darwin() {
+		envVars = append(envVars, "ANDROID_RUST_DARWIN=true")
+	}
+
 	return envVars
 }
 
@@ -254,6 +258,7 @@
 	var implicits, linkImplicits, linkOrderOnly android.Paths
 	var output buildOutput
 	var rustcFlags, linkFlags []string
+	var earlyLinkFlags string
 
 	output.outputFile = outputFile
 	crateName := ctx.RustModule().CrateName()
@@ -292,6 +297,10 @@
 	}
 
 	// Collect linker flags
+	if !ctx.Darwin() {
+		earlyLinkFlags = "-Wl,--as-needed"
+	}
+
 	linkFlags = append(linkFlags, flags.GlobalLinkFlags...)
 	linkFlags = append(linkFlags, flags.LinkFlags...)
 
@@ -391,9 +400,10 @@
 			Implicits:   linkImplicits,
 			OrderOnly:   linkOrderOnly,
 			Args: map[string]string{
-				"linkFlags": strings.Join(linkFlags, " "),
-				"crtBegin":  strings.Join(deps.CrtBegin.Strings(), " "),
-				"crtEnd":    strings.Join(deps.CrtEnd.Strings(), " "),
+				"earlyLinkFlags": earlyLinkFlags,
+				"linkFlags":      strings.Join(linkFlags, " "),
+				"crtBegin":       strings.Join(deps.CrtBegin.Strings(), " "),
+				"crtEnd":         strings.Join(deps.CrtEnd.Strings(), " "),
 			},
 		})
 	}
diff --git a/rust/config/global.go b/rust/config/global.go
index c39341e..86eb2d1 100644
--- a/rust/config/global.go
+++ b/rust/config/global.go
@@ -102,7 +102,6 @@
 
 	pctx.ImportAs("cc_config", "android/soong/cc/config")
 	pctx.StaticVariable("RustLinker", "${cc_config.ClangBin}/clang++")
-	pctx.StaticVariable("RustLinkerArgs", "-Wl,--as-needed")
 
 	pctx.StaticVariable("DeviceGlobalLinkFlags", strings.Join(deviceGlobalLinkFlags, " "))
 
diff --git a/scripts/mkcratersp.py b/scripts/mkcratersp.py
index 86b4aa3..6ef01eb 100755
--- a/scripts/mkcratersp.py
+++ b/scripts/mkcratersp.py
@@ -48,6 +48,8 @@
     linkdirs.append(sys.argv[i+1])
   if arg.startswith('-l') or arg == '-shared':
     libs.append(arg)
+  if os.getenv('ANDROID_RUST_DARWIN') and (arg == '-dylib' or arg == '-dynamiclib'):
+    libs.append(arg)
   if arg.startswith('-Wl,--version-script='):
     version_script = arg[21:]
   if arg[0] == '-':
@@ -64,9 +66,13 @@
 create_archive(f'{out}.a', [], temp_archives)
 
 with open(out, 'w') as f:
-  print(f'-Wl,--whole-archive', file=f)
-  print(f'{out}.whole.a', file=f)
-  print(f'-Wl,--no-whole-archive', file=f)
+  if os.getenv("ANDROID_RUST_DARWIN"):
+    print(f'-force_load', file=f)
+    print(f'{out}.whole.a', file=f)
+  else:
+    print(f'-Wl,--whole-archive', file=f)
+    print(f'{out}.whole.a', file=f)
+    print(f'-Wl,--no-whole-archive', file=f)
   print(f'{out}.a', file=f)
   for a in archives:
     print(a, file=f)
diff --git a/tests/sbom_test.sh b/tests/sbom_test.sh
index 681617a..c41f28d 100755
--- a/tests/sbom_test.sh
+++ b/tests/sbom_test.sh
@@ -88,24 +88,14 @@
   diff_excludes[vendor]="\
     -I /vendor/lib64/libkeystore2_crypto.so"
   diff_excludes[system]="\
-    -I /bin \
-    -I /bugreports \
-    -I /cache \
-    -I /d \
-    -I /etc \
-    -I /init \
-    -I /odm/app \
-    -I /odm/bin \
-    -I /odm_dlkm/etc \
-    -I /odm/etc \
-    -I /odm/firmware \
-    -I /odm/framework \
-    -I /odm/lib \
-    -I /odm/lib64 \
-    -I /odm/overlay \
-    -I /odm/priv-app \
-    -I /odm/usr \
-    -I /sdcard \
+    -I /system/bin/assemble_cvd
+    -I /system/bin/console_forwarder
+    -I /system/bin/kernel_log_monitor
+    -I /system/bin/logcat_receiver
+    -I /system/bin/mkenvimage_slim
+    -I /system/bin/run_cvd
+    -I /system/bin/simg2img
+    -I /system/bin/log_tee
     -I /system/lib64/android.hardware.confirmationui@1.0.so \
     -I /system/lib64/android.hardware.confirmationui-V1-ndk.so \
     -I /system/lib64/android.hardware.keymaster@4.1.so \
@@ -133,8 +123,7 @@
     -I /system/lib64/vndk-sp-29 \
     -I /system/lib/vndk-29 \
     -I /system/lib/vndk-sp-29 \
-    -I /system/usr/icu \
-    -I /vendor_dlkm/etc"
+    -I /system/usr/icu"
 
   # Example output of dump.erofs is as below, and the data used in the test start
   # at line 11. Column 1 is inode id, column 2 is inode type and column 3 is name.