diff options
author | Dianne Hackborn <hackbod@google.com> | 2010-03-30 13:42:50 -0700 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2010-03-30 13:42:50 -0700 |
commit | b4915265a09361c375e792781ead5bfec6c797d9 (patch) | |
tree | 4b3345896a4637e4cd196d42e294c1fb33ba99dd /services/java/com/android/server/PackageManagerService.java | |
parent | 91ff1dbf7f93c2cb3d618f36fad66122aadbe17b (diff) | |
parent | ab86fc91f5b54b8b730c0f594f04bbfb4c41697a (diff) | |
download | frameworks_base-b4915265a09361c375e792781ead5bfec6c797d9.zip frameworks_base-b4915265a09361c375e792781ead5bfec6c797d9.tar.gz frameworks_base-b4915265a09361c375e792781ead5bfec6c797d9.tar.bz2 |
am ab86fc91: am de2722af: Merge "Package manager optimizations." into froyo
Merge commit 'ab86fc91f5b54b8b730c0f594f04bbfb4c41697a' into kraken
* commit 'ab86fc91f5b54b8b730c0f594f04bbfb4c41697a':
Package manager optimizations.
Diffstat (limited to 'services/java/com/android/server/PackageManagerService.java')
-rw-r--r-- | services/java/com/android/server/PackageManagerService.java | 176 |
1 files changed, 138 insertions, 38 deletions
diff --git a/services/java/com/android/server/PackageManagerService.java b/services/java/com/android/server/PackageManagerService.java index 33a824b..6f16ee7 100644 --- a/services/java/com/android/server/PackageManagerService.java +++ b/services/java/com/android/server/PackageManagerService.java @@ -344,6 +344,9 @@ class PackageManagerService extends IPackageManager.Stub { static final int MCS_RECONNECT = 10; static final int MCS_GIVE_UP = 11; static final int UPDATED_MEDIA_STATUS = 12; + static final int WRITE_SETTINGS = 13; + + static final int WRITE_SETTINGS_DELAY = 10*1000; // 10 seconds // Delay time in millisecs static final int BROADCAST_DELAY = 10 * 1000; @@ -385,24 +388,38 @@ class PackageManagerService extends IPackageManager.Stub { if (DEBUG_SD_INSTALL) Log.i(TAG, "Trying to bind to" + " DefaultContainerService"); Intent service = new Intent().setComponent(DEFAULT_CONTAINER_COMPONENT); + Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); if (mContext.bindService(service, mDefContainerConn, Context.BIND_AUTO_CREATE)) { + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); mBound = true; return true; } + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); return false; } private void disconnectService() { mContainerService = null; mBound = false; + Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); mContext.unbindService(mDefContainerConn); + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); } PackageHandler(Looper looper) { super(looper); } + public void handleMessage(Message msg) { + try { + doHandleMessage(msg); + } finally { + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); + } + } + + void doHandleMessage(Message msg) { switch (msg.what) { case INIT_COPY: { if (DEBUG_SD_INSTALL) Log.i(TAG, "init_copy"); @@ -505,6 +522,7 @@ class PackageManagerService extends IPackageManager.Stub { ArrayList components[]; int size = 0; int uids[]; + Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); synchronized (mPackages) { if (mPendingBroadcasts == null) { return; @@ -536,15 +554,18 @@ class PackageManagerService extends IPackageManager.Stub { sendPackageChangedBroadcast(packages[i], true, (ArrayList<String>)components[i], uids[i]); } + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); break; } case START_CLEANING_PACKAGE: { String packageName = (String)msg.obj; + Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); synchronized (mPackages) { if (!mSettings.mPackagesToBeCleaned.contains(packageName)) { mSettings.mPackagesToBeCleaned.add(packageName); } } + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); startCleaningPackages(); } break; case POST_INSTALL: { @@ -604,10 +625,24 @@ class PackageManagerService extends IPackageManager.Stub { Log.e(TAG, "MountService not running?"); } } break; + case WRITE_SETTINGS: { + Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT); + synchronized (mPackages) { + removeMessages(WRITE_SETTINGS); + mSettings.writeLP(); + } + Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND); + } break; } } } + void scheduleWriteSettingsLocked() { + if (!mHandler.hasMessages(WRITE_SETTINGS)) { + mHandler.sendEmptyMessageDelayed(WRITE_SETTINGS, WRITE_SETTINGS_DELAY); + } + } + static boolean installOnSd(int flags) { if (((flags & PackageManager.INSTALL_FORWARD_LOCK) != 0) || ((flags & PackageManager.INSTALL_INTERNAL) != 0)) { @@ -1644,32 +1679,84 @@ class PackageManagerService extends IPackageManager.Stub { throw new SecurityException("No permission tree found for " + permName); } + static boolean compareStrings(CharSequence s1, CharSequence s2) { + if (s1 == null) { + return s2 == null; + } + if (s2 == null) { + return false; + } + if (s1.getClass() != s2.getClass()) { + return false; + } + return s1.equals(s2); + } + + static boolean comparePermissionInfos(PermissionInfo pi1, PermissionInfo pi2) { + if (pi1.icon != pi2.icon) return false; + if (pi1.protectionLevel != pi2.protectionLevel) return false; + if (!compareStrings(pi1.name, pi2.name)) return false; + if (!compareStrings(pi1.nonLocalizedLabel, pi2.nonLocalizedLabel)) return false; + // We'll take care of setting this one. + if (!compareStrings(pi1.packageName, pi2.packageName)) return false; + // These are not currently stored in settings. + //if (!compareStrings(pi1.group, pi2.group)) return false; + //if (!compareStrings(pi1.nonLocalizedDescription, pi2.nonLocalizedDescription)) return false; + //if (pi1.labelRes != pi2.labelRes) return false; + //if (pi1.descriptionRes != pi2.descriptionRes) return false; + return true; + } + + boolean addPermissionLocked(PermissionInfo info, boolean async) { + if (info.labelRes == 0 && info.nonLocalizedLabel == null) { + throw new SecurityException("Label must be specified in permission"); + } + BasePermission tree = checkPermissionTreeLP(info.name); + BasePermission bp = mSettings.mPermissions.get(info.name); + boolean added = bp == null; + boolean changed = true; + if (added) { + bp = new BasePermission(info.name, tree.sourcePackage, + BasePermission.TYPE_DYNAMIC); + } else if (bp.type != BasePermission.TYPE_DYNAMIC) { + throw new SecurityException( + "Not allowed to modify non-dynamic permission " + + info.name); + } else { + if (bp.protectionLevel == info.protectionLevel + && bp.perm.owner.equals(tree.perm.owner) + && bp.uid == tree.uid + && comparePermissionInfos(bp.perm.info, info)) { + changed = false; + } + } + bp.protectionLevel = info.protectionLevel; + bp.perm = new PackageParser.Permission(tree.perm.owner, + new PermissionInfo(info)); + bp.perm.info.packageName = tree.perm.info.packageName; + bp.uid = tree.uid; + if (added) { + mSettings.mPermissions.put(info.name, bp); + } + if (changed) { + if (!async) { + mSettings.writeLP(); + } else { + scheduleWriteSettingsLocked(); + } + } + return added; + } + public boolean addPermission(PermissionInfo info) { synchronized (mPackages) { - if (info.labelRes == 0 && info.nonLocalizedLabel == null) { - throw new SecurityException("Label must be specified in permission"); - } - BasePermission tree = checkPermissionTreeLP(info.name); - BasePermission bp = mSettings.mPermissions.get(info.name); - boolean added = bp == null; - if (added) { - bp = new BasePermission(info.name, tree.sourcePackage, - BasePermission.TYPE_DYNAMIC); - } else if (bp.type != BasePermission.TYPE_DYNAMIC) { - throw new SecurityException( - "Not allowed to modify non-dynamic permission " - + info.name); - } - bp.protectionLevel = info.protectionLevel; - bp.perm = new PackageParser.Permission(tree.perm.owner, - new PermissionInfo(info)); - bp.perm.info.packageName = tree.perm.info.packageName; - bp.uid = tree.uid; - if (added) { - mSettings.mPermissions.put(info.name, bp); - } - mSettings.writeLP(); - return added; + return addPermissionLocked(info, false); + } + } + + public boolean addPermissionAsync(PermissionInfo info) { + synchronized (mPackages) { + return addPermissionLocked(info, true); } } @@ -6477,7 +6564,7 @@ class PackageManagerService extends IPackageManager.Stub { filter.dump(new LogPrinter(Log.INFO, TAG), " "); mSettings.mPreferredActivities.addFilter( new PreferredActivity(filter, match, set, activity)); - mSettings.writeLP(); + scheduleWriteSettingsLocked(); } } @@ -6548,7 +6635,7 @@ class PackageManagerService extends IPackageManager.Stub { } if (clearPackagePreferredActivitiesLP(packageName)) { - mSettings.writeLP(); + scheduleWriteSettingsLocked(); } } } @@ -6637,18 +6724,28 @@ class PackageManagerService extends IPackageManager.Stub { } if (className == null) { // We're dealing with an application/package level state change + if (pkgSetting.enabled == newState) { + // Nothing to do + return; + } pkgSetting.enabled = newState; } else { // We're dealing with a component level state change switch (newState) { case COMPONENT_ENABLED_STATE_ENABLED: - pkgSetting.enableComponentLP(className); + if (!pkgSetting.enableComponentLP(className)) { + return; + } break; case COMPONENT_ENABLED_STATE_DISABLED: - pkgSetting.disableComponentLP(className); + if (!pkgSetting.disableComponentLP(className)) { + return; + } break; case COMPONENT_ENABLED_STATE_DEFAULT: - pkgSetting.restoreComponentLP(className); + if (!pkgSetting.restoreComponentLP(className)) { + return; + } break; default: Slog.e(TAG, "Invalid new component state: " + newState); @@ -7644,19 +7741,22 @@ class PackageManagerService extends IPackageManager.Stub { installStatus = base.installStatus; } - void enableComponentLP(String componentClassName) { - disabledComponents.remove(componentClassName); - enabledComponents.add(componentClassName); + boolean enableComponentLP(String componentClassName) { + boolean changed = disabledComponents.remove(componentClassName); + changed |= enabledComponents.add(componentClassName); + return changed; } - void disableComponentLP(String componentClassName) { - enabledComponents.remove(componentClassName); - disabledComponents.add(componentClassName); + boolean disableComponentLP(String componentClassName) { + boolean changed = enabledComponents.remove(componentClassName); + changed |= disabledComponents.add(componentClassName); + return changed; } - void restoreComponentLP(String componentClassName) { - enabledComponents.remove(componentClassName); - disabledComponents.remove(componentClassName); + boolean restoreComponentLP(String componentClassName) { + boolean changed = enabledComponents.remove(componentClassName); + changed |= disabledComponents.remove(componentClassName); + return changed; } int currentEnabledStateLP(String componentName) { |