summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--core/java/android/app/ActivityThread.java18
-rw-r--r--core/java/android/app/LoadedApk.java6
-rw-r--r--core/java/android/content/res/CompatibilityInfo.java15
-rw-r--r--core/java/android/content/res/Configuration.java6
-rwxr-xr-xcore/java/android/content/res/Resources.java14
-rw-r--r--core/java/android/view/IWindowManager.aidl3
-rw-r--r--core/java/android/view/WindowManagerPolicy.java3
-rwxr-xr-xpolicy/src/com/android/internal/policy/impl/PhoneWindowManager.java13
-rw-r--r--services/java/com/android/server/AppWidgetService.java1
-rw-r--r--services/java/com/android/server/am/ActivityManagerService.java9
-rw-r--r--services/java/com/android/server/am/ActivityStack.java8
-rw-r--r--services/java/com/android/server/am/CompatModePackages.java4
-rw-r--r--services/java/com/android/server/wm/StartingData.java7
-rw-r--r--services/java/com/android/server/wm/WindowManagerService.java17
-rw-r--r--tests/permission/src/com/android/framework/permission/tests/WindowManagerPermissionTests.java2
15 files changed, 86 insertions, 40 deletions
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index d30010a..063665b 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -172,6 +172,11 @@ public final class ActivityThread {
// These can be accessed by multiple threads; mPackages is the lock.
// XXX For now we keep around information about all packages we have
// seen, not removing entries from this map.
+ // NOTE: The activity manager in its process needs to call in to
+ // ActivityThread to do things like update resource configurations,
+ // which means this lock gets held while the activity manager holds its
+ // own lock. Thus you MUST NEVER call back into the activity manager
+ // or anything that depends on it while holding this lock.
final HashMap<String, WeakReference<LoadedApk>> mPackages
= new HashMap<String, WeakReference<LoadedApk>>();
final HashMap<String, WeakReference<LoadedApk>> mResourcePackages
@@ -1480,7 +1485,7 @@ public final class ActivityThread {
}
public Configuration getConfiguration() {
- return mConfiguration;
+ return mResConfiguration;
}
public boolean isProfiling() {
@@ -1525,7 +1530,7 @@ public final class ActivityThread {
synchronized (this) {
ContextImpl context = getSystemContext();
context.init(new LoadedApk(this, "android", context, info,
- new CompatibilityInfo(info, 0, 0, false)), null, this);
+ CompatibilityInfo.DEFAULT_COMPATIBILITY_INFO), null, this);
}
}
@@ -3274,6 +3279,12 @@ public final class ActivityThread {
}
}
+ public final void applyConfigurationToResources(Configuration config) {
+ synchronized (mPackages) {
+ applyConfigurationToResourcesLocked(config, null);
+ }
+ }
+
final boolean applyConfigurationToResourcesLocked(Configuration config,
CompatibilityInfo compat) {
if (mResConfiguration == null) {
@@ -3492,8 +3503,7 @@ public final class ActivityThread {
* reflect configuration changes. The configuration object passed
* in AppBindData can be safely assumed to be up to date
*/
- Resources.getSystem().updateConfiguration(mConfiguration,
- Resources.getSystem().getDisplayMetrics(), data.compatInfo);
+ applyConfigurationToResourcesLocked(data.config, data.compatInfo);
data.info = getPackageInfoNoCheck(data.appInfo, data.compatInfo);
diff --git a/core/java/android/app/LoadedApk.java b/core/java/android/app/LoadedApk.java
index 5307696..6287d33 100644
--- a/core/java/android/app/LoadedApk.java
+++ b/core/java/android/app/LoadedApk.java
@@ -98,6 +98,12 @@ final class LoadedApk {
return mApplication;
}
+ /**
+ * Create information about a new .apk
+ *
+ * NOTE: This constructor is called with ActivityThread's lock held,
+ * so MUST NOT call back out to the activity manager.
+ */
public LoadedApk(ActivityThread activityThread, ApplicationInfo aInfo,
CompatibilityInfo compatInfo,
ActivityThread mainThread, ClassLoader baseLoader,
diff --git a/core/java/android/content/res/CompatibilityInfo.java b/core/java/android/content/res/CompatibilityInfo.java
index e42caca..b7b6de6 100644
--- a/core/java/android/content/res/CompatibilityInfo.java
+++ b/core/java/android/content/res/CompatibilityInfo.java
@@ -243,11 +243,11 @@ public class CompatibilityInfo implements Parcelable {
}
public boolean neverSupportsScreen() {
- return (mCompatibilityFlags&NEVER_NEEDS_COMPAT) != 0;
+ return (mCompatibilityFlags&ALWAYS_NEEDS_COMPAT) != 0;
}
public boolean alwaysSupportsScreen() {
- return (mCompatibilityFlags&ALWAYS_NEEDS_COMPAT) != 0;
+ return (mCompatibilityFlags&NEVER_NEEDS_COMPAT) != 0;
}
/**
@@ -406,7 +406,7 @@ public class CompatibilityInfo implements Parcelable {
if (!supportsScreen()) {
// This is a larger screen device and the app is not
// compatible with large screens, so diddle it.
- CompatibilityInfo.updateCompatibleScreenFrame(inoutDm, null, inoutDm);
+ CompatibilityInfo.computeCompatibleScaling(inoutDm, inoutDm);
} else {
inoutDm.widthPixels = inoutDm.unscaledWidthPixels;
inoutDm.heightPixels = inoutDm.unscaledHeightPixels;
@@ -443,8 +443,7 @@ public class CompatibilityInfo implements Parcelable {
* @param outRect the output parameter which will contain the result.
* @return Returns the scaling factor for the window.
*/
- public static float updateCompatibleScreenFrame(DisplayMetrics dm,
- Rect outRect, DisplayMetrics outDm) {
+ public static float computeCompatibleScaling(DisplayMetrics dm, DisplayMetrics outDm) {
final int width = dm.unscaledWidthPixels;
final int height = dm.unscaledHeightPixels;
int shortSize, longSize;
@@ -477,12 +476,6 @@ public class CompatibilityInfo implements Parcelable {
scale = 1;
}
- if (outRect != null) {
- final int left = (int)((width-(newWidth*scale))/2);
- final int top = (int)((height-(newHeight*scale))/2);
- outRect.set(left, top, left+newWidth, top+newHeight);
- }
-
if (outDm != null) {
outDm.widthPixels = newWidth;
outDm.heightPixels = newHeight;
diff --git a/core/java/android/content/res/Configuration.java b/core/java/android/content/res/Configuration.java
index d476997..6409aac 100644
--- a/core/java/android/content/res/Configuration.java
+++ b/core/java/android/content/res/Configuration.java
@@ -330,17 +330,17 @@ public final class Configuration implements Parcelable, Comparable<Configuration
if (smallestScreenWidthDp != SMALLEST_SCREEN_WIDTH_DP_UNDEFINED) {
sb.append(" sw"); sb.append(smallestScreenWidthDp); sb.append("dp");
} else {
- sb.append("?swdp");
+ sb.append(" ?swdp");
}
if (screenWidthDp != SCREEN_WIDTH_DP_UNDEFINED) {
sb.append(" w"); sb.append(screenWidthDp); sb.append("dp");
} else {
- sb.append("?wdp");
+ sb.append(" ?wdp");
}
if (screenHeightDp != SCREEN_HEIGHT_DP_UNDEFINED) {
sb.append(" h"); sb.append(screenHeightDp); sb.append("dp");
} else {
- sb.append("?hdp");
+ sb.append(" ?hdp");
}
switch ((screenLayout&SCREENLAYOUT_SIZE_MASK)) {
case SCREENLAYOUT_SIZE_UNDEFINED: sb.append(" ?lsize"); break;
diff --git a/core/java/android/content/res/Resources.java b/core/java/android/content/res/Resources.java
index 81dc46a..70bf524 100755
--- a/core/java/android/content/res/Resources.java
+++ b/core/java/android/content/res/Resources.java
@@ -28,14 +28,13 @@ import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable.ConstantState;
import android.os.Build;
import android.os.Bundle;
-import android.os.SystemProperties;
import android.util.AttributeSet;
import android.util.DisplayMetrics;
import android.util.Log;
+import android.util.Slog;
import android.util.SparseArray;
import android.util.TypedValue;
import android.util.LongSparseArray;
-import android.view.Display;
import java.io.IOException;
import java.io.InputStream;
@@ -1406,6 +1405,12 @@ public class Resources {
public void updateConfiguration(Configuration config,
DisplayMetrics metrics, CompatibilityInfo compat) {
synchronized (mTmpValue) {
+ if (false) {
+ Slog.i(TAG, "**** Updating config of " + this + ": old config is "
+ + mConfiguration + " old compat is " + mCompatibilityInfo);
+ Slog.i(TAG, "**** Updating config of " + this + ": new config is "
+ + config + " new compat is " + compat);
+ }
if (compat != null) {
mCompatibilityInfo = compat;
}
@@ -1471,6 +1476,11 @@ public class Resources {
mConfiguration.screenLayout, mConfiguration.uiMode,
Build.VERSION.RESOURCES_SDK_INT);
+ if (false) {
+ Slog.i(TAG, "**** Updating config of " + this + ": final config is " + mConfiguration
+ + " final compat is " + mCompatibilityInfo);
+ }
+
clearDrawableCache(mDrawableCache, configChanges);
clearDrawableCache(mColorDrawableCache, configChanges);
diff --git a/core/java/android/view/IWindowManager.aidl b/core/java/android/view/IWindowManager.aidl
index bdf04ab..4427eb5 100644
--- a/core/java/android/view/IWindowManager.aidl
+++ b/core/java/android/view/IWindowManager.aidl
@@ -19,6 +19,7 @@ package android.view;
import com.android.internal.view.IInputContext;
import com.android.internal.view.IInputMethodClient;
+import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.graphics.Bitmap;
import android.graphics.Point;
@@ -88,7 +89,7 @@ interface IWindowManager
void overridePendingAppTransition(String packageName, int enterAnim, int exitAnim);
void executeAppTransition();
void setAppStartingWindow(IBinder token, String pkg, int theme,
- CharSequence nonLocalizedLabel, int labelRes,
+ in CompatibilityInfo compatInfo, CharSequence nonLocalizedLabel, int labelRes,
int icon, int windowFlags, IBinder transferFrom, boolean createIfNeeded);
void setAppWillBeHidden(IBinder token);
void setAppVisibility(IBinder token, boolean visible);
diff --git a/core/java/android/view/WindowManagerPolicy.java b/core/java/android/view/WindowManagerPolicy.java
index beb23aa..4d4569c 100644
--- a/core/java/android/view/WindowManagerPolicy.java
+++ b/core/java/android/view/WindowManagerPolicy.java
@@ -17,6 +17,7 @@
package android.view;
import android.content.Context;
+import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.graphics.Rect;
import android.os.IBinder;
@@ -537,7 +538,7 @@ public interface WindowManagerPolicy {
* @see #removeStartingWindow
*/
public View addStartingWindow(IBinder appToken, String packageName,
- int theme, CharSequence nonLocalizedLabel,
+ int theme, CompatibilityInfo compatInfo, CharSequence nonLocalizedLabel,
int labelRes, int icon, int windowFlags);
/**
diff --git a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
index 60066e0..36201ac 100755
--- a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
+++ b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java
@@ -29,6 +29,7 @@ import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.ActivityInfo;
import android.content.pm.PackageManager;
+import android.content.res.CompatibilityInfo;
import android.content.res.Configuration;
import android.content.res.Resources;
import android.database.ContentObserver;
@@ -1110,9 +1111,9 @@ public class PhoneWindowManager implements WindowManagerPolicy {
}
/** {@inheritDoc} */
- public View addStartingWindow(IBinder appToken, String packageName,
- int theme, CharSequence nonLocalizedLabel,
- int labelRes, int icon, int windowFlags) {
+ public View addStartingWindow(IBinder appToken, String packageName, int theme,
+ CompatibilityInfo compatInfo, CharSequence nonLocalizedLabel, int labelRes,
+ int icon, int windowFlags) {
if (!SHOW_STARTING_ANIMATIONS) {
return null;
}
@@ -1158,8 +1159,12 @@ public class PhoneWindowManager implements WindowManagerPolicy {
WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE|
WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM);
+ if (!compatInfo.supportsScreen()) {
+ win.addFlags(WindowManager.LayoutParams.FLAG_COMPATIBLE_WINDOW);
+ }
+
win.setLayout(WindowManager.LayoutParams.MATCH_PARENT,
- WindowManager.LayoutParams.MATCH_PARENT);
+ WindowManager.LayoutParams.MATCH_PARENT);
final WindowManager.LayoutParams params = win.getAttributes();
params.token = appToken;
diff --git a/services/java/com/android/server/AppWidgetService.java b/services/java/com/android/server/AppWidgetService.java
index a4a95a0..65f8b34 100644
--- a/services/java/com/android/server/AppWidgetService.java
+++ b/services/java/com/android/server/AppWidgetService.java
@@ -29,6 +29,7 @@ import java.util.Iterator;
import java.util.List;
import java.util.Locale;
+import org.apache.commons.logging.impl.SimpleLog;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlPullParserException;
import org.xmlpull.v1.XmlSerializer;
diff --git a/services/java/com/android/server/am/ActivityManagerService.java b/services/java/com/android/server/am/ActivityManagerService.java
index 72a2e4a..9989d3b 100644
--- a/services/java/com/android/server/am/ActivityManagerService.java
+++ b/services/java/com/android/server/am/ActivityManagerService.java
@@ -12225,6 +12225,15 @@ public final class ActivityManagerService extends ActivityManagerNative
ac.updateConfiguration(mConfiguration);
}
+ // Make sure all resources in our process are updated
+ // right now, so that anyone who is going to retrieve
+ // resource values after we return will be sure to get
+ // the new ones. This is especially important during
+ // boot, where the first config change needs to guarantee
+ // all resources have that config before following boot
+ // code is executed.
+ mSystemThread.applyConfigurationToResources(newConfig);
+
if (Settings.System.hasInterestingConfigurationChanges(changes)) {
Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG);
msg.obj = new Configuration(mConfiguration);
diff --git a/services/java/com/android/server/am/ActivityStack.java b/services/java/com/android/server/am/ActivityStack.java
index 65ea4f4..2706d49 100644
--- a/services/java/com/android/server/am/ActivityStack.java
+++ b/services/java/com/android/server/am/ActivityStack.java
@@ -1455,6 +1455,8 @@ public class ActivityStack {
if (SHOW_APP_STARTING_PREVIEW && mMainStack) {
mService.mWindowManager.setAppStartingWindow(
next, next.packageName, next.theme,
+ mService.compatibilityInfoForPackageLocked(
+ next.info.applicationInfo),
next.nonLocalizedLabel,
next.labelRes, next.icon, next.windowFlags,
null, true);
@@ -1491,6 +1493,8 @@ public class ActivityStack {
if (SHOW_APP_STARTING_PREVIEW) {
mService.mWindowManager.setAppStartingWindow(
next, next.packageName, next.theme,
+ mService.compatibilityInfoForPackageLocked(
+ next.info.applicationInfo),
next.nonLocalizedLabel,
next.labelRes, next.icon, next.windowFlags,
null, true);
@@ -1617,7 +1621,9 @@ public class ActivityStack {
else if (prev.nowVisible) prev = null;
}
mService.mWindowManager.setAppStartingWindow(
- r, r.packageName, r.theme, r.nonLocalizedLabel,
+ r, r.packageName, r.theme,
+ mService.compatibilityInfoForPackageLocked(
+ r.info.applicationInfo), r.nonLocalizedLabel,
r.labelRes, r.icon, r.windowFlags, prev, showStartingIcon);
}
} else {
diff --git a/services/java/com/android/server/am/CompatModePackages.java b/services/java/com/android/server/am/CompatModePackages.java
index 8949f48..1334bcd 100644
--- a/services/java/com/android/server/am/CompatModePackages.java
+++ b/services/java/com/android/server/am/CompatModePackages.java
@@ -150,9 +150,11 @@ public class CompatModePackages {
}
public CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) {
- return new CompatibilityInfo(ai, mService.mConfiguration.screenLayout,
+ CompatibilityInfo ci = new CompatibilityInfo(ai, mService.mConfiguration.screenLayout,
mService.mConfiguration.smallestScreenWidthDp,
(getPackageFlags(ai.packageName)&COMPAT_FLAG_ENABLED) != 0);
+ //Slog.i(TAG, "*********** COMPAT FOR PKG " + ai.packageName + ": " + ci);
+ return ci;
}
public int computeCompatModeLocked(ApplicationInfo ai) {
diff --git a/services/java/com/android/server/wm/StartingData.java b/services/java/com/android/server/wm/StartingData.java
index 625fcfe..46bb480 100644
--- a/services/java/com/android/server/wm/StartingData.java
+++ b/services/java/com/android/server/wm/StartingData.java
@@ -16,18 +16,23 @@
package com.android.server.wm;
+import android.content.res.CompatibilityInfo;
+
final class StartingData {
final String pkg;
final int theme;
+ final CompatibilityInfo compatInfo;
final CharSequence nonLocalizedLabel;
final int labelRes;
final int icon;
final int windowFlags;
- StartingData(String _pkg, int _theme, CharSequence _nonLocalizedLabel,
+ StartingData(String _pkg, int _theme, CompatibilityInfo _compatInfo,
+ CharSequence _nonLocalizedLabel,
int _labelRes, int _icon, int _windowFlags) {
pkg = _pkg;
theme = _theme;
+ compatInfo = _compatInfo;
nonLocalizedLabel = _nonLocalizedLabel;
labelRes = _labelRes;
icon = _icon;
diff --git a/services/java/com/android/server/wm/WindowManagerService.java b/services/java/com/android/server/wm/WindowManagerService.java
index 9c98296..7760897 100644
--- a/services/java/com/android/server/wm/WindowManagerService.java
+++ b/services/java/com/android/server/wm/WindowManagerService.java
@@ -602,8 +602,7 @@ public class WindowManagerService extends IWindowManager.Stub
final Configuration mTempConfiguration = new Configuration();
- // The frame use to limit the size of the app running in compatibility mode.
- Rect mCompatibleScreenFrame = new Rect();
+ // The desired scaling factor for compatible apps.
float mCompatibleScreenScale;
public static WindowManagerService main(Context context,
@@ -3526,7 +3525,8 @@ public class WindowManagerService extends IWindowManager.Stub
}
public void setAppStartingWindow(IBinder token, String pkg,
- int theme, CharSequence nonLocalizedLabel, int labelRes, int icon,
+ int theme, CompatibilityInfo compatInfo,
+ CharSequence nonLocalizedLabel, int labelRes, int icon,
int windowFlags, IBinder transferFrom, boolean createIfNeeded) {
if (!checkCallingPermission(android.Manifest.permission.MANAGE_APP_TOKENS,
"setAppStartingIcon()")) {
@@ -3676,8 +3676,7 @@ public class WindowManagerService extends IWindowManager.Stub
}
mStartingIconInTransition = true;
- wtoken.startingData = new StartingData(
- pkg, theme, nonLocalizedLabel,
+ wtoken.startingData = new StartingData(pkg, theme, compatInfo, nonLocalizedLabel,
labelRes, icon, windowFlags);
Message m = mH.obtainMessage(H.ADD_STARTING, wtoken);
// Note: we really want to do sendMessageAtFrontOfQueue() because we
@@ -5562,8 +5561,7 @@ public class WindowManagerService extends IWindowManager.Stub
dm.heightPixels = dm.unscaledHeightPixels = mAppDisplayHeight
= mPolicy.getNonDecorDisplayHeight(mRotation, dh);
- mCompatibleScreenScale = CompatibilityInfo.updateCompatibleScreenFrame(
- dm, mCompatibleScreenFrame, null);
+ mCompatibleScreenScale = CompatibilityInfo.computeCompatibleScaling(dm, null);
config.screenWidthDp = (int)(mPolicy.getConfigDisplayWidth(mRotation, dw) / dm.density);
config.screenHeightDp = (int)(mPolicy.getConfigDisplayHeight(mRotation, dh) / dm.density);
@@ -6138,9 +6136,8 @@ public class WindowManagerService extends IWindowManager.Stub
View view = null;
try {
view = mPolicy.addStartingWindow(
- wtoken.token, sd.pkg,
- sd.theme, sd.nonLocalizedLabel, sd.labelRes,
- sd.icon, sd.windowFlags);
+ wtoken.token, sd.pkg, sd.theme, sd.compatInfo,
+ sd.nonLocalizedLabel, sd.labelRes, sd.icon, sd.windowFlags);
} catch (Exception e) {
Slog.w(TAG, "Exception when adding starting window", e);
}
diff --git a/tests/permission/src/com/android/framework/permission/tests/WindowManagerPermissionTests.java b/tests/permission/src/com/android/framework/permission/tests/WindowManagerPermissionTests.java
index e0f0f05..f015378 100644
--- a/tests/permission/src/com/android/framework/permission/tests/WindowManagerPermissionTests.java
+++ b/tests/permission/src/com/android/framework/permission/tests/WindowManagerPermissionTests.java
@@ -164,7 +164,7 @@ public class WindowManagerPermissionTests extends TestCase {
}
try {
- mWm.setAppStartingWindow(null, "foo", 0, null, 0, 0, 0, null, false);
+ mWm.setAppStartingWindow(null, "foo", 0, null, null, 0, 0, 0, null, false);
fail("IWindowManager.setAppStartingWindow did not throw SecurityException as"
+ " expected");
} catch (SecurityException e) {