Export provenance metadata for prebuilt APKs and APEXes.

Bug: 217434690
Test: atest --host gen_provenance_metadata_test
Test: m provenance_metadata

Change-Id: I91c184b6e6fe5ccfc3fc65b55b09e7a3da9502a0
diff --git a/java/app_import_test.go b/java/app_import_test.go
index efa52c1..8f6c75f 100644
--- a/java/app_import_test.go
+++ b/java/app_import_test.go
@@ -53,6 +53,11 @@
 	if expected != signingFlag {
 		t.Errorf("Incorrect signing flags, expected: %q, got: %q", expected, signingFlag)
 	}
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_NoDexPreopt(t *testing.T) {
@@ -74,6 +79,12 @@
 		variant.MaybeOutput("dexpreopt/oat/arm64/package.odex").Rule != nil {
 		t.Errorf("dexpreopt shouldn't have run.")
 	}
+
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_Presigned(t *testing.T) {
@@ -102,6 +113,12 @@
 	if variant.MaybeOutput("zip-aligned/foo.apk").Rule == nil {
 		t.Errorf("can't find aligning rule")
 	}
+
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_SigningLineage(t *testing.T) {
@@ -137,6 +154,12 @@
 	if expected != signingFlag {
 		t.Errorf("Incorrect signing flags, expected: %q, got: %q", expected, signingFlag)
 	}
+
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_SigningLineageFilegroup(t *testing.T) {
@@ -163,6 +186,12 @@
 	if expected != signingFlag {
 		t.Errorf("Incorrect signing flags, expected: %q, got: %q", expected, signingFlag)
 	}
+
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_DefaultDevCert(t *testing.T) {
@@ -192,6 +221,12 @@
 	if expected != signingFlag {
 		t.Errorf("Incorrect signing flags, expected: %q, got: %q", expected, signingFlag)
 	}
+
+	rule := variant.Rule("genProvenanceMetaData")
+	android.AssertStringEquals(t, "Invalid input", "prebuilts/apk/app.apk", rule.Inputs[0].String())
+	android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+	android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+	android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", rule.Args["install_path"])
 }
 
 func TestAndroidAppImport_DpiVariants(t *testing.T) {
@@ -214,40 +249,46 @@
 		}
 		`
 	testCases := []struct {
-		name                string
-		aaptPreferredConfig *string
-		aaptPrebuiltDPI     []string
-		expected            string
+		name                                   string
+		aaptPreferredConfig                    *string
+		aaptPrebuiltDPI                        []string
+		expected                               string
+		expectedProvenanceMetaDataArtifactPath string
 	}{
 		{
-			name:                "no preferred",
-			aaptPreferredConfig: nil,
-			aaptPrebuiltDPI:     []string{},
-			expected:            "verify_uses_libraries/apk/app.apk",
+			name:                                   "no preferred",
+			aaptPreferredConfig:                    nil,
+			aaptPrebuiltDPI:                        []string{},
+			expected:                               "verify_uses_libraries/apk/app.apk",
+			expectedProvenanceMetaDataArtifactPath: "prebuilts/apk/app.apk",
 		},
 		{
-			name:                "AAPTPreferredConfig matches",
-			aaptPreferredConfig: proptools.StringPtr("xhdpi"),
-			aaptPrebuiltDPI:     []string{"xxhdpi", "ldpi"},
-			expected:            "verify_uses_libraries/apk/app_xhdpi.apk",
+			name:                                   "AAPTPreferredConfig matches",
+			aaptPreferredConfig:                    proptools.StringPtr("xhdpi"),
+			aaptPrebuiltDPI:                        []string{"xxhdpi", "ldpi"},
+			expected:                               "verify_uses_libraries/apk/app_xhdpi.apk",
+			expectedProvenanceMetaDataArtifactPath: "prebuilts/apk/app_xhdpi.apk",
 		},
 		{
-			name:                "AAPTPrebuiltDPI matches",
-			aaptPreferredConfig: proptools.StringPtr("mdpi"),
-			aaptPrebuiltDPI:     []string{"xxhdpi", "xhdpi"},
-			expected:            "verify_uses_libraries/apk/app_xxhdpi.apk",
+			name:                                   "AAPTPrebuiltDPI matches",
+			aaptPreferredConfig:                    proptools.StringPtr("mdpi"),
+			aaptPrebuiltDPI:                        []string{"xxhdpi", "xhdpi"},
+			expected:                               "verify_uses_libraries/apk/app_xxhdpi.apk",
+			expectedProvenanceMetaDataArtifactPath: "prebuilts/apk/app_xxhdpi.apk",
 		},
 		{
-			name:                "non-first AAPTPrebuiltDPI matches",
-			aaptPreferredConfig: proptools.StringPtr("mdpi"),
-			aaptPrebuiltDPI:     []string{"ldpi", "xhdpi"},
-			expected:            "verify_uses_libraries/apk/app_xhdpi.apk",
+			name:                                   "non-first AAPTPrebuiltDPI matches",
+			aaptPreferredConfig:                    proptools.StringPtr("mdpi"),
+			aaptPrebuiltDPI:                        []string{"ldpi", "xhdpi"},
+			expected:                               "verify_uses_libraries/apk/app_xhdpi.apk",
+			expectedProvenanceMetaDataArtifactPath: "prebuilts/apk/app_xhdpi.apk",
 		},
 		{
-			name:                "no matches",
-			aaptPreferredConfig: proptools.StringPtr("mdpi"),
-			aaptPrebuiltDPI:     []string{"ldpi", "xxxhdpi"},
-			expected:            "verify_uses_libraries/apk/app.apk",
+			name:                                   "no matches",
+			aaptPreferredConfig:                    proptools.StringPtr("mdpi"),
+			aaptPrebuiltDPI:                        []string{"ldpi", "xxxhdpi"},
+			expected:                               "verify_uses_libraries/apk/app.apk",
+			expectedProvenanceMetaDataArtifactPath: "prebuilts/apk/app.apk",
 		},
 	}
 
@@ -270,6 +311,12 @@
 		if strings.HasSuffix(matches[1], test.expected) {
 			t.Errorf("wrong src apk, expected: %q got: %q", test.expected, matches[1])
 		}
+
+		provenanceMetaDataRule := variant.Rule("genProvenanceMetaData")
+		android.AssertStringEquals(t, "Invalid input", test.expectedProvenanceMetaDataArtifactPath, provenanceMetaDataRule.Inputs[0].String())
+		android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", provenanceMetaDataRule.Output.String())
+		android.AssertStringEquals(t, "Invalid args", "foo", provenanceMetaDataRule.Args["module_name"])
+		android.AssertStringEquals(t, "Invalid args", "/system/app/foo/foo.apk", provenanceMetaDataRule.Args["install_path"])
 	}
 }
 
@@ -290,16 +337,25 @@
 		`)
 
 	testCases := []struct {
-		name     string
-		expected string
+		name                 string
+		expected             string
+		onDevice             string
+		expectedArtifactPath string
+		expectedMetaDataPath string
 	}{
 		{
-			name:     "foo",
-			expected: "foo.apk",
+			name:                 "foo",
+			expected:             "foo.apk",
+			onDevice:             "/system/app/foo/foo.apk",
+			expectedArtifactPath: "prebuilts/apk/app.apk",
+			expectedMetaDataPath: "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto",
 		},
 		{
-			name:     "bar",
-			expected: "bar_sample.apk",
+			name:                 "bar",
+			expected:             "bar_sample.apk",
+			onDevice:             "/system/app/bar/bar_sample.apk",
+			expectedArtifactPath: "prebuilts/apk/app.apk",
+			expectedMetaDataPath: "out/soong/.intermediates/provenance_metadata/bar/provenance_metadata.textproto",
 		},
 	}
 
@@ -316,15 +372,23 @@
 			t.Errorf("Incorrect LOCAL_INSTALLED_MODULE_STEM value '%s', expected '%s'",
 				actualValues, expectedValues)
 		}
+		rule := variant.Rule("genProvenanceMetaData")
+		android.AssertStringEquals(t, "Invalid input", test.expectedArtifactPath, rule.Inputs[0].String())
+		android.AssertStringEquals(t, "Invalid output", test.expectedMetaDataPath, rule.Output.String())
+		android.AssertStringEquals(t, "Invalid args", test.name, rule.Args["module_name"])
+		android.AssertStringEquals(t, "Invalid args", test.onDevice, rule.Args["install_path"])
 	}
 }
 
 func TestAndroidAppImport_ArchVariants(t *testing.T) {
 	// The test config's target arch is ARM64.
 	testCases := []struct {
-		name     string
-		bp       string
-		expected string
+		name         string
+		bp           string
+		expected     string
+		artifactPath string
+		metaDataPath string
+		installPath  string
 	}{
 		{
 			name: "matching arch",
@@ -343,7 +407,9 @@
 					},
 				}
 			`,
-			expected: "verify_uses_libraries/apk/app_arm64.apk",
+			expected:     "verify_uses_libraries/apk/app_arm64.apk",
+			artifactPath: "prebuilts/apk/app_arm64.apk",
+			installPath:  "/system/app/foo/foo.apk",
 		},
 		{
 			name: "no matching arch",
@@ -362,7 +428,9 @@
 					},
 				}
 			`,
-			expected: "verify_uses_libraries/apk/app.apk",
+			expected:     "verify_uses_libraries/apk/app.apk",
+			artifactPath: "prebuilts/apk/app.apk",
+			installPath:  "/system/app/foo/foo.apk",
 		},
 		{
 			name: "no matching arch without default",
@@ -380,7 +448,9 @@
 					},
 				}
 			`,
-			expected: "",
+			expected:     "",
+			artifactPath: "prebuilts/apk/app_arm.apk",
+			installPath:  "/system/app/foo/foo.apk",
 		},
 	}
 
@@ -393,6 +463,8 @@
 			if variant.Module().Enabled() {
 				t.Error("module should have been disabled, but wasn't")
 			}
+			rule := variant.MaybeRule("genProvenanceMetaData")
+			android.AssertDeepEquals(t, "Provenance metadata is not empty", android.TestingBuildParams{}, rule)
 			continue
 		}
 		jniRuleCommand := variant.Output("jnis-uncompressed/foo.apk").RuleParams.Command
@@ -403,6 +475,11 @@
 		if strings.HasSuffix(matches[1], test.expected) {
 			t.Errorf("wrong src apk, expected: %q got: %q", test.expected, matches[1])
 		}
+		rule := variant.Rule("genProvenanceMetaData")
+		android.AssertStringEquals(t, "Invalid input", test.artifactPath, rule.Inputs[0].String())
+		android.AssertStringEquals(t, "Invalid output", "out/soong/.intermediates/provenance_metadata/foo/provenance_metadata.textproto", rule.Output.String())
+		android.AssertStringEquals(t, "Invalid args", "foo", rule.Args["module_name"])
+		android.AssertStringEquals(t, "Invalid args", test.installPath, rule.Args["install_path"])
 	}
 }