summaryrefslogtreecommitdiffstats
path: root/services/java
diff options
context:
space:
mode:
authorDianne Hackborn <hackbod@google.com>2011-05-27 16:45:31 -0700
committerDianne Hackborn <hackbod@google.com>2011-05-27 16:49:29 -0700
commit8ea5e1d79eb1f05ee7628b0d45ea8fc8eea5330d (patch)
treea676c6b0daf45a90b600d3268bb37e81f23a2275 /services/java
parentb96cbbd11c4590bec846212c33361e02293f18b5 (diff)
downloadframeworks_base-8ea5e1d79eb1f05ee7628b0d45ea8fc8eea5330d.zip
frameworks_base-8ea5e1d79eb1f05ee7628b0d45ea8fc8eea5330d.tar.gz
frameworks_base-8ea5e1d79eb1f05ee7628b0d45ea8fc8eea5330d.tar.bz2
Fix compat mode bugs when updating apps.
No longer accidentally puts an app into compatibility mode. Also various cleanup, freezing screen while switching between modes. Change-Id: Ic1b3958be7800189a93f68e9dee3c5adfc45fe57
Diffstat (limited to 'services/java')
-rw-r--r--services/java/com/android/server/am/ActivityManagerService.java16
-rw-r--r--services/java/com/android/server/am/ActivityRecord.java3
-rw-r--r--services/java/com/android/server/am/ActivityStack.java4
-rw-r--r--services/java/com/android/server/am/CompatModePackages.java83
-rw-r--r--services/java/com/android/server/am/ProcessRecord.java2
5 files changed, 76 insertions, 32 deletions
diff --git a/services/java/com/android/server/am/ActivityManagerService.java b/services/java/com/android/server/am/ActivityManagerService.java
index 65b3258..080cbda 100644
--- a/services/java/com/android/server/am/ActivityManagerService.java
+++ b/services/java/com/android/server/am/ActivityManagerService.java
@@ -3642,12 +3642,12 @@ public final class ActivityManagerService extends ActivityManagerNative
+ processName + " with config " + mConfiguration);
ApplicationInfo appInfo = app.instrumentationInfo != null
? app.instrumentationInfo : app.info;
+ app.compat = compatibilityInfoForPackageLocked(appInfo);
thread.bindApplication(processName, appInfo, providers,
app.instrumentationClass, app.instrumentationProfileFile,
app.instrumentationArguments, app.instrumentationWatcher, testMode,
isRestrictedBackupMode || !normalMode,
- mConfiguration, compatibilityInfoForPackageLocked(appInfo),
- getCommonServicesLocked(),
+ mConfiguration, app.compat, getCommonServicesLocked(),
mCoreSettingsObserver.getCoreSettingsLocked());
updateLruProcessLocked(app, false, true);
app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis();
@@ -10977,13 +10977,11 @@ public final class ActivityManagerService extends ActivityManagerNative
// Special case for adding a package: by default turn on compatibility
// mode.
} else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) {
- if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) {
- Uri data = intent.getData();
- String ssp;
- if (data != null && (ssp=data.getSchemeSpecificPart()) != null) {
- mCompatModePackages.setPackageScreenCompatModeLocked(ssp,
- ActivityManager.COMPAT_MODE_ENABLED);
- }
+ Uri data = intent.getData();
+ String ssp;
+ if (data != null && (ssp=data.getSchemeSpecificPart()) != null) {
+ mCompatModePackages.handlePackageAddedLocked(ssp,
+ intent.getBooleanExtra(Intent.EXTRA_REPLACING, false));
}
}
diff --git a/services/java/com/android/server/am/ActivityRecord.java b/services/java/com/android/server/am/ActivityRecord.java
index d27cbda..33c12f4 100644
--- a/services/java/com/android/server/am/ActivityRecord.java
+++ b/services/java/com/android/server/am/ActivityRecord.java
@@ -24,6 +24,7 @@ import android.content.ComponentName;
import android.content.Intent;
import android.content.pm.ActivityInfo;
import android.content.pm.ApplicationInfo;
+import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.graphics.Bitmap;
import android.os.Build;
@@ -78,6 +79,7 @@ class ActivityRecord extends IApplicationToken.Stub {
long startTime; // last time this activity was started
long cpuTimeAtResume; // the cpu time of host process at the time of resuming activity
Configuration configuration; // configuration activity was last running in
+ CompatibilityInfo compat;// last used compatibility mode
ActivityRecord resultTo; // who started this entry, so will get our reply
final String resultWho; // additional identifier for use by resultTo.
final int requestCode; // code given by requester (resultTo)
@@ -137,6 +139,7 @@ class ActivityRecord extends IApplicationToken.Stub {
pw.print(" componentSpecified="); pw.print(componentSpecified);
pw.print(" isHomeActivity="); pw.println(isHomeActivity);
pw.print(prefix); pw.print("config="); pw.println(configuration);
+ pw.print(prefix); pw.print("compat="); pw.println(compat);
if (resultTo != null || resultWho != null) {
pw.print(prefix); pw.print("resultTo="); pw.print(resultTo);
pw.print(" resultWho="); pw.print(resultWho);
diff --git a/services/java/com/android/server/am/ActivityStack.java b/services/java/com/android/server/am/ActivityStack.java
index a704f88..65ea4f4 100644
--- a/services/java/com/android/server/am/ActivityStack.java
+++ b/services/java/com/android/server/am/ActivityStack.java
@@ -546,10 +546,10 @@ public class ActivityStack {
r.sleeping = false;
r.forceNewConfig = false;
showAskCompatModeDialogLocked(r);
+ r.compat = mService.compatibilityInfoForPackageLocked(r.info.applicationInfo);
app.thread.scheduleLaunchActivity(new Intent(r.intent), r,
System.identityHashCode(r),
- r.info, mService.compatibilityInfoForPackageLocked(r.info.applicationInfo),
- r.icicle, results, newIntents, !andResume,
+ r.info, r.compat, r.icicle, results, newIntents, !andResume,
mService.isNextTransitionForward());
if ((app.info.flags&ApplicationInfo.FLAG_CANT_SAVE_STATE) != 0) {
diff --git a/services/java/com/android/server/am/CompatModePackages.java b/services/java/com/android/server/am/CompatModePackages.java
index 221b59b..8949f48 100644
--- a/services/java/com/android/server/am/CompatModePackages.java
+++ b/services/java/com/android/server/am/CompatModePackages.java
@@ -17,6 +17,7 @@ import com.android.internal.util.FastXmlSerializer;
import android.app.ActivityManager;
import android.app.AppGlobals;
+import android.content.pm.ActivityInfo;
import android.content.pm.ApplicationInfo;
import android.content.pm.IPackageManager;
import android.content.res.CompatibilityInfo;
@@ -117,6 +118,37 @@ public class CompatModePackages {
return flags != null ? flags : 0;
}
+ public void handlePackageAddedLocked(String packageName, boolean updated) {
+ ApplicationInfo ai = null;
+ try {
+ ai = AppGlobals.getPackageManager().getApplicationInfo(packageName, 0);
+ } catch (RemoteException e) {
+ }
+ if (ai == null) {
+ return;
+ }
+ CompatibilityInfo ci = compatibilityInfoForPackageLocked(ai);
+ final boolean mayCompat = !ci.alwaysSupportsScreen()
+ && !ci.neverSupportsScreen();
+
+ if (!updated) {
+ // First time -- if the app may run in compat mode, enable that
+ // by default.
+ if (mayCompat) {
+ setPackageScreenCompatModeLocked(ai, ActivityManager.COMPAT_MODE_ENABLED);
+ }
+ } else {
+ // Update -- if the app no longer can run in compat mode, clear
+ // any current settings for it.
+ if (!mayCompat && mPackages.containsKey(packageName)) {
+ mPackages.remove(packageName);
+ mHandler.removeMessages(MSG_WRITE);
+ Message msg = mHandler.obtainMessage(MSG_WRITE);
+ mHandler.sendMessageDelayed(msg, 10000);
+ }
+ }
+ }
+
public CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) {
return new CompatibilityInfo(ai, mService.mConfiguration.screenLayout,
mService.mConfiguration.smallestScreenWidthDp,
@@ -242,28 +274,47 @@ public class CompatModePackages {
newFlags &= ~COMPAT_FLAG_ENABLED;
}
+ CompatibilityInfo ci = compatibilityInfoForPackageLocked(ai);
+ if (ci.alwaysSupportsScreen()) {
+ Slog.w(TAG, "Ignoring compat mode change of " + packageName
+ + "; compatibility never needed");
+ newFlags = 0;
+ }
+ if (ci.neverSupportsScreen()) {
+ Slog.w(TAG, "Ignoring compat mode change of " + packageName
+ + "; compatibility always needed");
+ newFlags = 0;
+ }
+
if (newFlags != curFlags) {
if (newFlags != 0) {
mPackages.put(packageName, newFlags);
} else {
mPackages.remove(packageName);
}
- CompatibilityInfo ci = compatibilityInfoForPackageLocked(ai);
- if (ci.alwaysSupportsScreen()) {
- Slog.w(TAG, "Ignoring compat mode change of " + packageName
- + "; compatibility never needed");
- return;
- }
- if (ci.neverSupportsScreen()) {
- Slog.w(TAG, "Ignoring compat mode change of " + packageName
- + "; compatibility always needed");
- return;
- }
+
+ // Need to get compatibility info in new state.
+ ci = compatibilityInfoForPackageLocked(ai);
mHandler.removeMessages(MSG_WRITE);
Message msg = mHandler.obtainMessage(MSG_WRITE);
mHandler.sendMessageDelayed(msg, 10000);
+ ActivityRecord starting = mService.mMainStack.topRunningActivityLocked(null);
+
+ // All activities that came from the package must be
+ // restarted as if there was a config change.
+ for (int i=mService.mMainStack.mHistory.size()-1; i>=0; i--) {
+ ActivityRecord a = (ActivityRecord)mService.mMainStack.mHistory.get(i);
+ if (a.info.packageName.equals(packageName)) {
+ a.forceNewConfig = true;
+ if (starting != null && a == starting && a.visible) {
+ a.startFreezingScreenLocked(starting.app,
+ ActivityInfo.CONFIG_SCREEN_LAYOUT);
+ }
+ }
+ }
+
// Tell all processes that loaded this package about the change.
for (int i=mService.mLruProcesses.size()-1; i>=0; i--) {
ProcessRecord app = mService.mLruProcesses.get(i);
@@ -280,16 +331,6 @@ public class CompatModePackages {
}
}
- // All activities that came from the packge must be
- // restarted as if there was a config change.
- for (int i=mService.mMainStack.mHistory.size()-1; i>=0; i--) {
- ActivityRecord a = (ActivityRecord)mService.mMainStack.mHistory.get(i);
- if (a.info.packageName.equals(packageName)) {
- a.forceNewConfig = true;
- }
- }
-
- ActivityRecord starting = mService.mMainStack.topRunningActivityLocked(null);
if (starting != null) {
mService.mMainStack.ensureActivityConfigurationLocked(starting, 0);
// And we need to make sure at this point that all other activities
diff --git a/services/java/com/android/server/am/ProcessRecord.java b/services/java/com/android/server/am/ProcessRecord.java
index a63ffae..5465e37 100644
--- a/services/java/com/android/server/am/ProcessRecord.java
+++ b/services/java/com/android/server/am/ProcessRecord.java
@@ -69,6 +69,7 @@ class ProcessRecord {
IBinder forcingToForeground;// Token that is forcing this process to be foreground
int adjSeq; // Sequence id for identifying oom_adj assignment cycles
int lruSeq; // Sequence id for identifying LRU update cycles
+ CompatibilityInfo compat; // last used compatibility mode
ComponentName instrumentationClass;// class installed to instrument app
ApplicationInfo instrumentationInfo; // the application being instrumented
String instrumentationProfileFile; // where to save profiling
@@ -145,6 +146,7 @@ class ProcessRecord {
pw.print(" publicDir="); pw.print(info.publicSourceDir);
pw.print(" data="); pw.println(info.dataDir);
pw.print(prefix); pw.print("packageList="); pw.println(pkgList);
+ pw.print(prefix); pw.print("compat="); pw.println(compat);
if (instrumentationClass != null || instrumentationProfileFile != null
|| instrumentationArguments != null) {
pw.print(prefix); pw.print("instrumentationClass=");