diff options
10 files changed, 173 insertions, 39 deletions
diff --git a/core/java/android/view/WindowManager.java b/core/java/android/view/WindowManager.java index 6e5127043337..eb3f72eb0e64 100644 --- a/core/java/android/view/WindowManager.java +++ b/core/java/android/view/WindowManager.java @@ -298,12 +298,14 @@ public interface WindowManager extends ViewManager { * Window type: the status bar. There can be only one status bar * window; it is placed at the top of the screen, and all other * windows are shifted down so they are below it. + * In multiuser systems shows on all users' windows. */ public static final int TYPE_STATUS_BAR = FIRST_SYSTEM_WINDOW; /** * Window type: the search bar. There can be only one search bar * window; it is placed at the top of the screen. + * In multiuser systems shows on all users' windows. */ public static final int TYPE_SEARCH_BAR = FIRST_SYSTEM_WINDOW+1; @@ -312,22 +314,26 @@ public interface WindowManager extends ViewManager { * user interaction with the phone (in particular incoming calls). * These windows are normally placed above all applications, but behind * the status bar. + * In multiuser systems shows on all users' windows. */ public static final int TYPE_PHONE = FIRST_SYSTEM_WINDOW+2; /** * Window type: system window, such as low power alert. These windows * are always on top of application windows. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_SYSTEM_ALERT = FIRST_SYSTEM_WINDOW+3; /** * Window type: keyguard window. + * In multiuser systems shows on all users' windows. */ public static final int TYPE_KEYGUARD = FIRST_SYSTEM_WINDOW+4; /** * Window type: transient notifications. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_TOAST = FIRST_SYSTEM_WINDOW+5; @@ -335,6 +341,7 @@ public interface WindowManager extends ViewManager { * Window type: system overlay windows, which need to be displayed * on top of everything else. These windows must not take input * focus, or they will interfere with the keyguard. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_SYSTEM_OVERLAY = FIRST_SYSTEM_WINDOW+6; @@ -342,22 +349,26 @@ public interface WindowManager extends ViewManager { * Window type: priority phone UI, which needs to be displayed even if * the keyguard is active. These windows must not take input * focus, or they will interfere with the keyguard. + * In multiuser systems shows on all users' windows. */ public static final int TYPE_PRIORITY_PHONE = FIRST_SYSTEM_WINDOW+7; /** * Window type: panel that slides out from the status bar + * In multiuser systems shows on all users' windows. */ public static final int TYPE_SYSTEM_DIALOG = FIRST_SYSTEM_WINDOW+8; /** * Window type: dialogs that the keyguard shows + * In multiuser systems shows on all users' windows. */ public static final int TYPE_KEYGUARD_DIALOG = FIRST_SYSTEM_WINDOW+9; /** * Window type: internal system error windows, appear on top of * everything they can. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_SYSTEM_ERROR = FIRST_SYSTEM_WINDOW+10; @@ -365,23 +376,27 @@ public interface WindowManager extends ViewManager { * Window type: internal input methods windows, which appear above * the normal UI. Application windows may be resized or panned to keep * the input focus visible while this window is displayed. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_INPUT_METHOD = FIRST_SYSTEM_WINDOW+11; /** * Window type: internal input methods dialog windows, which appear above * the current input method window. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_INPUT_METHOD_DIALOG= FIRST_SYSTEM_WINDOW+12; /** * Window type: wallpaper window, placed behind any window that wants * to sit on top of the wallpaper. + * In multiuser systems shows only on the owning user's window. */ public static final int TYPE_WALLPAPER = FIRST_SYSTEM_WINDOW+13; /** * Window type: panel that slides out from over the status bar + * In multiuser systems shows on all users' windows. */ public static final int TYPE_STATUS_BAR_PANEL = FIRST_SYSTEM_WINDOW+14; @@ -393,6 +408,8 @@ public interface WindowManager extends ViewManager { * This is exactly like {@link #TYPE_SYSTEM_OVERLAY} except that only the * system itself is allowed to create these overlays. Applications cannot * obtain permission to create secure system overlays. + * + * In multiuser systems shows only on the owning user's window. * @hide */ public static final int TYPE_SECURE_SYSTEM_OVERLAY = FIRST_SYSTEM_WINDOW+15; @@ -400,24 +417,28 @@ public interface WindowManager extends ViewManager { /** * Window type: the drag-and-drop pseudowindow. There is only one * drag layer (at most), and it is placed on top of all other windows. + * In multiuser systems shows only on the owning user's window. * @hide */ public static final int TYPE_DRAG = FIRST_SYSTEM_WINDOW+16; /** * Window type: panel that slides out from under the status bar + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_STATUS_BAR_SUB_PANEL = FIRST_SYSTEM_WINDOW+17; /** * Window type: (mouse) pointer + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_POINTER = FIRST_SYSTEM_WINDOW+18; /** * Window type: Navigation bar (when distinct from status bar) + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_NAVIGATION_BAR = FIRST_SYSTEM_WINDOW+19; @@ -425,6 +446,7 @@ public interface WindowManager extends ViewManager { /** * Window type: The volume level overlay/dialog shown when the user * changes the system volume. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_VOLUME_OVERLAY = FIRST_SYSTEM_WINDOW+20; @@ -432,6 +454,7 @@ public interface WindowManager extends ViewManager { /** * Window type: The boot progress dialog, goes on top of everything * in the world. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_BOOT_PROGRESS = FIRST_SYSTEM_WINDOW+21; @@ -439,30 +462,35 @@ public interface WindowManager extends ViewManager { /** * Window type: Fake window to consume touch events when the navigation * bar is hidden. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_HIDDEN_NAV_CONSUMER = FIRST_SYSTEM_WINDOW+22; /** * Window type: Dreams (screen saver) window, just above keyguard. + * In multiuser systems shows only on the owning user's window. * @hide */ public static final int TYPE_DREAM = FIRST_SYSTEM_WINDOW+23; /** * Window type: Navigation bar panel (when navigation bar is distinct from status bar) + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_NAVIGATION_BAR_PANEL = FIRST_SYSTEM_WINDOW+24; /** * Window type: Behind the universe of the real windows. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_UNIVERSE_BACKGROUND = FIRST_SYSTEM_WINDOW+25; /** * Window type: Display overlay window. Used to simulate secondary display devices. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_DISPLAY_OVERLAY = FIRST_SYSTEM_WINDOW+26; @@ -470,11 +498,20 @@ public interface WindowManager extends ViewManager { /** * Window type: Magnification overlay window. Used to highlight the magnified * portion of a display when accessibility magnification is enabled. + * In multiuser systems shows on all users' windows. * @hide */ public static final int TYPE_MAGNIFICATION_OVERLAY = FIRST_SYSTEM_WINDOW+27; /** + * Window type: Recents. Same layer as {@link #TYPE_SYSTEM_DIALOG} but only appears on + * one user's screen. + * In multiuser systems shows on all users' windows. + * @hide + */ + public static final int TYPE_RECENTS_OVERLAY = FIRST_SYSTEM_WINDOW+28; + + /** * End of types of system windows. */ public static final int LAST_SYSTEM_WINDOW = 2999; @@ -879,6 +916,14 @@ public interface WindowManager extends ViewManager { */ public static final int PRIVATE_FLAG_SET_NEEDS_MENU_KEY = 0x00000008; + /** In a multiuser system if this flag is set and the owner is a system process then this + * window will appear on all user screens. This overrides the default behavior of window + * types that normally only appear on the owning user's screen. Refer to each window type + * to determine its default behavior. + * + * {@hide} */ + public static final int PRIVATE_FLAG_SHOW_FOR_ALL_USERS = 0x00000010; + /** * Control flags that are private to the platform. * @hide diff --git a/core/java/android/view/WindowManagerPolicy.java b/core/java/android/view/WindowManagerPolicy.java index 82f07c7bbbb5..2d399a26beb8 100644 --- a/core/java/android/view/WindowManagerPolicy.java +++ b/core/java/android/view/WindowManagerPolicy.java @@ -500,6 +500,16 @@ public interface WindowManagerPolicy { public int checkAddPermission(WindowManager.LayoutParams attrs); /** + * Check permissions when adding a window. + * + * @param attrs The window's LayoutParams. + * + * @return True if the window may only be shown to the current user, false if the window can + * be shown on all users' windows. + */ + public boolean checkShowToOwnerOnly(WindowManager.LayoutParams attrs); + + /** * Sanitize the layout parameters coming from a client. Allows the policy * to do things like ensure that windows of a specific type can't take * input focus. diff --git a/packages/SystemUI/src/com/android/systemui/power/PowerUI.java b/packages/SystemUI/src/com/android/systemui/power/PowerUI.java index 3c30f5dd77b3..07fd0abb259a 100644 --- a/packages/SystemUI/src/com/android/systemui/power/PowerUI.java +++ b/packages/SystemUI/src/com/android/systemui/power/PowerUI.java @@ -207,6 +207,7 @@ public class PowerUI extends SystemUI { if (intent.resolveActivity(mContext.getPackageManager()) != null) { b.setNegativeButton(R.string.battery_low_why, new DialogInterface.OnClickListener() { + @Override public void onClick(DialogInterface dialog, int which) { mContext.startActivity(intent); dismissLowBatteryWarning(); @@ -216,12 +217,15 @@ public class PowerUI extends SystemUI { AlertDialog d = b.create(); d.setOnDismissListener(new DialogInterface.OnDismissListener() { + @Override public void onDismiss(DialogInterface dialog) { mLowBatteryDialog = null; mBatteryLevelTextView = null; } }); d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT); + d.getWindow().getAttributes().privateFlags |= + WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; d.show(); mLowBatteryDialog = d; } diff --git a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java index ba76bcd79731..5ed0a5ced82f 100755 --- a/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java +++ b/policy/src/com/android/internal/policy/impl/PhoneWindowManager.java @@ -17,7 +17,6 @@ package com.android.internal.policy.impl; import android.app.ActivityManager; import android.app.ActivityManagerNative; -import android.app.IUiModeManager; import android.app.ProgressDialog; import android.app.SearchManager; import android.app.UiModeManager; @@ -101,6 +100,7 @@ import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS; import static android.view.WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED; import static android.view.WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD; import static android.view.WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON; +import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; import static android.view.WindowManager.LayoutParams.SOFT_INPUT_MASK_ADJUST; import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE; import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING; @@ -108,6 +108,7 @@ import static android.view.WindowManager.LayoutParams.LAST_APPLICATION_WINDOW; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_MEDIA; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_MEDIA_OVERLAY; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_PANEL; +import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_STARTING; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_SUB_PANEL; import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_ATTACHED_DIALOG; import static android.view.WindowManager.LayoutParams.TYPE_DISPLAY_OVERLAY; @@ -119,6 +120,7 @@ import static android.view.WindowManager.LayoutParams.TYPE_KEYGUARD_DIALOG; import static android.view.WindowManager.LayoutParams.TYPE_MAGNIFICATION_OVERLAY; import static android.view.WindowManager.LayoutParams.TYPE_PHONE; import static android.view.WindowManager.LayoutParams.TYPE_PRIORITY_PHONE; +import static android.view.WindowManager.LayoutParams.TYPE_RECENTS_OVERLAY; import static android.view.WindowManager.LayoutParams.TYPE_SEARCH_BAR; import static android.view.WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR; @@ -202,7 +204,7 @@ public class PhoneWindowManager implements WindowManagerPolicy { static final int KEYGUARD_LAYER = 11; static final int KEYGUARD_DIALOG_LAYER = 12; // used for Dreams (screensavers with TYPE_DREAM windows) - static final int SCREENSAVER_LAYER = 13; + static final int SCREENSAVER_LAYER = 13; static final int STATUS_BAR_SUB_PANEL_LAYER = 14; static final int STATUS_BAR_LAYER = 15; static final int STATUS_BAR_PANEL_LAYER = 16; @@ -234,7 +236,7 @@ public class PhoneWindowManager implements WindowManagerPolicy { static final int APPLICATION_MEDIA_OVERLAY_SUBLAYER = -1; static final int APPLICATION_PANEL_SUBLAYER = 1; static final int APPLICATION_SUB_PANEL_SUBLAYER = 2; - + static public final String SYSTEM_DIALOG_REASON_KEY = "reason"; static public final String SYSTEM_DIALOG_REASON_GLOBAL_ACTIONS = "globalactions"; static public final String SYSTEM_DIALOG_REASON_RECENT_APPS = "recentapps"; @@ -289,7 +291,7 @@ public class PhoneWindowManager implements WindowManagerPolicy { // Vibrator pattern for haptic feedback of a long press. long[] mLongPressVibePattern; - + // Vibrator pattern for haptic feedback of virtual key press. long[] mVirtualKeyVibePattern; @@ -1199,6 +1201,7 @@ public class PhoneWindowManager implements WindowManagerPolicy { } /** {@inheritDoc} */ + @Override public int checkAddPermission(WindowManager.LayoutParams attrs) { int type = attrs.type; @@ -1236,7 +1239,55 @@ public class PhoneWindowManager implements WindowManagerPolicy { } return WindowManagerGlobal.ADD_OKAY; } - + + @Override + public boolean checkShowToOwnerOnly(WindowManager.LayoutParams attrs) { + + // If this switch statement is modified, modify the comment in the declarations of + // the type in {@link WindowManager.LayoutParams} as well. + switch (attrs.type) { + default: + // These are the windows that by default are shown only to the user that created + // them. If this needs to be overridden, set + // {@link WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS} in + // {@link WindowManager.LayoutParams}. Note that permission + // {@link android.Manifest.permission.INTERNAL_SYSTEM_WINDOW} is required as well. + if ((attrs.privateFlags & PRIVATE_FLAG_SHOW_FOR_ALL_USERS) == 0) { + return true; + } + break; + + // These are the windows that by default are shown to all users. However, to + // protect against spoofing, check permissions below. + case TYPE_APPLICATION_STARTING: + case TYPE_BOOT_PROGRESS: + case TYPE_DISPLAY_OVERLAY: + case TYPE_HIDDEN_NAV_CONSUMER: + case TYPE_KEYGUARD: + case TYPE_KEYGUARD_DIALOG: + case TYPE_MAGNIFICATION_OVERLAY: + case TYPE_NAVIGATION_BAR: + case TYPE_NAVIGATION_BAR_PANEL: + case TYPE_PHONE: + case TYPE_POINTER: + case TYPE_PRIORITY_PHONE: + case TYPE_RECENTS_OVERLAY: + case TYPE_SEARCH_BAR: + case TYPE_STATUS_BAR: + case TYPE_STATUS_BAR_PANEL: + case TYPE_STATUS_BAR_SUB_PANEL: + case TYPE_SYSTEM_DIALOG: + case TYPE_UNIVERSE_BACKGROUND: + case TYPE_VOLUME_OVERLAY: + break; + } + + // Check if third party app has set window to system window type. + return mContext.checkCallingOrSelfPermission( + android.Manifest.permission.INTERNAL_SYSTEM_WINDOW) + != PackageManager.PERMISSION_GRANTED; + } + public void adjustWindowParamsLw(WindowManager.LayoutParams attrs) { switch (attrs.type) { case TYPE_SYSTEM_OVERLAY: @@ -1355,6 +1406,8 @@ public class PhoneWindowManager implements WindowManagerPolicy { return DISPLAY_OVERLAY_LAYER; case TYPE_MAGNIFICATION_OVERLAY: return MAGNIFICATION_OVERLAY_LAYER; + case TYPE_RECENTS_OVERLAY: + return SYSTEM_DIALOG_LAYER; } Log.e(TAG, "Unknown window type: " + type); return APPLICATION_LAYER; @@ -1510,6 +1563,7 @@ public class PhoneWindowManager implements WindowManagerPolicy { com.android.internal.R.styleable.Window_windowAnimationStyle, 0); params.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_FAKE_HARDWARE_ACCELERATED; + params.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; params.setTitle("Starting " + packageName); WindowManager wm = (WindowManager)context.getSystemService(Context.WINDOW_SERVICE); diff --git a/policy/src/com/android/internal/policy/impl/RecentApplicationsDialog.java b/policy/src/com/android/internal/policy/impl/RecentApplicationsDialog.java index b9903dd906ea..2f0d7d6a81d8 100644 --- a/policy/src/com/android/internal/policy/impl/RecentApplicationsDialog.java +++ b/policy/src/com/android/internal/policy/impl/RecentApplicationsDialog.java @@ -94,7 +94,7 @@ public class RecentApplicationsDialog extends Dialog implements OnClickListener Window window = getWindow(); window.requestFeature(Window.FEATURE_NO_TITLE); - window.setType(WindowManager.LayoutParams.TYPE_SYSTEM_DIALOG); + window.setType(WindowManager.LayoutParams.TYPE_RECENTS_OVERLAY); window.setFlags(WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM, WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM); window.setTitle("Recents"); diff --git a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardViewManager.java b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardViewManager.java index 23a96fb2e9e6..7a1e235a97e0 100644 --- a/policy/src/com/android/internal/policy/impl/keyguard/KeyguardViewManager.java +++ b/policy/src/com/android/internal/policy/impl/keyguard/KeyguardViewManager.java @@ -164,6 +164,9 @@ public class KeyguardViewManager { WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_HARDWARE_ACCELERATED; } lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SET_NEEDS_MENU_KEY; + if (isActivity) { + lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; + } lp.inputFeatures |= WindowManager.LayoutParams.INPUT_FEATURE_DISABLE_USER_ACTIVITY; lp.userActivityTimeout = KeyguardViewMediator.AWAKE_INTERVAL_DEFAULT_MS; lp.setTitle(isActivity ? "KeyguardMock" : "Keyguard"); diff --git a/services/java/com/android/server/accessibility/ScreenMagnifier.java b/services/java/com/android/server/accessibility/ScreenMagnifier.java index 14762a14800e..ec3c88c4c598 100644 --- a/services/java/com/android/server/accessibility/ScreenMagnifier.java +++ b/services/java/com/android/server/accessibility/ScreenMagnifier.java @@ -1009,7 +1009,8 @@ public final class ScreenMagnifier implements EventStreamTransformation { case WindowManager.LayoutParams.TYPE_KEYGUARD_DIALOG: case WindowManager.LayoutParams.TYPE_SYSTEM_ERROR: case WindowManager.LayoutParams.TYPE_VOLUME_OVERLAY: - case WindowManager.LayoutParams.TYPE_NAVIGATION_BAR_PANEL: { + case WindowManager.LayoutParams.TYPE_NAVIGATION_BAR_PANEL: + case WindowManager.LayoutParams.TYPE_RECENTS_OVERLAY: { Rect magnifiedRegionBounds = mMagnificationController .getMagnifiedRegionBounds(); Rect touchableRegion = info.touchableRegion; diff --git a/services/java/com/android/server/wm/WindowManagerService.java b/services/java/com/android/server/wm/WindowManagerService.java index 180579dc025c..1b1d85b7adc7 100755 --- a/services/java/com/android/server/wm/WindowManagerService.java +++ b/services/java/com/android/server/wm/WindowManagerService.java @@ -34,6 +34,7 @@ import static android.view.WindowManager.LayoutParams.TYPE_DREAM; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD_DIALOG; import static android.view.WindowManager.LayoutParams.TYPE_KEYGUARD; +import static android.view.WindowManager.LayoutParams.TYPE_RECENTS_OVERLAY; import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_DIALOG; import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_ERROR; import static android.view.WindowManager.LayoutParams.TYPE_UNIVERSE_BACKGROUND; @@ -2083,6 +2084,7 @@ public class WindowManagerService extends IWindowManager.Stub WindowState attachedWindow = null; WindowState win = null; long origId; + final int type = attrs.type; synchronized(mWindowMap) { if (!mDisplayReady) { @@ -2094,7 +2096,7 @@ public class WindowManagerService extends IWindowManager.Stub return WindowManagerGlobal.ADD_DUPLICATE_ADD; } - if (attrs.type >= FIRST_SUB_WINDOW && attrs.type <= LAST_SUB_WINDOW) { + if (type >= FIRST_SUB_WINDOW && type <= LAST_SUB_WINDOW) { attachedWindow = windowForClientLocked(null, attrs.token, false); if (attachedWindow == null) { Slog.w(TAG, "Attempted to add window with token that is not a window: " @@ -2112,31 +2114,29 @@ public class WindowManagerService extends IWindowManager.Stub boolean addToken = false; WindowToken token = mTokenMap.get(attrs.token); if (token == null) { - if (attrs.type >= FIRST_APPLICATION_WINDOW - && attrs.type <= LAST_APPLICATION_WINDOW) { + if (type >= FIRST_APPLICATION_WINDOW && type <= LAST_APPLICATION_WINDOW) { Slog.w(TAG, "Attempted to add application window with unknown token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } - if (attrs.type == TYPE_INPUT_METHOD) { + if (type == TYPE_INPUT_METHOD) { Slog.w(TAG, "Attempted to add input method window with unknown token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } - if (attrs.type == TYPE_WALLPAPER) { + if (type == TYPE_WALLPAPER) { Slog.w(TAG, "Attempted to add wallpaper window with unknown token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } - if (attrs.type == TYPE_DREAM) { + if (type == TYPE_DREAM) { Slog.w(TAG, "Attempted to add Dream window with unknown token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } token = new WindowToken(this, attrs.token, -1, false); addToken = true; - } else if (attrs.type >= FIRST_APPLICATION_WINDOW - && attrs.type <= LAST_APPLICATION_WINDOW) { + } else if (type >= FIRST_APPLICATION_WINDOW && type <= LAST_APPLICATION_WINDOW) { AppWindowToken atoken = token.appWindowToken; if (atoken == null) { Slog.w(TAG, "Attempted to add window with non-application token " @@ -2147,25 +2147,25 @@ public class WindowManagerService extends IWindowManager.Stub + token + ". Aborting."); return WindowManagerGlobal.ADD_APP_EXITING; } - if (attrs.type == TYPE_APPLICATION_STARTING && atoken.firstWindowDrawn) { + if (type == TYPE_APPLICATION_STARTING && atoken.firstWindowDrawn) { // No need for this guy! if (localLOGV) Slog.v( TAG, "**** NO NEED TO START: " + attrs.getTitle()); return WindowManagerGlobal.ADD_STARTING_NOT_NEEDED; } - } else if (attrs.type == TYPE_INPUT_METHOD) { + } else if (type == TYPE_INPUT_METHOD) { if (token.windowType != TYPE_INPUT_METHOD) { Slog.w(TAG, "Attempted to add input method window with bad token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } - } else if (attrs.type == TYPE_WALLPAPER) { + } else if (type == TYPE_WALLPAPER) { if (token.windowType != TYPE_WALLPAPER) { Slog.w(TAG, "Attempted to add wallpaper window with bad token " + attrs.token + ". Aborting."); return WindowManagerGlobal.ADD_BAD_APP_TOKEN; } - } else if (attrs.type == TYPE_DREAM) { + } else if (type == TYPE_DREAM) { if (token.windowType != TYPE_DREAM) { Slog.w(TAG, "Attempted to add Dream window with bad token " + attrs.token + ". Aborting."); @@ -2185,6 +2185,7 @@ public class WindowManagerService extends IWindowManager.Stub } mPolicy.adjustWindowParamsLw(win.mAttrs); + win.setShowToOwnerOnlyLocked(mPolicy.checkShowToOwnerOnly(attrs)); res = mPolicy.prepareAddWindowLw(win, attrs); if (res != WindowManagerGlobal.ADD_OKAY) { @@ -2213,8 +2214,7 @@ public class WindowManagerService extends IWindowManager.Stub win.attach(); mWindowMap.put(client.asBinder(), win); - if (attrs.type == TYPE_APPLICATION_STARTING && - token.appWindowToken != null) { + if (type == TYPE_APPLICATION_STARTING && token.appWindowToken != null) { token.appWindowToken.startingWindow = win; if (DEBUG_STARTING_WINDOW) Slog.v (TAG, "addWindow: " + token.appWindowToken + " startingWindow=" + win); @@ -2222,19 +2222,19 @@ public class WindowManagerService extends IWindowManager.Stub boolean imMayMove = true; - if (attrs.type == TYPE_INPUT_METHOD) { + if (type == TYPE_INPUT_METHOD) { win.mGivenInsetsPending = true; mInputMethodWindow = win; addInputMethodWindowToListLocked(win); imMayMove = false; - } else if (attrs.type == TYPE_INPUT_METHOD_DIALOG) { + } else if (type == TYPE_INPUT_METHOD_DIALOG) { mInputMethodDialogs.add(win); addWindowToListInOrderLocked(win, true); adjustInputMethodDialogsLocked(); imMayMove = false; } else { addWindowToListInOrderLocked(win, true); - if (attrs.type == TYPE_WALLPAPER) { + if (type == TYPE_WALLPAPER) { mLastWallpaperTimeoutTime = 0; adjustWallpaperWindowsLocked(); } else if ((attrs.flags&FLAG_SHOW_WALLPAPER) != 0) { @@ -5404,6 +5404,22 @@ public class WindowManagerService extends IWindowManager.Stub synchronized (mWindowMap) { mCurrentUserId = newUserId; mPolicy.setCurrentUserLw(newUserId); + + // Hide windows that should not be seen by the new user. + DisplayContentsIterator iterator = new DisplayContentsIterator(); + while (iterator.hasNext()) { + final WindowList windows = iterator.next().getWindowList(); + for (int i = 0; i < windows.size(); i++) { + final WindowState win = windows.get(i); + if (win.isOtherUsersAppWindow()) { + Slog.w(TAG, "current user violation " + newUserId + " hiding " + + win + ", attrs=" + win.mAttrs.type + ", belonging to " + + win.mOwnerUid); + win.hideLw(false); + } + } + } + performLayoutAndPlaceSurfacesLocked(); } } @@ -8784,6 +8800,7 @@ public class WindowManagerService extends IWindowManager.Stub final int type = attrs.type; if (canBeSeen && (type == TYPE_SYSTEM_DIALOG + || type == TYPE_RECENTS_OVERLAY || type == TYPE_KEYGUARD || type == TYPE_SYSTEM_ERROR)) { mInnerFields.mSyswin = true; diff --git a/services/java/com/android/server/wm/WindowState.java b/services/java/com/android/server/wm/WindowState.java index d23448b783cf..6e388f24836f 100644 --- a/services/java/com/android/server/wm/WindowState.java +++ b/services/java/com/android/server/wm/WindowState.java @@ -22,9 +22,6 @@ import static android.view.WindowManager.LayoutParams.LAST_SUB_WINDOW; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD; import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD_DIALOG; import static android.view.WindowManager.LayoutParams.TYPE_WALLPAPER; -import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION; -import static android.view.WindowManager.LayoutParams.LAST_APPLICATION_WINDOW; -import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_STARTING; import com.android.server.input.InputWindowHandle; @@ -36,7 +33,6 @@ import android.graphics.Rect; import android.graphics.RectF; import android.graphics.Region; import android.os.IBinder; -import android.os.Process; import android.os.RemoteException; import android.os.UserHandle; import android.util.Slog; @@ -263,7 +259,10 @@ final class WindowState implements WindowManagerPolicy.WindowState { DisplayContent mDisplayContent; // UserId and appId of the owner. Don't display windows of non-current user. - final int mOwnerUid; + int mOwnerUid; + + /** When true this window can be displayed on screens owther than mOwnerUid's */ + private boolean mShowToOwnerOnly; WindowState(WindowManagerService service, Session s, IWindow c, WindowToken token, WindowState attachedWindow, int seq, WindowManager.LayoutParams a, @@ -654,6 +653,7 @@ final class WindowState implements WindowManagerPolicy.WindowState { * surface, or we are in the process of running an exit animation * that will remove the surface, or its app token has been hidden. */ + @Override public boolean isVisibleLw() { final AppWindowToken atoken = mAppToken; return mHasSurface && mPolicyVisibility && !mAttachedHidden @@ -669,6 +669,7 @@ final class WindowState implements WindowManagerPolicy.WindowState { * for this "hidden behind keyguard" state rather than overloading * mPolicyVisibility. Ungh. */ + @Override public boolean isVisibleOrBehindKeyguardLw() { if (mRootToken.waitingToShow && mService.mNextAppTransition != WindowManagerPolicy.TRANSIT_UNSET) { @@ -940,7 +941,7 @@ final class WindowState implements WindowManagerPolicy.WindowState { boolean showLw(boolean doAnimation, boolean requestAnim) { if (isOtherUsersAppWindow()) { - Slog.w(TAG, "Current user " + mService.mCurrentUserId + " trying to display " + Slog.w(TAG, "current user violation " + mService.mCurrentUserId + " trying to display " + this + ", type " + mAttrs.type + ", belonging to " + mOwnerUid); return false; } @@ -1025,15 +1026,12 @@ final class WindowState implements WindowManagerPolicy.WindowState { return mDisplayContent.isDefaultDisplay; } + public void setShowToOwnerOnlyLocked(boolean showToOwnerOnly) { + mShowToOwnerOnly = showToOwnerOnly; + } + boolean isOtherUsersAppWindow() { - final int type = mAttrs.type; - if ((UserHandle.getUserId(mOwnerUid) != mService.mCurrentUserId) - && (mOwnerUid != Process.SYSTEM_UID) - && (type >= TYPE_BASE_APPLICATION) && (type <= LAST_APPLICATION_WINDOW) - && (type != TYPE_APPLICATION_STARTING)) { - return true; - } - return false; + return mShowToOwnerOnly && UserHandle.getUserId(mOwnerUid) != mService.mCurrentUserId; } private static void applyInsets(Region outRegion, Rect frame, Rect inset) { @@ -1072,6 +1070,8 @@ final class WindowState implements WindowManagerPolicy.WindowState { pw.print(prefix); pw.print("mDisplayId="); pw.print(mDisplayContent.getDisplayId()); pw.print(" mSession="); pw.print(mSession); pw.print(" mClient="); pw.println(mClient.asBinder()); + pw.print(prefix); pw.print("mOwnerUid="); pw.print(mOwnerUid); + pw.print(" mShowToOwnerOnly="); pw.println(mShowToOwnerOnly); pw.print(prefix); pw.print("mAttrs="); pw.println(mAttrs); pw.print(prefix); pw.print("Requested w="); pw.print(mRequestedWidth); pw.print(" h="); pw.print(mRequestedHeight); diff --git a/services/java/com/android/server/wm/WindowStateAnimator.java b/services/java/com/android/server/wm/WindowStateAnimator.java index acf452ffc713..817a2344a545 100644 --- a/services/java/com/android/server/wm/WindowStateAnimator.java +++ b/services/java/com/android/server/wm/WindowStateAnimator.java @@ -1335,7 +1335,7 @@ class WindowStateAnimator { // This must be called while inside a transaction. boolean performShowLocked() { if (mWin.isOtherUsersAppWindow()) { - Slog.w(TAG, "Current user " + mService.mCurrentUserId + " trying to display " + Slog.w(TAG, "current user violation " + mService.mCurrentUserId + " trying to display " + this + ", type " + mWin.mAttrs.type + ", belonging to " + mWin.mOwnerUid); return false; } |