1 /*
2  * Copyright (C) 2018 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.testing;
18 
19 import android.annotation.IntDef;
20 import android.content.pm.ApplicationInfo;
21 import android.os.Process;
22 
23 import java.lang.annotation.Retention;
24 import java.lang.annotation.RetentionPolicy;
25 
26 // TODO: Preconditions is not available, include its target in dependencies
27 public class PackageData {
28     public static final PackageData PM_PACKAGE = new PmPackageData();
29 
keyValuePackage(int identifier)30     public static PackageData keyValuePackage(int identifier) {
31         return androidPackage(identifier, BackupStatus.KEY_VALUE_BACKUP);
32     }
33 
fullBackupPackage(int identifier)34     public static PackageData fullBackupPackage(int identifier) {
35         return androidPackage(identifier, BackupStatus.FULL_BACKUP);
36     }
37 
38     /** Returns {@link PackageData} for unique package identifier {@code identifier}. */
androidPackage(int identifier)39     public static PackageData androidPackage(int identifier) {
40         return androidPackage(identifier, BackupStatus.KEY_VALUE_BACKUP);
41     }
42 
43     public final String packageName;
44     public final String agentName;
45     @BackupStatus public final int backupStatus;
46     public final boolean available;
47     public final boolean stopped;
48     public final int uid;
49 
PackageData( String packageName, String agentName, int backupStatus, boolean stopped, boolean available, int uid)50     private PackageData(
51             String packageName,
52             String agentName,
53             int backupStatus,
54             boolean stopped,
55             boolean available,
56             int uid) {
57         // checkArgument(!stopped || !available, "stopped => !available")
58 
59         this.packageName = packageName;
60         this.agentName = agentName;
61         this.backupStatus = backupStatus;
62         this.stopped = stopped;
63         this.available = available;
64         this.uid = uid;
65     }
66 
flags()67     public int flags() {
68         int flags = 0;
69         if (backupStatus != BackupStatus.BACKUP_NOT_ALLOWED) {
70             flags |= ApplicationInfo.FLAG_ALLOW_BACKUP;
71         }
72         if (backupStatus == BackupStatus.FULL_BACKUP) {
73             flags |= ApplicationInfo.FLAG_FULL_BACKUP_ONLY;
74         }
75         if (stopped) {
76             flags |= ApplicationInfo.FLAG_STOPPED;
77         }
78         return flags;
79     }
80 
backupNotAllowed()81     public PackageData backupNotAllowed() {
82         return new PackageData(
83                 packageName, agentName, BackupStatus.BACKUP_NOT_ALLOWED, stopped, available, uid);
84     }
85 
stopped()86     public PackageData stopped() {
87         return new PackageData(packageName, agentName, backupStatus, true, false, uid);
88     }
89 
unavailable()90     public PackageData unavailable() {
91         return new PackageData(packageName, agentName, backupStatus, stopped, false, uid);
92     }
93 
isPm()94     public boolean isPm() {
95         return this == PM_PACKAGE;
96     }
97 
androidPackage(int identifier, @BackupStatus int backupStatus)98     private static PackageData androidPackage(int identifier, @BackupStatus int backupStatus) {
99         // checkArgument(identifier >= 0, "identifier can't be < 0");
100 
101         String packageName = "com.sample.package" + identifier;
102         return new PackageData(
103                 packageName,
104                 packageName + ".BackupAgent",
105                 backupStatus,
106                 false,
107                 true,
108                 Process.FIRST_APPLICATION_UID + identifier);
109     }
110 
111     private static class PmPackageData extends PackageData {
PmPackageData()112         private PmPackageData() {
113             super(
114                     "@pm@",
115                     "com.android.server.backup.PackageManagerBackupAgent",
116                     BackupStatus.KEY_VALUE_BACKUP,
117                     false,
118                     true,
119                     Process.SYSTEM_UID);
120         }
121 
122         @Override
flags()123         public int flags() {
124             throw new UnsupportedOperationException("PM \"package\" has no flags");
125         }
126 
127         @Override
backupNotAllowed()128         public PackageData backupNotAllowed() {
129             throw new UnsupportedOperationException("PM \"package\" has backup allowed");
130         }
131 
132         @Override
stopped()133         public PackageData stopped() {
134             throw new UnsupportedOperationException("PM \"package\" can't be stopped");
135         }
136 
137         @Override
unavailable()138         public PackageData unavailable() {
139             throw new UnsupportedOperationException("PM \"package\" is always available");
140         }
141     }
142 
143     @IntDef({
144         BackupStatus.KEY_VALUE_BACKUP,
145         BackupStatus.FULL_BACKUP,
146         BackupStatus.BACKUP_NOT_ALLOWED
147     })
148     @Retention(RetentionPolicy.SOURCE)
149     public @interface BackupStatus {
150         int KEY_VALUE_BACKUP = 0;
151         int FULL_BACKUP = 1;
152         int BACKUP_NOT_ALLOWED = 2;
153     }
154 }
155