Merge commit 'ab86fc91f5b54b8b730c0f594f04bbfb4c41697a' into kraken * commit 'ab86fc91f5b54b8b730c0f594f04bbfb4c41697a': Package manager optimizations.
This commit is contained in:
@@ -44268,6 +44268,19 @@
|
|||||||
<parameter name="info" type="android.content.pm.PermissionInfo">
|
<parameter name="info" type="android.content.pm.PermissionInfo">
|
||||||
</parameter>
|
</parameter>
|
||||||
</method>
|
</method>
|
||||||
|
<method name="addPermissionAsync"
|
||||||
|
return="boolean"
|
||||||
|
abstract="true"
|
||||||
|
native="false"
|
||||||
|
synchronized="false"
|
||||||
|
static="false"
|
||||||
|
final="false"
|
||||||
|
deprecated="not deprecated"
|
||||||
|
visibility="public"
|
||||||
|
>
|
||||||
|
<parameter name="info" type="android.content.pm.PermissionInfo">
|
||||||
|
</parameter>
|
||||||
|
</method>
|
||||||
<method name="addPreferredActivity"
|
<method name="addPreferredActivity"
|
||||||
return="void"
|
return="void"
|
||||||
abstract="true"
|
abstract="true"
|
||||||
@@ -148793,6 +148806,19 @@
|
|||||||
<parameter name="info" type="android.content.pm.PermissionInfo">
|
<parameter name="info" type="android.content.pm.PermissionInfo">
|
||||||
</parameter>
|
</parameter>
|
||||||
</method>
|
</method>
|
||||||
|
<method name="addPermissionAsync"
|
||||||
|
return="boolean"
|
||||||
|
abstract="false"
|
||||||
|
native="false"
|
||||||
|
synchronized="false"
|
||||||
|
static="false"
|
||||||
|
final="false"
|
||||||
|
deprecated="not deprecated"
|
||||||
|
visibility="public"
|
||||||
|
>
|
||||||
|
<parameter name="info" type="android.content.pm.PermissionInfo">
|
||||||
|
</parameter>
|
||||||
|
</method>
|
||||||
<method name="addPreferredActivity"
|
<method name="addPreferredActivity"
|
||||||
return="void"
|
return="void"
|
||||||
abstract="false"
|
abstract="false"
|
||||||
|
|||||||
@@ -1852,6 +1852,15 @@ class ContextImpl extends Context {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean addPermissionAsync(PermissionInfo info) {
|
||||||
|
try {
|
||||||
|
return mPM.addPermissionAsync(info);
|
||||||
|
} catch (RemoteException e) {
|
||||||
|
throw new RuntimeException("Package manager has died", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void removePermission(String name) {
|
public void removePermission(String name) {
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -314,4 +314,6 @@ interface IPackageManager {
|
|||||||
String nextPackageToClean(String lastPackage);
|
String nextPackageToClean(String lastPackage);
|
||||||
|
|
||||||
void movePackage(String packageName, IPackageMoveObserver observer, int flags);
|
void movePackage(String packageName, IPackageMoveObserver observer, int flags);
|
||||||
|
|
||||||
|
boolean addPermissionAsync(in PermissionInfo info);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1119,6 +1119,15 @@ public abstract class PackageManager {
|
|||||||
*/
|
*/
|
||||||
public abstract boolean addPermission(PermissionInfo info);
|
public abstract boolean addPermission(PermissionInfo info);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Like {@link #addPermission(PermissionInfo)} but asynchronously
|
||||||
|
* persists the package manager state after returning from the call,
|
||||||
|
* allowing it to return quicker and batch a series of adds at the
|
||||||
|
* expense of no guarantee the added permission will be retained if
|
||||||
|
* the device is rebooted before it is written.
|
||||||
|
*/
|
||||||
|
public abstract boolean addPermissionAsync(PermissionInfo info);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Removes a permission that was previously added with
|
* Removes a permission that was previously added with
|
||||||
* {@link #addPermission(PermissionInfo)}. The same ownership rules apply
|
* {@link #addPermission(PermissionInfo)}. The same ownership rules apply
|
||||||
|
|||||||
@@ -344,6 +344,9 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
static final int MCS_RECONNECT = 10;
|
static final int MCS_RECONNECT = 10;
|
||||||
static final int MCS_GIVE_UP = 11;
|
static final int MCS_GIVE_UP = 11;
|
||||||
static final int UPDATED_MEDIA_STATUS = 12;
|
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
|
// Delay time in millisecs
|
||||||
static final int BROADCAST_DELAY = 10 * 1000;
|
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" +
|
if (DEBUG_SD_INSTALL) Log.i(TAG, "Trying to bind to" +
|
||||||
" DefaultContainerService");
|
" DefaultContainerService");
|
||||||
Intent service = new Intent().setComponent(DEFAULT_CONTAINER_COMPONENT);
|
Intent service = new Intent().setComponent(DEFAULT_CONTAINER_COMPONENT);
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT);
|
||||||
if (mContext.bindService(service, mDefContainerConn,
|
if (mContext.bindService(service, mDefContainerConn,
|
||||||
Context.BIND_AUTO_CREATE)) {
|
Context.BIND_AUTO_CREATE)) {
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
mBound = true;
|
mBound = true;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void disconnectService() {
|
private void disconnectService() {
|
||||||
mContainerService = null;
|
mContainerService = null;
|
||||||
mBound = false;
|
mBound = false;
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT);
|
||||||
mContext.unbindService(mDefContainerConn);
|
mContext.unbindService(mDefContainerConn);
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
}
|
}
|
||||||
|
|
||||||
PackageHandler(Looper looper) {
|
PackageHandler(Looper looper) {
|
||||||
super(looper);
|
super(looper);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void handleMessage(Message msg) {
|
public void handleMessage(Message msg) {
|
||||||
|
try {
|
||||||
|
doHandleMessage(msg);
|
||||||
|
} finally {
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void doHandleMessage(Message msg) {
|
||||||
switch (msg.what) {
|
switch (msg.what) {
|
||||||
case INIT_COPY: {
|
case INIT_COPY: {
|
||||||
if (DEBUG_SD_INSTALL) Log.i(TAG, "init_copy");
|
if (DEBUG_SD_INSTALL) Log.i(TAG, "init_copy");
|
||||||
@@ -505,6 +522,7 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
ArrayList components[];
|
ArrayList components[];
|
||||||
int size = 0;
|
int size = 0;
|
||||||
int uids[];
|
int uids[];
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT);
|
||||||
synchronized (mPackages) {
|
synchronized (mPackages) {
|
||||||
if (mPendingBroadcasts == null) {
|
if (mPendingBroadcasts == null) {
|
||||||
return;
|
return;
|
||||||
@@ -536,15 +554,18 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
sendPackageChangedBroadcast(packages[i], true,
|
sendPackageChangedBroadcast(packages[i], true,
|
||||||
(ArrayList<String>)components[i], uids[i]);
|
(ArrayList<String>)components[i], uids[i]);
|
||||||
}
|
}
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case START_CLEANING_PACKAGE: {
|
case START_CLEANING_PACKAGE: {
|
||||||
String packageName = (String)msg.obj;
|
String packageName = (String)msg.obj;
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_DEFAULT);
|
||||||
synchronized (mPackages) {
|
synchronized (mPackages) {
|
||||||
if (!mSettings.mPackagesToBeCleaned.contains(packageName)) {
|
if (!mSettings.mPackagesToBeCleaned.contains(packageName)) {
|
||||||
mSettings.mPackagesToBeCleaned.add(packageName);
|
mSettings.mPackagesToBeCleaned.add(packageName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
|
||||||
startCleaningPackages();
|
startCleaningPackages();
|
||||||
} break;
|
} break;
|
||||||
case POST_INSTALL: {
|
case POST_INSTALL: {
|
||||||
@@ -604,10 +625,24 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
Log.e(TAG, "MountService not running?");
|
Log.e(TAG, "MountService not running?");
|
||||||
}
|
}
|
||||||
} break;
|
} 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) {
|
static boolean installOnSd(int flags) {
|
||||||
if (((flags & PackageManager.INSTALL_FORWARD_LOCK) != 0) ||
|
if (((flags & PackageManager.INSTALL_FORWARD_LOCK) != 0) ||
|
||||||
((flags & PackageManager.INSTALL_INTERNAL) != 0)) {
|
((flags & PackageManager.INSTALL_INTERNAL) != 0)) {
|
||||||
@@ -1644,32 +1679,84 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
throw new SecurityException("No permission tree found for " + permName);
|
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) {
|
public boolean addPermission(PermissionInfo info) {
|
||||||
synchronized (mPackages) {
|
synchronized (mPackages) {
|
||||||
if (info.labelRes == 0 && info.nonLocalizedLabel == null) {
|
return addPermissionLocked(info, false);
|
||||||
throw new SecurityException("Label must be specified in permission");
|
}
|
||||||
}
|
}
|
||||||
BasePermission tree = checkPermissionTreeLP(info.name);
|
|
||||||
BasePermission bp = mSettings.mPermissions.get(info.name);
|
public boolean addPermissionAsync(PermissionInfo info) {
|
||||||
boolean added = bp == null;
|
synchronized (mPackages) {
|
||||||
if (added) {
|
return addPermissionLocked(info, true);
|
||||||
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;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -6477,7 +6564,7 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
filter.dump(new LogPrinter(Log.INFO, TAG), " ");
|
filter.dump(new LogPrinter(Log.INFO, TAG), " ");
|
||||||
mSettings.mPreferredActivities.addFilter(
|
mSettings.mPreferredActivities.addFilter(
|
||||||
new PreferredActivity(filter, match, set, activity));
|
new PreferredActivity(filter, match, set, activity));
|
||||||
mSettings.writeLP();
|
scheduleWriteSettingsLocked();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -6548,7 +6635,7 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (clearPackagePreferredActivitiesLP(packageName)) {
|
if (clearPackagePreferredActivitiesLP(packageName)) {
|
||||||
mSettings.writeLP();
|
scheduleWriteSettingsLocked();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -6637,18 +6724,28 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
}
|
}
|
||||||
if (className == null) {
|
if (className == null) {
|
||||||
// We're dealing with an application/package level state change
|
// We're dealing with an application/package level state change
|
||||||
|
if (pkgSetting.enabled == newState) {
|
||||||
|
// Nothing to do
|
||||||
|
return;
|
||||||
|
}
|
||||||
pkgSetting.enabled = newState;
|
pkgSetting.enabled = newState;
|
||||||
} else {
|
} else {
|
||||||
// We're dealing with a component level state change
|
// We're dealing with a component level state change
|
||||||
switch (newState) {
|
switch (newState) {
|
||||||
case COMPONENT_ENABLED_STATE_ENABLED:
|
case COMPONENT_ENABLED_STATE_ENABLED:
|
||||||
pkgSetting.enableComponentLP(className);
|
if (!pkgSetting.enableComponentLP(className)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case COMPONENT_ENABLED_STATE_DISABLED:
|
case COMPONENT_ENABLED_STATE_DISABLED:
|
||||||
pkgSetting.disableComponentLP(className);
|
if (!pkgSetting.disableComponentLP(className)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case COMPONENT_ENABLED_STATE_DEFAULT:
|
case COMPONENT_ENABLED_STATE_DEFAULT:
|
||||||
pkgSetting.restoreComponentLP(className);
|
if (!pkgSetting.restoreComponentLP(className)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
Slog.e(TAG, "Invalid new component state: " + newState);
|
Slog.e(TAG, "Invalid new component state: " + newState);
|
||||||
@@ -7644,19 +7741,22 @@ class PackageManagerService extends IPackageManager.Stub {
|
|||||||
installStatus = base.installStatus;
|
installStatus = base.installStatus;
|
||||||
}
|
}
|
||||||
|
|
||||||
void enableComponentLP(String componentClassName) {
|
boolean enableComponentLP(String componentClassName) {
|
||||||
disabledComponents.remove(componentClassName);
|
boolean changed = disabledComponents.remove(componentClassName);
|
||||||
enabledComponents.add(componentClassName);
|
changed |= enabledComponents.add(componentClassName);
|
||||||
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
void disableComponentLP(String componentClassName) {
|
boolean disableComponentLP(String componentClassName) {
|
||||||
enabledComponents.remove(componentClassName);
|
boolean changed = enabledComponents.remove(componentClassName);
|
||||||
disabledComponents.add(componentClassName);
|
changed |= disabledComponents.add(componentClassName);
|
||||||
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
void restoreComponentLP(String componentClassName) {
|
boolean restoreComponentLP(String componentClassName) {
|
||||||
enabledComponents.remove(componentClassName);
|
boolean changed = enabledComponents.remove(componentClassName);
|
||||||
disabledComponents.remove(componentClassName);
|
changed |= disabledComponents.remove(componentClassName);
|
||||||
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
int currentEnabledStateLP(String componentName) {
|
int currentEnabledStateLP(String componentName) {
|
||||||
|
|||||||
@@ -141,6 +141,11 @@ public class MockPackageManager extends PackageManager {
|
|||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean addPermissionAsync(PermissionInfo info) {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void removePermission(String name) {
|
public void removePermission(String name) {
|
||||||
throw new UnsupportedOperationException();
|
throw new UnsupportedOperationException();
|
||||||
|
|||||||
Reference in New Issue
Block a user