blob: 3390efe18610ce9246d09d7483221793c10c81a8 [file] [log] [blame]
Kenny Rootcf0b38c2011-03-22 14:17:59 -07001/*
2 * Copyright (C) 2011 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
17package com.android.server.pm;
18
19import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DEFAULT;
20import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_DISABLED;
21import static android.content.pm.PackageManager.COMPONENT_ENABLED_STATE_ENABLED;
22
Dianne Hackborn7767eac2012-08-23 18:25:40 -070023import android.content.pm.PackageUserState;
Amith Yamasani483f3b02012-03-13 16:08:00 -070024import android.util.SparseArray;
Kenny Rootcf0b38c2011-03-22 14:17:59 -070025
26import java.io.File;
27import java.util.HashSet;
28
29/**
30 * Settings base class for pending and resolved classes.
31 */
32class PackageSettingBase extends GrantedPermissions {
33 /**
34 * Indicates the state of installation. Used by PackageManager to figure out
35 * incomplete installations. Say a package is being installed (the state is
36 * set to PKG_INSTALL_INCOMPLETE) and remains so till the package
37 * installation is successful or unsuccessful in which case the
38 * PackageManager will no longer maintain state information associated with
39 * the package. If some exception(like device freeze or battery being pulled
40 * out) occurs during installation of a package, the PackageManager needs
41 * this information to clean up the previously failed installation.
42 */
43 static final int PKG_INSTALL_COMPLETE = 1;
44 static final int PKG_INSTALL_INCOMPLETE = 0;
45
46 final String name;
47 final String realName;
Jeff Sharkey57dcf5b2014-06-18 17:46:05 -070048
49 /**
50 * Path where this package was found on disk. For monolithic packages
51 * this is path to single base APK file; for cluster packages this is
52 * path to the cluster directory.
53 */
Kenny Rootcf0b38c2011-03-22 14:17:59 -070054 File codePath;
55 String codePathString;
56 File resourcePath;
57 String resourcePathString;
Narayan Kamathff110bd2014-07-04 18:30:45 +010058
59 /**
60 * The path under which native libraries for legacy apps are unpacked.
61 * Will be set to {@code null} for newer installs, where the path can be
62 * derived from {@link #codePath} unambiguously.
63 */
64 String legacyNativeLibraryPathString;
65
66 String primaryCpuAbiString;
67 String secondaryCpuAbiString;
Kenny Rootcf0b38c2011-03-22 14:17:59 -070068 long timeStamp;
69 long firstInstallTime;
70 long lastUpdateTime;
71 int versionCode;
72
73 boolean uidError;
74
75 PackageSignatures signatures = new PackageSignatures();
76
77 boolean permissionsFixed;
78 boolean haveGids;
79
Geremy Condraf1bcca82013-01-07 22:35:24 -080080 PackageKeySetData keySetData = new PackageKeySetData();
81
Dianne Hackborn4a9f0712012-10-02 15:29:06 -070082 private static final PackageUserState DEFAULT_USER_STATE = new PackageUserState();
Dianne Hackborn7767eac2012-08-23 18:25:40 -070083
Kenny Rootcf0b38c2011-03-22 14:17:59 -070084 // Whether this package is currently stopped, thus can not be
85 // started until explicitly launched by the user.
Dianne Hackborn7767eac2012-08-23 18:25:40 -070086 private final SparseArray<PackageUserState> userState = new SparseArray<PackageUserState>();
Amith Yamasani483f3b02012-03-13 16:08:00 -070087
Kenny Rootcf0b38c2011-03-22 14:17:59 -070088 int installStatus = PKG_INSTALL_COMPLETE;
89
90 PackageSettingBase origPackage;
Amith Yamasani483f3b02012-03-13 16:08:00 -070091
Kenny Rootcf0b38c2011-03-22 14:17:59 -070092 /* package name of the app that installed this package */
93 String installerPackageName;
94 PackageSettingBase(String name, String realName, File codePath, File resourcePath,
Narayan Kamathff110bd2014-07-04 18:30:45 +010095 String legacyNativeLibraryPathString, String primaryCpuAbiString,
96 String secondaryCpuAbiString, int pVersionCode, int pkgFlags) {
Kenny Rootcf0b38c2011-03-22 14:17:59 -070097 super(pkgFlags);
98 this.name = name;
99 this.realName = realName;
Narayan Kamathff110bd2014-07-04 18:30:45 +0100100 init(codePath, resourcePath, legacyNativeLibraryPathString, primaryCpuAbiString,
101 secondaryCpuAbiString, pVersionCode);
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700102 }
103
104 /**
105 * New instance of PackageSetting with one-level-deep cloning.
106 */
107 @SuppressWarnings("unchecked")
108 PackageSettingBase(PackageSettingBase base) {
109 super(base);
110
111 name = base.name;
112 realName = base.realName;
113 codePath = base.codePath;
114 codePathString = base.codePathString;
115 resourcePath = base.resourcePath;
116 resourcePathString = base.resourcePathString;
Narayan Kamathff110bd2014-07-04 18:30:45 +0100117 legacyNativeLibraryPathString = base.legacyNativeLibraryPathString;
118 primaryCpuAbiString = base.primaryCpuAbiString;
119 secondaryCpuAbiString = base.secondaryCpuAbiString;
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700120 timeStamp = base.timeStamp;
121 firstInstallTime = base.firstInstallTime;
122 lastUpdateTime = base.lastUpdateTime;
123 versionCode = base.versionCode;
124
125 uidError = base.uidError;
126
127 signatures = new PackageSignatures(base.signatures);
128
129 permissionsFixed = base.permissionsFixed;
130 haveGids = base.haveGids;
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700131 userState.clear();
132 for (int i=0; i<base.userState.size(); i++) {
133 userState.put(base.userState.keyAt(i),
134 new PackageUserState(base.userState.valueAt(i)));
135 }
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700136 installStatus = base.installStatus;
137
138 origPackage = base.origPackage;
139
140 installerPackageName = base.installerPackageName;
Geremy Condraf1bcca82013-01-07 22:35:24 -0800141
142 keySetData = new PackageKeySetData(base.keySetData);
143
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700144 }
145
Narayan Kamathff110bd2014-07-04 18:30:45 +0100146 void init(File codePath, File resourcePath, String legacyNativeLibraryPathString,
147 String primaryCpuAbiString, String secondaryCpuAbiString, int pVersionCode) {
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700148 this.codePath = codePath;
149 this.codePathString = codePath.toString();
150 this.resourcePath = resourcePath;
151 this.resourcePathString = resourcePath.toString();
Narayan Kamathff110bd2014-07-04 18:30:45 +0100152 this.legacyNativeLibraryPathString = legacyNativeLibraryPathString;
153 this.primaryCpuAbiString = primaryCpuAbiString;
154 this.secondaryCpuAbiString = secondaryCpuAbiString;
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700155 this.versionCode = pVersionCode;
156 }
157
158 public void setInstallerPackageName(String packageName) {
159 installerPackageName = packageName;
160 }
161
162 String getInstallerPackageName() {
163 return installerPackageName;
164 }
165
166 public void setInstallStatus(int newStatus) {
167 installStatus = newStatus;
168 }
169
170 public int getInstallStatus() {
171 return installStatus;
172 }
173
174 public void setTimeStamp(long newStamp) {
175 timeStamp = newStamp;
176 }
177
178 /**
179 * Make a shallow copy of this package settings.
180 */
181 public void copyFrom(PackageSettingBase base) {
182 grantedPermissions = base.grantedPermissions;
183 gids = base.gids;
184
Narayan Kamathff110bd2014-07-04 18:30:45 +0100185 primaryCpuAbiString = base.primaryCpuAbiString;
186 secondaryCpuAbiString = base.secondaryCpuAbiString;
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700187 timeStamp = base.timeStamp;
188 firstInstallTime = base.firstInstallTime;
189 lastUpdateTime = base.lastUpdateTime;
190 signatures = base.signatures;
191 permissionsFixed = base.permissionsFixed;
192 haveGids = base.haveGids;
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700193 userState.clear();
194 for (int i=0; i<base.userState.size(); i++) {
195 userState.put(base.userState.keyAt(i), base.userState.valueAt(i));
196 }
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700197 installStatus = base.installStatus;
Geremy Condraf1bcca82013-01-07 22:35:24 -0800198 keySetData = base.keySetData;
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700199 }
200
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700201 private PackageUserState modifyUserState(int userId) {
202 PackageUserState state = userState.get(userId);
203 if (state == null) {
Dianne Hackborn4a9f0712012-10-02 15:29:06 -0700204 state = new PackageUserState();
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700205 userState.put(userId, state);
206 }
207 return state;
208 }
209
210 public PackageUserState readUserState(int userId) {
211 PackageUserState state = userState.get(userId);
Dianne Hackbornd4ac8d72012-09-27 23:20:10 -0700212 if (state != null) {
213 return state;
214 }
Dianne Hackborn4a9f0712012-10-02 15:29:06 -0700215 return DEFAULT_USER_STATE;
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700216 }
217
Dianne Hackborn3fa3c28a2013-03-26 16:15:41 -0700218 void setEnabled(int state, int userId, String callingPackage) {
219 PackageUserState st = modifyUserState(userId);
220 st.enabled = state;
221 st.lastDisableAppCaller = callingPackage;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700222 }
223
224 int getEnabled(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700225 return readUserState(userId).enabled;
226 }
227
Dianne Hackborn3fa3c28a2013-03-26 16:15:41 -0700228 String getLastDisabledAppCaller(int userId) {
229 return readUserState(userId).lastDisableAppCaller;
230 }
231
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700232 void setInstalled(boolean inst, int userId) {
233 modifyUserState(userId).installed = inst;
234 }
235
236 boolean getInstalled(int userId) {
237 return readUserState(userId).installed;
238 }
239
240 boolean isAnyInstalled(int[] users) {
241 for (int user: users) {
242 if (readUserState(user).installed) {
243 return true;
244 }
245 }
246 return false;
247 }
248
Dianne Hackborn786b4402012-08-27 15:14:02 -0700249 int[] queryInstalledUsers(int[] users, boolean installed) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700250 int num = 0;
251 for (int user : users) {
Dianne Hackborn786b4402012-08-27 15:14:02 -0700252 if (getInstalled(user) == installed) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700253 num++;
254 }
255 }
256 int[] res = new int[num];
257 num = 0;
258 for (int user : users) {
Dianne Hackborn786b4402012-08-27 15:14:02 -0700259 if (getInstalled(user) == installed) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700260 res[num] = user;
261 num++;
262 }
263 }
264 return res;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700265 }
266
267 boolean getStopped(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700268 return readUserState(userId).stopped;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700269 }
270
271 void setStopped(boolean stop, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700272 modifyUserState(userId).stopped = stop;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700273 }
274
275 boolean getNotLaunched(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700276 return readUserState(userId).notLaunched;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700277 }
278
279 void setNotLaunched(boolean stop, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700280 modifyUserState(userId).notLaunched = stop;
281 }
282
Amith Yamasani655d0e22013-06-12 14:19:10 -0700283 boolean getBlocked(int userId) {
284 return readUserState(userId).blocked;
285 }
286
287 void setBlocked(boolean blocked, int userId) {
288 modifyUserState(userId).blocked = blocked;
289 }
290
Kenny Guyc13053b2014-05-29 14:17:17 +0100291 boolean getBlockUninstall(int userId) {
292 return readUserState(userId).blockUninstall;
293 }
294
295 void setBlockUninstall(boolean blockUninstall, int userId) {
296 modifyUserState(userId).blockUninstall = blockUninstall;
297 }
298
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700299 void setUserState(int userId, int enabled, boolean installed, boolean stopped,
Amith Yamasani655d0e22013-06-12 14:19:10 -0700300 boolean notLaunched, boolean blocked,
301 String lastDisableAppCaller, HashSet<String> enabledComponents,
Kenny Guyc13053b2014-05-29 14:17:17 +0100302 HashSet<String> disabledComponents, boolean blockUninstall) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700303 PackageUserState state = modifyUserState(userId);
304 state.enabled = enabled;
305 state.installed = installed;
306 state.stopped = stopped;
307 state.notLaunched = notLaunched;
Amith Yamasani655d0e22013-06-12 14:19:10 -0700308 state.blocked = blocked;
Dianne Hackborn3fa3c28a2013-03-26 16:15:41 -0700309 state.lastDisableAppCaller = lastDisableAppCaller;
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700310 state.enabledComponents = enabledComponents;
311 state.disabledComponents = disabledComponents;
Kenny Guyc13053b2014-05-29 14:17:17 +0100312 state.blockUninstall = blockUninstall;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700313 }
314
315 HashSet<String> getEnabledComponents(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700316 return readUserState(userId).enabledComponents;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700317 }
318
319 HashSet<String> getDisabledComponents(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700320 return readUserState(userId).disabledComponents;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700321 }
322
323 void setEnabledComponents(HashSet<String> components, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700324 modifyUserState(userId).enabledComponents = components;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700325 }
326
327 void setDisabledComponents(HashSet<String> components, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700328 modifyUserState(userId).disabledComponents = components;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700329 }
330
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700331 void setEnabledComponentsCopy(HashSet<String> components, int userId) {
332 modifyUserState(userId).enabledComponents = components != null
333 ? new HashSet<String>(components) : null;
334 }
335
336 void setDisabledComponentsCopy(HashSet<String> components, int userId) {
337 modifyUserState(userId).disabledComponents = components != null
338 ? new HashSet<String>(components) : null;
339 }
340
341 PackageUserState modifyUserStateComponents(int userId, boolean disabled, boolean enabled) {
342 PackageUserState state = modifyUserState(userId);
343 if (disabled && state.disabledComponents == null) {
344 state.disabledComponents = new HashSet<String>(1);
Amith Yamasani483f3b02012-03-13 16:08:00 -0700345 }
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700346 if (enabled && state.enabledComponents == null) {
347 state.enabledComponents = new HashSet<String>(1);
348 }
349 return state;
Amith Yamasani483f3b02012-03-13 16:08:00 -0700350 }
351
352 void addDisabledComponent(String componentClassName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700353 modifyUserStateComponents(userId, true, false).disabledComponents.add(componentClassName);
Amith Yamasani483f3b02012-03-13 16:08:00 -0700354 }
355
356 void addEnabledComponent(String componentClassName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700357 modifyUserStateComponents(userId, false, true).enabledComponents.add(componentClassName);
Amith Yamasani483f3b02012-03-13 16:08:00 -0700358 }
359
360 boolean enableComponentLPw(String componentClassName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700361 PackageUserState state = modifyUserStateComponents(userId, false, true);
362 boolean changed = state.disabledComponents != null
363 ? state.disabledComponents.remove(componentClassName) : false;
364 changed |= state.enabledComponents.add(componentClassName);
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700365 return changed;
366 }
367
Amith Yamasani483f3b02012-03-13 16:08:00 -0700368 boolean disableComponentLPw(String componentClassName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700369 PackageUserState state = modifyUserStateComponents(userId, true, false);
370 boolean changed = state.enabledComponents != null
371 ? state.enabledComponents.remove(componentClassName) : false;
372 changed |= state.disabledComponents.add(componentClassName);
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700373 return changed;
374 }
375
Amith Yamasani483f3b02012-03-13 16:08:00 -0700376 boolean restoreComponentLPw(String componentClassName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700377 PackageUserState state = modifyUserStateComponents(userId, true, true);
378 boolean changed = state.disabledComponents != null
379 ? state.disabledComponents.remove(componentClassName) : false;
380 changed |= state.enabledComponents != null
381 ? state.enabledComponents.remove(componentClassName) : false;
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700382 return changed;
383 }
384
Amith Yamasani483f3b02012-03-13 16:08:00 -0700385 int getCurrentEnabledStateLPr(String componentName, int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700386 PackageUserState state = readUserState(userId);
387 if (state.enabledComponents != null && state.enabledComponents.contains(componentName)) {
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700388 return COMPONENT_ENABLED_STATE_ENABLED;
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700389 } else if (state.disabledComponents != null
390 && state.disabledComponents.contains(componentName)) {
Kenny Rootcf0b38c2011-03-22 14:17:59 -0700391 return COMPONENT_ENABLED_STATE_DISABLED;
392 } else {
393 return COMPONENT_ENABLED_STATE_DEFAULT;
394 }
395 }
Amith Yamasani13593602012-03-22 16:16:17 -0700396
397 void removeUser(int userId) {
Dianne Hackborn7767eac2012-08-23 18:25:40 -0700398 userState.delete(userId);
Amith Yamasani13593602012-03-22 16:16:17 -0700399 }
Amith Yamasani483f3b02012-03-13 16:08:00 -0700400}