Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a203d43e authored by Khaled Abdelmohsen's avatar Khaled Abdelmohsen Committed by Android (Google) Code Review
Browse files

Merge "Skip integrity verification for verifiers"

parents 9f22c535 73901619
Loading
Loading
Loading
Loading
+21 −3
Original line number Diff line number Diff line
@@ -220,7 +220,17 @@ public class AppIntegrityManagerServiceImpl extends IAppIntegrityManager.Stub {
                return;
            }

            String ruleProvider = getCallerPackageName();
            String installerPackageName = getInstallerPackageName(intent);

            // Skip integrity verification if the verifier is doing the install.
            if (ruleProvider != null && ruleProvider.equals(installerPackageName)) {
                Slog.i(TAG, "Verifier doing the install. Skipping integrity check.");
                mPackageManagerInternal.setIntegrityVerificationResult(
                        verificationId, PackageManagerInternal.INTEGRITY_VERIFICATION_ALLOW);
                return;
            }

            String appCert = getCertificateFingerprint(packageInfo);

            AppInstallMetadata.Builder builder = new AppInstallMetadata.Builder();
@@ -518,6 +528,16 @@ public class AppIntegrityManagerServiceImpl extends IAppIntegrityManager.Stub {
    }

    private String getCallerPackageNameOrThrow() {
        String callerPackageName = getCallerPackageName();
        if (callerPackageName == null) {
            throw new SecurityException(
                    "Only system packages specified in config_integrityRuleProviderPackages are"
                            + " allowed to call this method.");
        }
        return callerPackageName;
    }

    private String getCallerPackageName() {
        final String[] allowedRuleProviders =
                mContext.getResources()
                        .getStringArray(R.array.config_integrityRuleProviderPackages);
@@ -537,9 +557,7 @@ public class AppIntegrityManagerServiceImpl extends IAppIntegrityManager.Stub {
                Slog.i(TAG, "Rule provider package " + packageName + " not installed.");
            }
        }
        throw new SecurityException(
                "Only system packages specified in config_integrityRuleProviderPackages are"
                        + " allowed to call this method.");
        return null;
    }

    private boolean isSystemApp(String packageName) {
+49 −6
Original line number Diff line number Diff line
@@ -92,7 +92,7 @@ public class AppIntegrityManagerServiceImplTest {

    private static final String PACKAGE_NAME = "com.test.app";
    private static final int VERSION_CODE = 100;
    private static final String INSTALLER = TEST_FRAMEWORK_PACKAGE;
    private static final String INSTALLER = "com.long.random.test.installer.name";
    // These are obtained by running the test and checking logcat.
    private static final String APP_CERT =
            "301AA3CB081134501C45F1422ABC66C24224FD5DED5FDC8F17E697176FD866AA";
@@ -100,7 +100,7 @@ public class AppIntegrityManagerServiceImplTest {
            "301AA3CB081134501C45F1422ABC66C24224FD5DED5FDC8F17E697176FD866AA";
    // We use SHA256 for package names longer than 32 characters.
    private static final String INSTALLER_SHA256 =
            "786933C28839603EB48C50B2A688DC6BE52C833627CB2731FF8466A2AE9F94CD";
            "30F41A7CBF96EE736A54DD6DF759B50ED3CC126ABCEF694E167C324F5976C227";

    private static final String PLAY_STORE_PKG = "com.android.vending";
    private static final String ADB_INSTALLER = "adb";
@@ -267,6 +267,8 @@ public class AppIntegrityManagerServiceImplTest {

    @Test
    public void broadcastReceiverRegistration() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        ArgumentCaptor<IntentFilter> intentFilterCaptor =
                ArgumentCaptor.forClass(IntentFilter.class);

@@ -281,6 +283,8 @@ public class AppIntegrityManagerServiceImplTest {

    @Test
    public void handleBroadcast_correctArgs() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        ArgumentCaptor<BroadcastReceiver> broadcastReceiverCaptor =
                ArgumentCaptor.forClass(BroadcastReceiver.class);
        verify(mMockContext)
@@ -314,6 +318,8 @@ public class AppIntegrityManagerServiceImplTest {

    @Test
    public void handleBroadcast_allow() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        ArgumentCaptor<BroadcastReceiver> broadcastReceiverCaptor =
                ArgumentCaptor.forClass(BroadcastReceiver.class);
        verify(mMockContext)
@@ -331,6 +337,8 @@ public class AppIntegrityManagerServiceImplTest {

    @Test
    public void handleBroadcast_reject() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        ArgumentCaptor<BroadcastReceiver> broadcastReceiverCaptor =
                ArgumentCaptor.forClass(BroadcastReceiver.class);
        verify(mMockContext)
@@ -354,6 +362,8 @@ public class AppIntegrityManagerServiceImplTest {

    @Test
    public void handleBroadcast_notInitialized() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        when(mIntegrityFileManager.initialized()).thenReturn(false);
        ArgumentCaptor<BroadcastReceiver> broadcastReceiverCaptor =
                ArgumentCaptor.forClass(BroadcastReceiver.class);
@@ -371,6 +381,26 @@ public class AppIntegrityManagerServiceImplTest {
        verify(mSpyPackageManager, never()).getPackageArchiveInfo(any(), anyInt());
    }

    @Test
    public void verifierAsInstaller_skipIntegrityVerification() throws Exception {
        whitelistUsAsRuleProvider();
        makeUsSystemApp();
        ArgumentCaptor<BroadcastReceiver> broadcastReceiverCaptor =
                ArgumentCaptor.forClass(BroadcastReceiver.class);
        verify(mMockContext)
                .registerReceiver(broadcastReceiverCaptor.capture(), any(), any(), any());
        Intent intent = makeVerificationIntent(TEST_FRAMEWORK_PACKAGE);
        when(mRuleEvaluationEngine.evaluate(any(), any())).thenReturn(
                IntegrityCheckResult.deny(/* rule= */ null));

        broadcastReceiverCaptor.getValue().onReceive(mMockContext, intent);
        runJobInHandler();

        verify(mPackageManagerInternal)
                .setIntegrityVerificationResult(
                        1, PackageManagerInternal.INTEGRITY_VERIFICATION_ALLOW);
    }

    private void whitelistUsAsRuleProvider() {
        Resources mockResources = mock(Resources.class);
        when(mockResources.getStringArray(R.array.config_integrityRuleProviderPackages))
@@ -395,15 +425,28 @@ public class AppIntegrityManagerServiceImplTest {
    }

    private Intent makeVerificationIntent() throws Exception {
        PackageInfo packageInfo =
                mRealContext.getPackageManager().getPackageInfo(TEST_FRAMEWORK_PACKAGE,
                        PackageManager.GET_SIGNATURES);
        doReturn(packageInfo)
                .when(mSpyPackageManager)
                .getPackageInfo(eq(INSTALLER), anyInt());
        doReturn(1)
                .when(mSpyPackageManager)
                .getPackageUid(eq(INSTALLER), anyInt());
        return makeVerificationIntent(INSTALLER);
    }

    private Intent makeVerificationIntent(String installer) throws Exception {
        Intent intent = new Intent();
        intent.setDataAndType(Uri.fromFile(mTestApk), PACKAGE_MIME_TYPE);
        intent.setAction(Intent.ACTION_PACKAGE_NEEDS_INTEGRITY_VERIFICATION);
        intent.putExtra(EXTRA_VERIFICATION_ID, 1);
        intent.putExtra(Intent.EXTRA_PACKAGE_NAME, PACKAGE_NAME);
        intent.putExtra(EXTRA_VERIFICATION_INSTALLER_PACKAGE, INSTALLER);
        intent.putExtra(EXTRA_VERIFICATION_INSTALLER_PACKAGE, installer);
        intent.putExtra(
                EXTRA_VERIFICATION_INSTALLER_UID,
                mRealContext.getPackageManager().getPackageUid(INSTALLER, /* flags= */ 0));
                mMockContext.getPackageManager().getPackageUid(installer, /* flags= */ 0));
        intent.putExtra(Intent.EXTRA_VERSION_CODE, VERSION_CODE);
        return intent;
    }