Home | History | Annotate | Download | only in utils
      1 /*
      2  * Copyright (C) 2017 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License
     15  */
     16 
     17 package com.android.server.backup.utils;
     18 
     19 import static com.google.common.truth.Truth.assertThat;
     20 
     21 import static org.mockito.Mockito.doReturn;
     22 import static org.mockito.Mockito.mock;
     23 import static org.mockito.Mockito.when;
     24 
     25 import android.content.pm.ApplicationInfo;
     26 import android.content.pm.PackageInfo;
     27 import android.content.pm.PackageManager;
     28 import android.content.pm.PackageManagerInternal;
     29 import android.content.pm.PackageParser;
     30 import android.content.pm.Signature;
     31 import android.content.pm.SigningInfo;
     32 import android.os.Process;
     33 import android.platform.test.annotations.Presubmit;
     34 import android.support.test.filters.SmallTest;
     35 import android.support.test.runner.AndroidJUnit4;
     36 
     37 import com.android.server.backup.BackupManagerService;
     38 import com.android.server.backup.testutils.PackageManagerStub;
     39 
     40 import org.junit.Before;
     41 import org.junit.Test;
     42 import org.junit.runner.RunWith;
     43 
     44 @SmallTest
     45 @Presubmit
     46 @RunWith(AndroidJUnit4.class)
     47 public class AppBackupUtilsTest {
     48     private static final String CUSTOM_BACKUP_AGENT_NAME = "custom.backup.agent";
     49     private static final String TEST_PACKAGE_NAME = "test_package";
     50 
     51     private static final Signature SIGNATURE_1 = generateSignature((byte) 1);
     52     private static final Signature SIGNATURE_2 = generateSignature((byte) 2);
     53     private static final Signature SIGNATURE_3 = generateSignature((byte) 3);
     54     private static final Signature SIGNATURE_4 = generateSignature((byte) 4);
     55 
     56     private PackageManagerStub mPackageManagerStub;
     57     private PackageManagerInternal mMockPackageManagerInternal;
     58 
     59     @Before
     60     public void setUp() throws Exception {
     61         mPackageManagerStub = new PackageManagerStub();
     62         mMockPackageManagerInternal = mock(PackageManagerInternal.class);
     63     }
     64 
     65     @Test
     66     public void appIsEligibleForBackup_backupNotAllowed_returnsFalse() throws Exception {
     67         ApplicationInfo applicationInfo = new ApplicationInfo();
     68         applicationInfo.flags = 0;
     69         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
     70         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
     71         applicationInfo.packageName = TEST_PACKAGE_NAME;
     72 
     73         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
     74                 mPackageManagerStub);
     75 
     76         assertThat(isEligible).isFalse();
     77     }
     78 
     79     @Test
     80     public void appIsEligibleForBackup_systemAppWithoutCustomBackupAgent_returnsFalse()
     81             throws Exception {
     82         ApplicationInfo applicationInfo = new ApplicationInfo();
     83         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
     84         applicationInfo.uid = Process.SYSTEM_UID;
     85         applicationInfo.backupAgentName = null;
     86         applicationInfo.packageName = TEST_PACKAGE_NAME;
     87 
     88         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
     89                 mPackageManagerStub);
     90 
     91         assertThat(isEligible).isFalse();
     92     }
     93 
     94     @Test
     95     public void appIsEligibleForBackup_sharedStorageBackupPackage_returnsFalse() throws Exception {
     96         ApplicationInfo applicationInfo = new ApplicationInfo();
     97         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
     98         applicationInfo.uid = Process.SYSTEM_UID;
     99         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    100         applicationInfo.packageName = BackupManagerService.SHARED_BACKUP_AGENT_PACKAGE;
    101 
    102         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    103                 mPackageManagerStub);
    104 
    105         assertThat(isEligible).isFalse();
    106     }
    107 
    108     @Test
    109     public void appIsEligibleForBackup_systemAppWithCustomBackupAgentAndEnabled_returnsTrue()
    110             throws Exception {
    111         ApplicationInfo applicationInfo = new ApplicationInfo();
    112         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    113         applicationInfo.uid = Process.SYSTEM_UID;
    114         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    115         applicationInfo.packageName = TEST_PACKAGE_NAME;
    116 
    117         PackageManagerStub.sApplicationEnabledSetting =
    118                 PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
    119 
    120         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    121                 mPackageManagerStub);
    122 
    123         assertThat(isEligible).isTrue();
    124     }
    125 
    126     @Test
    127     public void appIsEligibleForBackup_nonSystemAppWithoutCustomBackupAgentAndEnabled_returnsTrue()
    128             throws Exception {
    129         ApplicationInfo applicationInfo = new ApplicationInfo();
    130         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    131         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    132         applicationInfo.backupAgentName = null;
    133         applicationInfo.packageName = TEST_PACKAGE_NAME;
    134 
    135         PackageManagerStub.sApplicationEnabledSetting =
    136                 PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
    137 
    138         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    139                 mPackageManagerStub);
    140 
    141         assertThat(isEligible).isTrue();
    142     }
    143 
    144     @Test
    145     public void appIsEligibleForBackup_nonSystemAppWithCustomBackupAgentAndEnabled_returnsTrue()
    146             throws Exception {
    147         ApplicationInfo applicationInfo = new ApplicationInfo();
    148         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    149         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    150         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    151         applicationInfo.packageName = TEST_PACKAGE_NAME;
    152 
    153         PackageManagerStub.sApplicationEnabledSetting =
    154                 PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
    155 
    156         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    157                 mPackageManagerStub);
    158 
    159         assertThat(isEligible).isTrue();
    160     }
    161 
    162     @Test
    163     public void appIsEligibleForBackup_systemAppWithCustomBackupAgentAndDisabled_returnsFalse()
    164             throws Exception {
    165         ApplicationInfo applicationInfo = new ApplicationInfo();
    166         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    167         applicationInfo.uid = Process.SYSTEM_UID;
    168         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    169         applicationInfo.packageName = TEST_PACKAGE_NAME;
    170 
    171         PackageManagerStub.sApplicationEnabledSetting =
    172                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
    173 
    174         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    175                 mPackageManagerStub);
    176 
    177         assertThat(isEligible).isFalse();
    178     }
    179 
    180     @Test
    181     public void appIsEligibleForBackup_nonSystemAppWithoutCustomBackupAgentAndDisabled_returnsFalse()
    182             throws Exception {
    183         ApplicationInfo applicationInfo = new ApplicationInfo();
    184         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    185         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    186         applicationInfo.backupAgentName = null;
    187         applicationInfo.packageName = TEST_PACKAGE_NAME;
    188 
    189         PackageManagerStub.sApplicationEnabledSetting =
    190                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
    191 
    192         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    193                 mPackageManagerStub);
    194 
    195         assertThat(isEligible).isFalse();
    196     }
    197 
    198     @Test
    199     public void appIsEligibleForBackup_nonSystemAppWithCustomBackupAgentAndDisbled_returnsFalse()
    200             throws Exception {
    201         ApplicationInfo applicationInfo = new ApplicationInfo();
    202         applicationInfo.flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
    203         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    204         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    205         applicationInfo.packageName = TEST_PACKAGE_NAME;
    206 
    207         PackageManagerStub.sApplicationEnabledSetting =
    208                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
    209 
    210         boolean isEligible = AppBackupUtils.appIsEligibleForBackup(applicationInfo,
    211                 mPackageManagerStub);
    212 
    213         assertThat(isEligible).isFalse();
    214     }
    215 
    216     @Test
    217     public void appIsDisabled_stateEnabled_returnsFalse() throws Exception {
    218         ApplicationInfo applicationInfo = new ApplicationInfo();
    219         applicationInfo.flags = 0;
    220         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    221         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    222         applicationInfo.packageName = TEST_PACKAGE_NAME;
    223 
    224         PackageManagerStub.sApplicationEnabledSetting =
    225                 PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
    226 
    227         boolean isDisabled = AppBackupUtils.appIsDisabled(applicationInfo, mPackageManagerStub);
    228 
    229         assertThat(isDisabled).isFalse();
    230     }
    231 
    232     @Test
    233     public void appIsDisabled_stateDisabled_returnsTrue() throws Exception {
    234         ApplicationInfo applicationInfo = new ApplicationInfo();
    235         applicationInfo.flags = 0;
    236         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    237         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    238         applicationInfo.packageName = TEST_PACKAGE_NAME;
    239 
    240         PackageManagerStub.sApplicationEnabledSetting =
    241                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
    242 
    243         boolean isDisabled = AppBackupUtils.appIsDisabled(applicationInfo, mPackageManagerStub);
    244 
    245         assertThat(isDisabled).isTrue();
    246     }
    247 
    248     @Test
    249     public void appIsDisabled_stateDisabledUser_returnsTrue() throws Exception {
    250         ApplicationInfo applicationInfo = new ApplicationInfo();
    251         applicationInfo.flags = 0;
    252         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    253         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    254         applicationInfo.packageName = TEST_PACKAGE_NAME;
    255 
    256         PackageManagerStub.sApplicationEnabledSetting =
    257                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED_USER;
    258 
    259         boolean isDisabled = AppBackupUtils.appIsDisabled(applicationInfo, mPackageManagerStub);
    260 
    261         assertThat(isDisabled).isTrue();
    262     }
    263 
    264     @Test
    265     public void appIsDisabled_stateDisabledUntilUsed_returnsTrue() throws Exception {
    266         ApplicationInfo applicationInfo = new ApplicationInfo();
    267         applicationInfo.flags = 0;
    268         applicationInfo.uid = Process.FIRST_APPLICATION_UID;
    269         applicationInfo.backupAgentName = CUSTOM_BACKUP_AGENT_NAME;
    270         applicationInfo.packageName = TEST_PACKAGE_NAME;
    271 
    272         PackageManagerStub.sApplicationEnabledSetting =
    273                 PackageManager.COMPONENT_ENABLED_STATE_DISABLED_UNTIL_USED;
    274 
    275         boolean isDisabled = AppBackupUtils.appIsDisabled(applicationInfo, mPackageManagerStub);
    276 
    277         assertThat(isDisabled).isTrue();
    278     }
    279 
    280     @Test
    281     public void appIsStopped_returnsTrue() throws Exception {
    282         ApplicationInfo applicationInfo = new ApplicationInfo();
    283         applicationInfo.flags |= ApplicationInfo.FLAG_STOPPED;
    284 
    285         boolean isStopped = AppBackupUtils.appIsStopped(applicationInfo);
    286 
    287         assertThat(isStopped).isTrue();
    288     }
    289 
    290     @Test
    291     public void appIsStopped_returnsFalse() throws Exception {
    292         ApplicationInfo applicationInfo = new ApplicationInfo();
    293         applicationInfo.flags = ~ApplicationInfo.FLAG_STOPPED;
    294 
    295         boolean isStopped = AppBackupUtils.appIsStopped(applicationInfo);
    296 
    297         assertThat(isStopped).isFalse();
    298     }
    299 
    300     @Test
    301     public void appGetsFullBackup_noCustomBackupAgent_returnsTrue() throws Exception {
    302         PackageInfo packageInfo = new PackageInfo();
    303         packageInfo.applicationInfo = new ApplicationInfo();
    304         packageInfo.applicationInfo.backupAgentName = null;
    305 
    306         boolean result = AppBackupUtils.appGetsFullBackup(packageInfo);
    307 
    308         assertThat(result).isTrue();
    309     }
    310 
    311     @Test
    312     public void appGetsFullBackup_withCustomBackupAgentAndFullBackupOnlyFlag_returnsTrue()
    313             throws Exception {
    314         PackageInfo packageInfo = new PackageInfo();
    315         packageInfo.applicationInfo = new ApplicationInfo();
    316         packageInfo.applicationInfo.backupAgentName = "backup.agent";
    317         packageInfo.applicationInfo.flags |= ApplicationInfo.FLAG_FULL_BACKUP_ONLY;
    318 
    319         boolean result = AppBackupUtils.appGetsFullBackup(packageInfo);
    320 
    321         assertThat(result).isTrue();
    322     }
    323 
    324     @Test
    325     public void appGetsFullBackup_withCustomBackupAgentAndWithoutFullBackupOnlyFlag_returnsFalse()
    326             throws Exception {
    327         PackageInfo packageInfo = new PackageInfo();
    328         packageInfo.applicationInfo = new ApplicationInfo();
    329         packageInfo.applicationInfo.backupAgentName = "backup.agent";
    330         packageInfo.applicationInfo.flags = ~ApplicationInfo.FLAG_FULL_BACKUP_ONLY;
    331 
    332         boolean result = AppBackupUtils.appGetsFullBackup(packageInfo);
    333 
    334         assertThat(result).isFalse();
    335     }
    336 
    337     @Test
    338     public void appIsKeyValueOnly_noCustomBackupAgent_returnsTrue() throws Exception {
    339         PackageInfo packageInfo = new PackageInfo();
    340         packageInfo.applicationInfo = new ApplicationInfo();
    341         packageInfo.applicationInfo.backupAgentName = null;
    342 
    343         boolean result = AppBackupUtils.appIsKeyValueOnly(packageInfo);
    344 
    345         assertThat(result).isFalse();
    346     }
    347 
    348     @Test
    349     public void appIsKeyValueOnly_withCustomBackupAgentAndFullBackupOnlyFlag_returnsTrue()
    350             throws Exception {
    351         PackageInfo packageInfo = new PackageInfo();
    352         packageInfo.applicationInfo = new ApplicationInfo();
    353         packageInfo.applicationInfo.backupAgentName = "backup.agent";
    354         packageInfo.applicationInfo.flags |= ApplicationInfo.FLAG_FULL_BACKUP_ONLY;
    355 
    356         boolean result = AppBackupUtils.appIsKeyValueOnly(packageInfo);
    357 
    358         assertThat(result).isFalse();
    359     }
    360 
    361     @Test
    362     public void appIsKeyValueOnly_withCustomBackupAgentAndWithoutFullBackupOnlyFlag_returnsFalse()
    363             throws Exception {
    364         PackageInfo packageInfo = new PackageInfo();
    365         packageInfo.applicationInfo = new ApplicationInfo();
    366         packageInfo.applicationInfo.backupAgentName = "backup.agent";
    367         packageInfo.applicationInfo.flags = ~ApplicationInfo.FLAG_FULL_BACKUP_ONLY;
    368 
    369         boolean result = AppBackupUtils.appIsKeyValueOnly(packageInfo);
    370 
    371         assertThat(result).isTrue();
    372     }
    373 
    374     @Test
    375     public void signaturesMatch_targetIsNull_returnsFalse() throws Exception {
    376         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {SIGNATURE_1}, null,
    377                 mMockPackageManagerInternal);
    378 
    379         assertThat(result).isFalse();
    380     }
    381 
    382     @Test
    383     public void signaturesMatch_systemApplication_returnsTrue() throws Exception {
    384         PackageInfo packageInfo = new PackageInfo();
    385         packageInfo.packageName = "test";
    386         packageInfo.applicationInfo = new ApplicationInfo();
    387         packageInfo.applicationInfo.flags |= ApplicationInfo.FLAG_SYSTEM;
    388 
    389         boolean result = AppBackupUtils.signaturesMatch(new Signature[0], packageInfo,
    390                 mMockPackageManagerInternal);
    391 
    392         assertThat(result).isTrue();
    393     }
    394 
    395     @Test
    396     public void signaturesMatch_disallowsUnsignedApps_storedSignatureNull_returnsFalse()
    397             throws Exception {
    398         PackageInfo packageInfo = new PackageInfo();
    399         packageInfo.packageName = "test";
    400         packageInfo.signingInfo = new SigningInfo(
    401                 new PackageParser.SigningDetails(
    402                         new Signature[] {SIGNATURE_1},
    403                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    404                         null,
    405                         null,
    406                         null));
    407         packageInfo.applicationInfo = new ApplicationInfo();
    408 
    409         boolean result = AppBackupUtils.signaturesMatch(null, packageInfo,
    410                 mMockPackageManagerInternal);
    411 
    412         assertThat(result).isFalse();
    413     }
    414 
    415     @Test
    416     public void signaturesMatch_disallowsUnsignedApps_storedSignatureEmpty_returnsFalse()
    417             throws Exception {
    418         PackageInfo packageInfo = new PackageInfo();
    419         packageInfo.packageName = "test";
    420         packageInfo.signingInfo = new SigningInfo(
    421                 new PackageParser.SigningDetails(
    422                         new Signature[] {SIGNATURE_1},
    423                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    424                         null,
    425                         null,
    426                         null));
    427         packageInfo.applicationInfo = new ApplicationInfo();
    428 
    429         boolean result = AppBackupUtils.signaturesMatch(new Signature[0], packageInfo,
    430                 mMockPackageManagerInternal);
    431 
    432         assertThat(result).isFalse();
    433     }
    434 
    435 
    436     @Test
    437     public void
    438     signaturesMatch_disallowsUnsignedApps_targetSignatureEmpty_returnsFalse()
    439             throws Exception {
    440         PackageInfo packageInfo = new PackageInfo();
    441         packageInfo.packageName = "test";
    442         packageInfo.signingInfo = null;
    443         packageInfo.applicationInfo = new ApplicationInfo();
    444 
    445         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {SIGNATURE_1}, packageInfo,
    446                 mMockPackageManagerInternal);
    447 
    448         assertThat(result).isFalse();
    449     }
    450 
    451     @Test
    452     public void
    453     signaturesMatch_disallowsUnsignedApps_targetSignatureNull_returnsFalse()
    454             throws Exception {
    455         PackageInfo packageInfo = new PackageInfo();
    456         packageInfo.packageName = "test";
    457         packageInfo.signingInfo = null;
    458         packageInfo.applicationInfo = new ApplicationInfo();
    459 
    460         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {SIGNATURE_1}, packageInfo,
    461                 mMockPackageManagerInternal);
    462 
    463         assertThat(result).isFalse();
    464     }
    465 
    466     @Test
    467     public void signaturesMatch_disallowsUnsignedApps_bothSignaturesNull_returnsFalse()
    468             throws Exception {
    469         PackageInfo packageInfo = new PackageInfo();
    470         packageInfo.signingInfo = null;
    471         packageInfo.applicationInfo = new ApplicationInfo();
    472 
    473         boolean result = AppBackupUtils.signaturesMatch(null, packageInfo,
    474                 mMockPackageManagerInternal);
    475 
    476         assertThat(result).isFalse();
    477     }
    478 
    479     @Test
    480     public void signaturesMatch_disallowsUnsignedApps_bothSignaturesEmpty_returnsFalse()
    481             throws Exception {
    482         PackageInfo packageInfo = new PackageInfo();
    483         packageInfo.packageName = "test";
    484         packageInfo.signingInfo = null;
    485         packageInfo.applicationInfo = new ApplicationInfo();
    486 
    487         boolean result = AppBackupUtils.signaturesMatch(new Signature[0], packageInfo,
    488                 mMockPackageManagerInternal);
    489 
    490         assertThat(result).isFalse();
    491     }
    492 
    493     @Test
    494     public void signaturesMatch_equalSignatures_returnsTrue() throws Exception {
    495         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    496         Signature signature2Copy = new Signature(SIGNATURE_2.toByteArray());
    497         Signature signature3Copy = new Signature(SIGNATURE_3.toByteArray());
    498 
    499         PackageInfo packageInfo = new PackageInfo();
    500         packageInfo.packageName = "test";
    501         packageInfo.signingInfo = new SigningInfo(
    502                 new PackageParser.SigningDetails(
    503                         new Signature[] {SIGNATURE_1, SIGNATURE_2, SIGNATURE_3},
    504                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    505                         null,
    506                         null,
    507                         null));
    508         packageInfo.applicationInfo = new ApplicationInfo();
    509 
    510         boolean result = AppBackupUtils.signaturesMatch(
    511                 new Signature[] {signature3Copy, signature1Copy, signature2Copy}, packageInfo,
    512                 mMockPackageManagerInternal);
    513 
    514         assertThat(result).isTrue();
    515     }
    516 
    517     @Test
    518     public void signaturesMatch_extraSignatureInTarget_returnsTrue() throws Exception {
    519         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    520         Signature signature2Copy = new Signature(SIGNATURE_2.toByteArray());
    521 
    522         PackageInfo packageInfo = new PackageInfo();
    523         packageInfo.packageName = "test";
    524         packageInfo.signingInfo = new SigningInfo(
    525                 new PackageParser.SigningDetails(
    526                         new Signature[] {SIGNATURE_1, SIGNATURE_2, SIGNATURE_3},
    527                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    528                         null,
    529                         null,
    530                         null));
    531         packageInfo.applicationInfo = new ApplicationInfo();
    532 
    533         boolean result = AppBackupUtils.signaturesMatch(
    534                 new Signature[]{signature2Copy, signature1Copy}, packageInfo,
    535                 mMockPackageManagerInternal);
    536 
    537         assertThat(result).isTrue();
    538     }
    539 
    540     @Test
    541     public void signaturesMatch_extraSignatureInStored_returnsFalse() throws Exception {
    542         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    543         Signature signature2Copy = new Signature(SIGNATURE_2.toByteArray());
    544 
    545         PackageInfo packageInfo = new PackageInfo();
    546         packageInfo.packageName = "test";
    547         packageInfo.signingInfo = new SigningInfo(
    548                 new PackageParser.SigningDetails(
    549                         new Signature[] {signature1Copy, signature2Copy},
    550                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    551                         null,
    552                         null,
    553                         null));
    554         packageInfo.applicationInfo = new ApplicationInfo();
    555 
    556         boolean result = AppBackupUtils.signaturesMatch(
    557                 new Signature[]{SIGNATURE_1, SIGNATURE_2, SIGNATURE_3}, packageInfo,
    558                 mMockPackageManagerInternal);
    559 
    560         assertThat(result).isFalse();
    561     }
    562 
    563     @Test
    564     public void signaturesMatch_oneNonMatchingSignature_returnsFalse() throws Exception {
    565         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    566         Signature signature2Copy = new Signature(SIGNATURE_2.toByteArray());
    567 
    568         PackageInfo packageInfo = new PackageInfo();
    569         packageInfo.packageName = "test";
    570         packageInfo.signingInfo = new SigningInfo(
    571                 new PackageParser.SigningDetails(
    572                         new Signature[] {SIGNATURE_1, SIGNATURE_2, SIGNATURE_3},
    573                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    574                         null,
    575                         null,
    576                         null));
    577         packageInfo.applicationInfo = new ApplicationInfo();
    578 
    579         boolean result = AppBackupUtils.signaturesMatch(
    580                 new Signature[]{signature1Copy, signature2Copy, SIGNATURE_4}, packageInfo,
    581                 mMockPackageManagerInternal);
    582 
    583         assertThat(result).isFalse();
    584     }
    585 
    586     @Test
    587     public void signaturesMatch_singleStoredSignatureNoRotation_returnsTrue()
    588             throws Exception {
    589         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    590 
    591         PackageInfo packageInfo = new PackageInfo();
    592         packageInfo.packageName = "test";
    593         packageInfo.signingInfo = new SigningInfo(
    594                 new PackageParser.SigningDetails(
    595                         new Signature[] {SIGNATURE_1},
    596                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    597                         null,
    598                         null,
    599                         null));
    600         packageInfo.applicationInfo = new ApplicationInfo();
    601 
    602         doReturn(true).when(mMockPackageManagerInternal).isDataRestoreSafe(signature1Copy,
    603                 packageInfo.packageName);
    604 
    605         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {signature1Copy},
    606                 packageInfo, mMockPackageManagerInternal);
    607 
    608         assertThat(result).isTrue();
    609     }
    610 
    611     @Test
    612     public void signaturesMatch_singleStoredSignatureWithRotationAssumeDataCapability_returnsTrue()
    613             throws Exception {
    614         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    615 
    616         PackageInfo packageInfo = new PackageInfo();
    617         packageInfo.packageName = "test";
    618         packageInfo.signingInfo = new SigningInfo(
    619                 new PackageParser.SigningDetails(
    620                         new Signature[] {SIGNATURE_2},
    621                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    622                         null,
    623                         new Signature[] {SIGNATURE_1, SIGNATURE_2},
    624                         new int[] {0, 0}));
    625         packageInfo.applicationInfo = new ApplicationInfo();
    626 
    627         // we know signature1Copy is in history, and we want to assume it has
    628         // SigningDetails.CertCapabilities.INSTALLED_DATA capability
    629         doReturn(true).when(mMockPackageManagerInternal).isDataRestoreSafe(signature1Copy,
    630                 packageInfo.packageName);
    631 
    632         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {signature1Copy},
    633                 packageInfo, mMockPackageManagerInternal);
    634 
    635         assertThat(result).isTrue();
    636     }
    637 
    638     @Test
    639     public void
    640             signaturesMatch_singleStoredSignatureWithRotationAssumeNoDataCapability_returnsFalse()
    641             throws Exception {
    642         Signature signature1Copy = new Signature(SIGNATURE_1.toByteArray());
    643 
    644         PackageInfo packageInfo = new PackageInfo();
    645         packageInfo.packageName = "test";
    646         packageInfo.signingInfo = new SigningInfo(
    647                 new PackageParser.SigningDetails(
    648                         new Signature[] {SIGNATURE_2},
    649                         PackageParser.SigningDetails.SignatureSchemeVersion.SIGNING_BLOCK_V3,
    650                         null,
    651                         new Signature[] {SIGNATURE_1, SIGNATURE_2},
    652                         new int[] {0, 0}));
    653         packageInfo.applicationInfo = new ApplicationInfo();
    654 
    655         // we know signature1Copy is in history, but we want to assume it does not have
    656         // SigningDetails.CertCapabilities.INSTALLED_DATA capability
    657         doReturn(false).when(mMockPackageManagerInternal).isDataRestoreSafe(signature1Copy,
    658                 packageInfo.packageName);
    659 
    660         boolean result = AppBackupUtils.signaturesMatch(new Signature[] {signature1Copy},
    661                 packageInfo, mMockPackageManagerInternal);
    662 
    663         assertThat(result).isFalse();
    664     }
    665 
    666     private static Signature generateSignature(byte i) {
    667         byte[] signatureBytes = new byte[256];
    668         signatureBytes[0] = i;
    669         return new Signature(signatureBytes);
    670     }
    671 }
    672